Without Cross-Origin-Opener-Policy, a cross-origin page that your app opens (or that opens your app) can hold a reference to your window object. Spectre-class speculative-execution attacks use cross-origin window references and shared memory to read data across origin boundaries. CWE-1021 (Improper Restriction of Rendered UI Layers / Frame Hijacking) applies. OWASP A05 (Security Misconfiguration) flags missing isolation headers as a configuration gap. The absence of COOP also prevents the browser from enabling SharedArrayBuffer and high-resolution timers, which are required for performant web workers in security-sensitive contexts.
Medium because Spectre-class attacks require local code execution and specific browser conditions, but the window reference exposure is a prerequisite that is cheap to eliminate with a single header.
Set Cross-Origin-Opener-Policy in your Next.js headers config. Use same-origin-allow-popups if your app opens OAuth flows or payment windows; use same-origin for maximum isolation.
// next.config.js
module.exports = {
async headers() {
return [{
source: '/(.*)',
headers: [{
key: 'Cross-Origin-Opener-Policy',
value: 'same-origin-allow-popups'
}]
}]
}
}
Verify OAuth popups still function after deploying — same-origin will break popup-based OAuth flows that communicate via window.opener. Switch to same-origin-allow-popups if you hit that issue.
ID: security-headers-ii.cross-origin-isolation.coop-set
Severity: medium
What to look for: Check framework config, middleware, and deployment config for a Cross-Origin-Opener-Policy (COOP) header. Acceptable values: same-origin (strictest — isolates the window completely) or same-origin-allow-popups (allows OAuth popups, payment windows). COOP isolates the browsing context from cross-origin references, preventing Spectre-class side-channel data leaks.
Pass criteria: COOP header is set to same-origin or same-origin-allow-popups — at least 1 location must configure it. Quote the actual header value and count all locations where COOP is configured (framework config, middleware, deployment config).
Fail criteria: No COOP header configured, or COOP is set to unsafe-none (the default, provides no protection).
Do NOT pass when: COOP is set to unsafe-none — this is the browser default and provides no protection.
Skip (N/A) when: Project is an API-only service with no browser-facing pages.
Detail on fail: "No Cross-Origin-Opener-Policy header configured — window is not isolated from cross-origin references" or "COOP set to unsafe-none — provides no Spectre-class protection"
Remediation: COOP prevents cross-origin windows from accessing your window object, mitigating Spectre-class attacks:
// next.config.js
headers: [{
key: 'Cross-Origin-Opener-Policy',
value: 'same-origin-allow-popups'
}]
Use same-origin-allow-popups if your app opens OAuth popups or payment windows. Use same-origin for maximum isolation if you don't need cross-origin popups.