Cross-Origin Embedder Policy

Every resource on your page should have asked to be there

By default a page can pull in any cross-origin image, script, font or frame without that resource ever agreeing to it. Cross-Origin Embedder Policy inverts the default and requires each one to opt in. Report URI collects the reports so you can see which of your assets a policy would affect, if any, before you enforce anything.

What's at Stake

Your page can embed anything. Nothing had to agree to it.

The web's default is permissive: your document may load a cross-origin image, font, script or iframe without the server hosting it ever consenting, and without your page knowing what it received. That embedding relationship is also what keeps your origin out of its own process, because the browser cannot safely isolate a document that may be holding cross-origin data it was never authorised to read. Cross-Origin Embedder Policy flips the default to opt-in — and on a real site, a surprising number of assets have never opted in to anything.

Silent Embedding

Resources load without ever consenting

Images from a partner CDN, fonts from a type foundry, an embedded map or video player — none of them had to agree to being loaded by your origin. Without an embedder policy the browser fetches them regardless, and neither party can tell what the other received.

Unknown Inventory

You don't know which assets are affected

Enforcing require-corp blocks any cross-origin resource lacking a CORP or CORS header. Most teams have no list of which third-party assets carry one, so without reporting the first enforcement attempt is also the first time they find out — usually in production.

Blocked Isolation

Cross-origin isolation stays out of reach

An opener policy alone is not enough. Until you also set an embedder policy your origin never reaches the cross-origin isolated state, and SharedArrayBuffer, unthrottled timers and precise memory measurement stay switched off.

What COEP Reporting Does

A complete list of what a policy would block

Report URI collects Cross-Origin Embedder Policy reports straight from your visitors' browsers, turning an unknown into a definite list — however long or short that list turns out to be.

Blocked Resource Reporting

Every asset that would be blocked, named and counted

Each report carries the URL that was blocked, what kind of resource it was, and whether the browser enforced or merely reported. You get a working list of exactly which images, scripts, fonts and frames need a Cross-Origin-Resource-Policy header or CORS before enforcement can go on.

Learn more about the Reporting API →
Safe Rollout

Find the affected assets without affecting one

Send Cross-Origin-Embedder-Policy-Report-Only and the browser evaluates the policy, reports what it would have blocked, and loads everything as normal. Your fonts still render and your embedded players still play while you work through whatever the reports turn up.

Learn more about COEP setup →
Cross-Origin Isolation

The second half of unlocking the powerful APIs

Cross-origin isolation needs an embedder policy of require-corp or credentialless alongside an opener policy of same-origin. Report URI collects reports for both headers, so you can run the two rollouts together and see which one is still standing between you and isolation.

Learn more about COOP Reports →
Get Started

See what a policy would affect. Before you enforce it.

One header. No code. COEP reports start arriving from your first visitor.

30-day free trial  ·  One header  ·  No code  ·  Cancel anytime

Detection

Every report tells you what to fix, and how

A COEP report is not just a failure notice. It identifies the resource, what the page was trying to do with it, and which mechanism was missing — usually enough to tell you whether the fix is a header on your own CDN or an email to a vendor.

Report field What it tells you
blockedURL The exact resource that failed the policy, so you know who to chase
destination What the resource was being used as — image, script, font, iframe, style
type: corp A subresource was blocked because it carried no CORP or CORS opt-in
type: navigation A nested document or frame was blocked rather than a subresource
disposition: reporting Report-only mode — the resource still loaded, this is a dry run
disposition: enforce The policy is live and the resource was actually blocked

This is the difference between “the page looks wrong” and a named list of assets with an owner against each one.

Architecture

One response header. No code. No crawlers.

Cross-Origin Embedder Policy is a browser standard and its reporting is built in alongside it. The data comes from real sessions, which matters here more than most: the third-party assets least likely to be checked are the ones behind a login, in a checkout flow, or served only to certain regions — exactly what a crawler never sees.

Start in report-only and nothing changes for your visitors. Add the header, point it at your reporting endpoint, and the blocked-asset list begins building from your first visitor.

Minimal setup — report-only, nothing blocked
Cross-Origin-Embedder-Policy-Report-Only: require-corp;
  report-to="default"

COEP delivers its reports over the Reporting API, so you will also need a Report-To group pointing at your Report URI endpoint. Your subdomain and the exact header are on your Setup page once you have an account.

No code added to your pages

No crawler simulating page loads

Report-only mode blocks nothing while you evaluate

Your site's performance is unaffected

Catches assets that only load in real flows — authenticated pages, geo-targeted content, embedded checkouts

Cross-Origin Isolation

COEP, COOP, and the capabilities behind them

Browsers will only grant SharedArrayBuffer, unthrottled performance.now() and precise memory measurement to documents that are cross-origin isolated, and that state requires two headers working together. Cross-Origin Embedder Policy governs the resources you pull in; Cross-Origin Opener Policy governs the windows around you. Neither is sufficient alone.

If require-corp turns out to be too blunt for your third-party assets, credentialless is the softer route — cross-origin resources load without credentials instead of requiring an explicit opt-in. Report-only reporting is how you find out which of the two your site can actually live with.

Scope

One layer in the stack. Here's how it fits.

Cross-Origin Embedder Policy governs what your page is allowed to pull in from elsewhere. It does not tell you what your own scripts are doing, and it does not isolate you from the windows around you — it is the embedding layer, and it works alongside the rest.

COEP does Pairs with
Requires cross-origin resources to opt in COOP for window relationships — the other half of cross-origin isolation
Reports every asset a policy would block CSP for load control — deciding what is allowed to execute at all
Turns an unknown into a definite list Script Watch for dependency visibility — knowing when those third parties change
Unlocks isolation-gated browser APIs Policy Watch for header integrity — detecting when the policy itself changes

Together, these form the browser-native security layer that sits between your application and the code executing around it.