Question Comment identifier si une page Web est chargée dans un iframe ou directement dans la fenêtre du navigateur?


J'écris une application Facebook basée sur iframe. Maintenant, je veux utiliser la même page html pour rendre le site normal ainsi que la page de toile dans facebook. Je veux savoir si je peux déterminer si la page a été chargée dans l'iframe ou directement dans le navigateur?


459
2017-11-28 15:45


origine


Réponses:


Les navigateurs peuvent bloquer l'accès à window.top en raison de même politique d'origine. Des bogues IE ont également lieu. Voici le code de travail:

function inIframe () {
    try {
        return window.self !== window.top;
    } catch (e) {
        return true;
    }
}

top et self sont les deux window objets (avec parent), donc vous voyez si votre fenêtre est la fenêtre supérieure.


863
2017-11-28 15:47



window.frameElement Renvoie l'élément (tel que <iframe> ou <object>) dans lequel la fenêtre est incorporée ou null si la fenêtre est de niveau supérieur. Donc, le code d'identification ressemble à

if (window.frameElement) {
  // in frame
}
else {
  // not in frame
}

Ceci est standard et plutôt nouveau méthode.  Cela fonctionne exactement dans Chrome et Firefox. Je ne peux pas le recommander comme solution universelle mais il faut le mentionner ici je pense.


66
2017-09-07 22:55



RoBorg est correct, mais je voulais ajouter une note de côté.

Dans IE7 / IE8 lorsque Microsoft a ajouté des onglets à leur navigateur, ils ont cassé une chose qui causera des ravages avec votre JS si vous ne faites pas attention.

Imaginez cette mise en page:

MainPage.html
  IframedPage1.html   (named "foo")
  IframedPage2.html   (named "bar")
    IframedPage3.html (named "baz")

Maintenant dans le cadre "baz" vous cliquez sur un lien (pas de cible, charge dans le cadre "baz") ça fonctionne bien.

Si la page qui est chargée, appelons-la special.html, utilise JS pour vérifier si "elle" a un cadre parent nommé "bar" elle retournera vrai (attendu).

Maintenant, supposons que la page special.html lors du chargement vérifie le cadre parent (pour l'existence et son nom, et s'il s'agit de "bar", il se recharge dans le cadre de la barre.

if(window.parent && window.parent.name == 'bar'){
  window.parent.location = self.location;
}

Jusqu'ici tout va bien. Maintenant vient le bug.

Disons qu'au lieu de cliquer sur le lien d'origine comme d'habitude, et de charger la page special.html dans le cadre "baz", vous l'avez cliqué au milieu ou choisi de l'ouvrir dans un nouvel onglet.

Lorsque cette nouvelle page est chargée (sans cadres parents du tout!) IE va entrer dans une boucle sans fin de chargement de la page! car IE "copie" la structure de l'image dans JavaScript de sorte que le nouvel onglet DOES ait un parent, et que ce parent ait le nom "bar".

Les bonnes nouvelles, est-ce vérifier:

if(self == top){
  //this returns true!
}

dans ce nouvel onglet retourne true, et donc vous pouvez tester cette condition étrange.


25
2017-11-28 17:53



La réponse acceptée ne fonctionnait pas pour moi dans le script de contenu d’une extension de Firefox 6.0 (Addon-SDK 1.0): Firefox exécute le script de contenu dans chacune des fenêtres: au niveau supérieur et dans tous les iframes.

Dans le script de contenu, j'obtiens les résultats suivants:

 (window !== window.top) : false 
 (window.self !== window.top) : true

La chose étrange à propos de cette sortie est qu'elle est toujours la même, que le code soit exécuté dans une iframe ou dans la fenêtre de niveau supérieur.

D'autre part, Google Chrome semble exécuter mon script de contenu une seule fois dans la fenêtre de haut niveau, ce qui ne fonctionnerait donc pas du tout.

Ce qui a finalement fonctionné pour moi dans un script de contenu dans les deux navigateurs est la suivante:

 console.log(window.frames.length + ':' + parent.frames.length);

Sans les iframes, cela imprime 0:0, dans une fenêtre de niveau supérieur contenant un cadre, il imprime 1:1, et dans la seule iframe d'un document qu'il imprime 0:1.

Cela permet à mon extension de déterminer dans les deux navigateurs si des iframes sont présents et dans Firefox si elle est exécutée dans l'un des iframes.


16
2017-10-14 14:32



J'utilise ceci:

var isIframe = (self.frameElement && (self.frameElement+"").indexOf("HTMLIFrameElement") > -1);

5
2018-06-20 10:04



Je ne suis pas sûr de savoir comment cet exemple fonctionne pour les anciens navigateurs Web, mais je l'utilise pour IE, Firefox et Chrome sans problème:

var iFrameDetection = (window === window.parent) ? false : true;

3
2017-11-19 09:30



Utilisez cette fonction javascript comme exemple pour accomplir cela.

function isNoIframeOrIframeInMyHost() {
// Validation: it must be loaded as the top page, or if it is loaded in an iframe 
// then it must be embedded in my own domain.
// Info: IF top.location.href is not accessible THEN it is embedded in an iframe 
// and the domains are different.
var myresult = true;
try {
    var tophref = top.location.href;
    var tophostname = top.location.hostname.toString();
    var myhref = location.href;
    if (tophref === myhref) {
        myresult = true;
    } else if (tophostname !== "www.yourdomain.com") {
        myresult = false;
    }
} catch (error) { 
  // error is a permission error that top.location.href is not accessible 
  // (which means parent domain <> iframe domain)!
    myresult = false;
}
return myresult;
}

2
2017-09-21 02:32



Étant donné que vous posez la question dans le contexte d’une application facebook, vous pouvez envisager de le détecter sur le serveur lors de la demande initiale. Facebook transmettra un ensemble de données de chaîne de requête, y compris la clé fb_sig_user si elle est appelée depuis un iframe.

Puisque vous avez probablement besoin de vérifier et d'utiliser ces données de toute façon dans votre application, utilisez-la pour déterminer le contexte approprié à afficher.


1
2017-12-11 22:04



J'ai effectivement utilisé pour vérifier window.parent et cela a fonctionné pour moi, mais dernièrement window est un objet cyclique et a toujours une clé parente, iframe ou aucun iframe.

Comme les commentaires suggèrent une comparaison difficile avec les travaux window.parent. Vous ne savez pas si cela fonctionnera si iframe est exactement la même page Web que le parent.

window === window.parent;

1
2018-03-04 03:47