En-tête Cross-Origin-Opener-Policy (COOP)
L'en-tête de réponse HTTP Cross-Origin-Opener-Policy (COOP) permet à un site web de contrôler si un nouveau document de premier niveau, ouvert avec Window.open() ou lors de la navigation vers une nouvelle page, est ouvert dans le même groupe de contexte de navigation (BCG) ou dans un nouveau groupe de contexte de navigation.
Lorsqu'il est ouvert dans un nouveau BCG, toute référence entre le nouveau document et son ouvreur est rompue, et le nouveau document peut être isolé en processus de son ouvreur.
Cela garantit que des attaquants potentiels ne peuvent pas ouvrir vos documents avec Window.open() puis utiliser la valeur retournée pour accéder à son objet global, ce qui prévient un ensemble d'attaques inter-origines appelées XS-Leaks (angl.).
Cela signifie aussi que tout objet ouvert par votre document dans un nouveau BCG ne peut pas y accéder avec window.opener.
Cela vous permet d'avoir un contrôle plus fin sur les références à une fenêtre que rel=noopener, qui affecte les navigations sortantes mais pas les documents ouverts avec Window.open().
Le comportement dépend des politiques du nouveau document et de son ouvreur, et si le nouveau document est ouvert après une navigation ou avec Window.open().
| Type d'en-tête | En-tête de réponse |
|---|
Syntaxe
Cross-Origin-Opener-Policy: unsafe-none
Cross-Origin-Opener-Policy: same-origin-allow-popups
Cross-Origin-Opener-Policy: same-origin
Cross-Origin-Opener-Policy: noopener-allow-popups
Directives
unsafe-none-
Le document autorise le partage de son groupe de contexte de navigation avec n'importe quel autre document, ce qui peut donc être dangereux. Il sert à exclure un document de l'utilisation de COOP pour l'isolation des processus. Il s'agit de la valeur par défaut.
Lors des navigations, les documents avec
unsafe-noneouvriront toujours et seront toujours ouverts dans un nouveau BCG — sauf si l'autre document a égalementunsafe-none(ou n'a pas de valeur de directive COOP).Avec
Window.open(), les documents avecunsafe-noneouvriront toujours les documents ayant une autre valeur dans un nouveau BCG. Cependant, les documents avecunsafe-nonepeuvent être ouverts dans le même BCG si l'ouvreur possède la directivesame-origin-allow-popups,noopener-allow-popupsouunsafe-none. Un document avecsame-originouvrira toujours un document avecunsafe-nonedans un nouveau BCG. same-origin-
Le document autorise le chargement dans des BCG qui utilisent COOP et ne contiennent que des documents de même origine. Cela sert à fournir la compartimentation inter-origines pour un BCG.
Les documents avec
same-originn'ouvriront et ne seront ouverts dans le même BCG que si les deux documents sont de même origine et possèdent la directivesame-origin. same-origin-allow-popups-
Cette directive est similaire à
same-origin, sauf qu'elle permet d'ouvrir des documents avecWindow.open()dans le même BCG s'ils ont une valeur COOP deunsafe-none.Cette directive sert à assouplir la restriction
same-originpour les intégrations où un document a besoin des avantages de la compartimentation inter-origines mais doit aussi ouvrir et conserver une référence à des documents inter-origines de confiance. Par exemple, lors de l'utilisation d'un service inter-origines pour OAuth ou les paiements.Un document avec cette directive peut ouvrir un document dans le même BCG avec
Window.open()si ce dernier a une valeur COOP deunsafe-none. Dans ce cas, il n'est pas important que le document ouvert soit inter-site ou même site.Sinon, les documents avec
same-origin-allow-popupsn'ouvriront et ne seront ouverts dans le même BCG que si les deux documents sont de même origine et possèdent la directivesame-origin-allow-popups. noopener-allow-popups-
Les documents avec cette directive sont toujours ouverts dans un nouveau BCG, sauf lorsqu'ils sont ouverts par navigation depuis un document qui possède aussi
noopener-allow-popups. Elle est utilisée pour les cas où il est nécessaire d'isoler en processus des documents de même origine.Cela coupe les connexions entre le nouveau document et son ouvreur, isolant le contexte de navigation pour le document courant, quelle que soit l'origine du document ouvreur. Cela garantit que l'ouvreur ne peut pas exécuter de scripts dans les documents ouverts et inversement — même s'ils sont de même origine.
Lors des navigations, un document avec cette directive ouvrira toujours les autres documents dans un nouveau BCG sauf s'ils sont de même origine et possèdent la directive
noopener-allow-popups. AvecWindow.open(), un document avec cette directive ouvrira les documents dans un nouveau BCG sauf s'ils ontunsafe-none; dans ce cas, il n'est pas important qu'ils soient même site ou inter-site.
Description
De manière générale, vous devez définir vos politiques de façon à ce que seules les ressources de même origine et les ressources inter-origines de confiance, qui ont besoin de pouvoir s'exécuter mutuellement, soient autorisées à s'ouvrir dans le même groupe de contexte de navigation. Les autres ressources doivent être isolées inter-origines dans leur propre groupe.
Les sections suivantes indiquent si les documents seront ouverts dans le même BCG ou dans un nouveau BCG à la suite d'une navigation ou de l'ouverture d'une fenêtre par programme.
Note :
La spécification utilise le terme « fenêtre contextuelle » pour désigner tout document ouvert avec Window.open(), qu'il s'agisse d'une fenêtre contextuelle, d'un onglet, d'une fenêtre ou d'un autre contexte.
Navigations
Lors des navigations entre documents, le nouveau document s'ouvre dans le même BCG si les deux documents ont des « politiques COOP correspondantes », sinon dans un nouveau BCG.
Les politiques correspondent si les deux documents ont la politique unsafe-none, ou si les politiques sont identiques et que les documents sont de même origine.
Le tableau ci‑dessous montre comment cette règle détermine si les documents sont ouverts dans le même BCG ou dans un nouveau BCG, selon les différentes valeurs de directive.
| Ouverture (↓) / Ouvert (→) | unsafe-none |
same-origin-allow-popups |
same-origin |
noopener-allow-popups |
|---|---|---|---|---|
unsafe-none |
Identique | Nouveau | Nouveau | Nouveau |
same-origin-allow-popups |
Nouveau | Identique si même origine | Nouveau | Nouveau |
same-origin |
Nouveau | Nouveau | Identique si même origine | Nouveau |
noopener-allow-popups |
Nouveau | Nouveau | Nouveau | Identique si même origine |
Ouverture avec Window.open()
Lors de l'ouverture d'un document avec Window.open(), le nouveau document est ouvert dans un nouveau BCG selon les règles suivantes, évaluées dans l'ordre :
- Si le nouveau document a COOP défini sur
noopener-allow-popups=> ouvrir le nouveau document dans un nouveau BCG - Si le nouveau document a COOP défini sur
unsafe-noneet que le document ouvreur a COOP défini sursame-origin-allow-popupsounoopener-allow-popups=> ouvrir le nouveau document dans le même BCG - Si le nouveau document et le document ouvreur ont des politiques COOP correspondantes => ouvrir le nouveau document dans le même BCG
- Sinon, ouvrir le nouveau document dans un nouveau BCG
Le tableau ci‑dessous montre comment ces règles déterminent si les documents sont ouverts dans le même BCG ou dans un nouveau BCG, selon les différentes valeurs de directive.
| Ouverture (↓) / Ouvert (→) | unsafe-none |
same-origin-allow-popups |
same-origin |
noopener-allow-popups |
|---|---|---|---|---|
unsafe-none |
Identique | Nouveau | Nouveau | Nouveau |
same-origin-allow-popups |
Identique | Identique si même origine | Nouveau | Nouveau |
same-origin |
Nouveau | Nouveau | Identique si même origine | Nouveau |
noopener-allow-popups |
Identique | Nouveau | Nouveau | Nouveau |
Exemples
>Fonctionnalités dépendant de la compartimentation inter-origines
Certaines fonctionnalités, comme l'accès aux objets SharedArrayBuffer ou l'utilisation de Performance.now() avec des minuteurs non bridés, ne sont disponibles que si votre document est isolé inter-origines.
Pour utiliser ces fonctionnalités dans un document, vous devez définir l'en-tête COOP sur same-origin et l'en-tête Cross-Origin-Embedder-Policy sur require-corp (ou credentialless).
De plus, la fonctionnalité ne doit pas être bloquée par Permissions-Policy: cross-origin-isolated.
Cross-Origin-Opener-Policy: same-origin
Cross-Origin-Embedder-Policy: require-corp
Vous pouvez utiliser les propriétés Window.crossOriginIsolated et WorkerGlobalScope.crossOriginIsolated pour vérifier si un document est isolé inter-origines et donc si les fonctionnalités sont restreintes :
const monWorker = new Worker("worker.js");
if (crossOriginIsolated) {
const tampon = new SharedArrayBuffer(16);
monWorker.postMessage(tampon);
} else {
const tampon = new ArrayBuffer(16);
monWorker.postMessage(tampon);
}
Rompre la relation avec l'ouverture
Considérez une origine hypothétique example.com qui héberge deux applications très différentes sur la même origine :
- Une application de chat à
/chatqui permet à n'importe quel utilisateur·ice de contacter n'importe quel autre utilisateur·ice et de lui envoyer des messages. - Une application de gestion de mots de passe à
/passwordsqui contient tous les mots de passe de l'utilisateur·ice,es mots de passes pour différents services.
Les administrateur·ice·s de l'application « des mots de passe » souhaiteraient s'assurer qu'elle ne peut pas être scriptée directement par l'application de chat, qui, de par sa nature, a une surface XSS plus importante. La « bonne solution » pour isoler ces applications serait de les héberger sur des origines différentes, mais dans certains cas ce n'est pas possible, et ces deux applications doivent rester sur une même origine pour des raisons historiques, commerciales ou de marque.
L'en-tête Cross-Origin-Opener-Policy: noopener-allow-popups peut être utilisé pour s'assurer qu'un document ne peut pas être scripté par un document qui l'ouvre.
Si example.com/passwords est servi avec noopener-allow-popups, le WindowProxy renvoyé par Window.open() indiquera que la fenêtre est fermée (Window.closed est true), de sorte que l'ouvreur ne peut pas exécuter de scripts dans l'application de gestion des mots de passe :
const handle = window.open("example.com/passwords", "passwordTab");
if (windowProxy.closed) {
// La nouvelle fenêtre est fermée, elle ne peut donc pas être scriptée.
}
Notez que cela seul n'est pas considéré comme une mesure de sécurité suffisante. Le site devrait également faire ce qui suit :
- Utiliser Fetch Metadata pour bloquer les requêtes same-origin vers l'application la plus sensible qui ne sont pas des requêtes de navigation.
- S'assurer que leurs cookies d'authentification sont tous
HttpOnly. - S'assurer que des Service Workers au niveau racine ne sont pas installés par l'application moins sensible.
- S'assurer que
postMessageouBroadcastChannelsur l'application la plus sensible n'exposent aucune information sensible à toute autre application de la même origine. - Servir leur page de connexion sur une origine distincte, car le remplissage automatique des gestionnaires de mots de passe est appliqué en fonction de l'origine.
- Comprendre que le navigateur peut toujours allouer l'application la plus sensible dans le même processus que la moins sensible, la rendant vulnérable à des attaques de type Spectre.
Spécifications
| Specification |
|---|
| HTML> # the-coop-headers> |
Compatibilité des navigateurs
Voir aussi
- L'en-tête
Cross-Origin-Embedder-Policy