Pendant que je testais le SOP, je suis arrivé à ce scénario, deux documents ont une relation avec le même domaine que je m'attendais et cela génère une erreur lorsque j'essaie d'obtenir l'emplacement.
Pour reproduire le problème:
let opened = window.open("https://www.google.com")
opened.location.toString()
qui retournera l'emplacement correctdocument.domain = "www.google.com"
à partir du premier onglet, faites opened.location.toString()
et vous obtiendrez une erreur
Uncaught DOMException: Blocked a frame with Origin "https://www.google.com" from accessing a cross-Origin frame.
at <anonymous>:1:12
Quelqu'un peut-il expliquer ce comportement étrange?
Cette erreur n'est pas un bug. La politique de même origine est un mécanisme de sécurité qui garantit que les objets de fenêtre n'ont accès qu'aux informations qu'ils sont autorisés à obtenir. Dans votre cas, cela inclut l'accès à opened.location
.
Lors de la création, les deux onglets ont la même origine, ce qui permet au premier d'accéder à opened.location
. Mais après l'appel à document.domain='www.google.com'
, ils ne le font plus.
"Quoi? Mais dans les deux onglets, window.location.Origin
sont identiques "
Oui, mais c'est un peu plus complexe. L'origine est définie par le schéma/hôte/tuple de port, voir la réponse de @ TheUnknown pour plus de détails. Le schéma et l'hôte restent les mêmes tout au long, et ils sont ceux inclus dans la chaîne de window.location.Origin
.
La chose délicate à savoir est que tout appel à document.domain
, comprenant document.domain = document.domain
, entraîne le remplacement du numéro de port par null
, provoquant ainsi une différence dans les origines des deux onglets et les empêchant de communiquer des informations comme opened.location
les uns avec les autres, d'où l'erreur.
Informations extraites de MDN's guide sur la même politique d'origine
Tout d'abord, je vous recommande de lire Politique de même origine .
La stratégie de même origine est un mécanisme de sécurité critique qui limite la façon dont un document ou un script chargé à partir d'une origine peut interagir avec une ressource d'une autre origine. Il permet d'isoler les documents potentiellement malveillants, réduisant ainsi les vecteurs d'attaque possibles.
Deux URL ont la même origine si le protocole , le port (si spécifié) et l'hôte sont identiques pour les deux. Vous pouvez voir cela référencé comme le "schéma/hôte/port Tuple", ou simplement "Tuple". (Un "tuple" est un ensemble d'éléments qui forment ensemble un tout - une forme générique pour double/triple/quadruple/quintuple/etc.)
Dans ce cas particulier, vous ouvrez une fenêtre avec le protocole [~ # ~] https [~ # ~], cependant, lorsque vous définissez le domaine, le protocole est modifié en [~ # ~] http [~ # ~] , voir l'image ci-dessous:
Selon 1 , si les protocoles ne sont pas les mêmes, alors c'est une violation du principe et donc vous obtenez l'erreur
DOMException non bloquée: blocage d'une trame avec l'origine " https://www.google.com " contre l'accès à une origine croisée Cadre.
cross-Origin est le mot-clé ici.
Vérifiez également ceci SecurityError: Bloqué une trame avec Origin d'accéder à une trame cross-Origin pour plus de détails.
Ce sera un peu informatif (énonce simplement des faits), néanmoins:
Après avoir modifié domain
dans la fenêtre B, la fenêtre B arrête la fenêtre de comptabilité A en tant que opener
.
La fenêtre A n'étant plus considérée comme une ouverture de la fenêtre B, l'accès est interdit.
Cela me fait penser que la modification de document.domain
est considéré comme potentiellement non sécurisé et est "puni" en rendant orphelin la fenêtre enfant.