COOP (Cross-Origin-Opener-Policy) is a security header that isolates a specific document from sharing the same browse context group with other documents such as cross-origin popups. This allows you to control interactions between cross-origin documents and defend against certain attacks like XS-Leaks.
The Problem
By default, web browsers allow new windows or tabs (openees) launched through methods like window.open()
to access the window that opened them (opener). Even if the opener and openee have different origins, limited interaction is possible through the window.opener
object.
These interactions enable functionality like checking if a window is closed with window.opener.closed
or giving it focus with window.opener.focus()
. However, from a security perspective, this creates several threats. For example, a malicious page could open a legitimate page as a popup and then use window.opener
to infer certain information or interfere with user interactions (e.g., Tabnabbing).
What is COOP?
COOP is an HTTP response header introduced to address these issues. It isolates a document's top-level browse context, breaking direct window
object references with cross-origin documents.
If a document is loaded with the COOP: same-origin
header, any cross-origin document it opens will have a null
value for window.opener
. Consequently, the openee cannot obtain information about or control the opener.
graph TD subgraph Default Behavior A[Opener Page: a.com] -- window.open() --> B[Popup: b.com]; B -- "window.opener is NOT null" --> A; end subgraph With COOP: same-origin C[Opener Page: a.com with COOP] -- window.open() --> D[Popup: b.com]; D -- "window.opener is null" --> C; end
COOP Directives
The COOP header has three main directives:
unsafe-none
- This is the default value.
- It allows the document to be added to the opener's browse context group (unless the opener has
same-origin
orsame-origin-allow-popups
).
same-origin-allow-popups
- The document maintains its top-level browse context.
- However, it permits interaction with popups it opens that have either not set COOP or have opted out of isolation by setting
unsafe-none
.
same-origin
- This is the strongest level of isolation.
- The document maintains its top-level browse context and can only belong to the same browse context group as documents with the same origin.
- Cross-origin documents opened from this document will always have
window.opener
set tonull
.
Implementation
COOP can be applied by adding it to the HTTP response headers, similar to other security headers:
HTTP/1.1 200 OK
Content-Type: text/html
Cross-Origin-Opener-Policy: same-origin
COOP and COEP
COOP is often used in conjunction with COEP (Cross-Origin-Embedder-Policy). When these two headers are enabled together, the document achieves a Cross-Origin Isolated
state, which is a prerequisite for using powerful APIs like SharedArrayBuffer
and performance.measureUserAgentSpecificMemory()
. This is an essential measure to defend against side-channel attacks like Spectre.
Conclusion
COOP is a simple yet effective way to enhance web application security by blocking unwanted interactions between cross-origin documents. Applying the same-origin
policy, in particular, can significantly reduce the attack surface for vulnerabilities like XS-Leaks. By using it together with COEP to create a Cross-Origin Isolated
environment, you can build a more secure web environment and leverage all the features browsers have to offer.