Il peut être parfois nécessaire d’utiliser une iframe, pour accéder par exemple à des cookies sur un autre site, se logguer, etc. Le problème est que si vous utilisez une iframe sur un domaine différent, le navigateur va vous renvoyer une erreur.

iframe et sécurité

Lorsque les domaine ou port diffèrent entre les deux frames, le navigateur va refuser la communication. En effet, imaginez que vous puissiez afficher une iframe cachée dans votre page, pour ensuite y récupérer des informations sensibles.

Exemple : dans mon site example.org, je mets une iframe vers mabanque.com et je récupère les informations bancaires de l’utilisateur de mon site (si celui-ci est déjà loggué sur le site de la banque).

La solution

Pour autoriser la communication entre les frames, il faut utiliser le protocole de communication entre les fenêtres.

Cette communication se fait par évènement : une fenêtre envoie à l’autre un objet1, qui le reçoit en ajoutant un handler sur l’évènement « message ».

Exemple

Dans notre exemple, l’iframe enverra un message à la fenêtre principale.

Fenêtre principale :

  1. // On rajoute un handler d'évènement
  2. function onMessage(e)
  3. {
  4.   // Vous pouvez vérifier l'origine de la fenêtre avec e.origin
  5.   document.getElementById('div-test').innerHTML = "Réception du message " + JSON.stringify(e.data);
  6. }
  7. window.addEventListener("message", onMessage, true);

Fenêtre iframe

  1. var dstWindow = window.parent;
  2. // Vous pouvez choisir le domaine vers lequel vous acceptez d'envoyer un message (ici, tous les domaines)
  3. dstWindow.postMessage([1,2,3], '*');

div-test pour la réception du message


1 : en fonction du navigateur, vous ne pourrez passer que des chaînes de caractères (Firefox 3.6 par exemple – Chrome supportant les objets). Pour pallier ce défaut, vous pouvez utiliser JSON.stringify et JSON.parse pour passer des objets comme des chaines ou des variables. Pour tout ce qui est DOM, ce n’est pas possible de faire passer les handler d’évènement définis dans la fenêtre source.

2 Comments

  1. Philippe says:

    Hello Cyril,

    Je suis actuellement sur ce genre de problématique pour intégrer une application dans une autre sur des domaines différents.
    Ce résultat me convenait parfaitement jusqu’à ce que j’essaye sur IE7 et là, marche pô 🙁
    IE7 est un requirement client, donc pas possible d’utiliser autre chose.
    Saurais-tu dire ce qui ne fonctionne pas dans ce cas ?
    Merci pour ton aide.

  2. Cyril says:

    Salut Philippe,

    Il semble que postMessage ne soit pas supporté par IE7, il va donc te falloir trouver une autre solution.

    Je suis tombé sur un article et une autre page intéressants :
    http://softwareas.com/cross-domain-communication-with-iframes : un article qui explique différentes manière de faire de la communication cross-domain
    http://benalman.com/projects/jquery-postmessage-plugin/ : un plugin jQuery qui, a priori, utilise les techniques énoncées dans l’article ci-dessus pour faire la communication cross-domain.

    Par ailleurs, si tes pages sont sur des domaines identiques (même si elles sont sur des domaines différents – cf document.domain), alors tu devrais pouvoir exécuter du javascript directement en appelant les fonctions.

    Cyril

Leave a Reply