Should I use X-Frame-Options or CSP frame-ancestors?

x_frame_options_vs_csp_frame_ancestors global

The issue

X-Frame-Options can only say “nowhere” or “this site”. A page that must be framed by a partner has no reliable way to allow it, and teams fall back on ALLOW-FROM, which current browsers ignore. The Content Security Policy’s frame-ancestors directive replaces it.

The cause is the older header’s design. It predates CSP and was never extended, and when a page sends both, browsers that support frame-ancestors follow it and ignore X-Frame-Options.

Scope

Both are set per response. Probeo checks framing through the Content Security Policy and doesn’t grade X-Frame-Options.

How to check you have it

  • In probeo: a policy with no frame-ancestors directive is recorded as csp:missing-frame-ancestors, and a page with no policy at all as csp-missing.
  • By hand: run curl -sI https://example.com/ and read content-security-policy for frame-ancestors, and x-frame-options if present.

The fix

Control framing with the Content Security Policy’s frame-ancestors directive.

Use frame-ancestors 'none' for a page that is never framed, 'self' for one framed only by the site, and a list of origins for partners. Keep X-Frame-Options only as a fallback for old browsers, set to the matching DENY or SAMEORIGIN.

Done when: every HTML page has frame-ancestors matching its intended embedding, and the check above comes back clean.

Do not

  • Do not rely on X-Frame-Options: ALLOW-FROM.
  • Do not set the two to conflicting values.
  • Do not expect X-Frame-Options to allow several origins.

FAQ

What is the difference between X-Frame-Options and frame-ancestors?

X-Frame-Options supports only three values and cannot specify multiple origins. frame-ancestors supports explicit origin lists, wildcard patterns, and more granular control.

Do browsers support both mechanisms?

Yes, but modern browsers that support CSP Level 2 or higher prioritize frame-ancestors. If frame-ancestors is present, X-Frame-Options is ignored.

Should both headers be set?

Only if legacy browser support is required. Set X-Frame-Options as a fallback for older browsers that do not support frame-ancestors.

Can X-Frame-Options allow embedding by multiple origins?

No. The ALLOW-FROM directive only supports a single origin and is deprecated. Most browsers do not honor it.

What does frame-ancestors ‘none’ do?

It prevents the page from being embedded in any iframe, frame, or object. This is equivalent to X-Frame-Options: DENY.

Should X-Frame-Options be removed once frame-ancestors is deployed?

Yes, unless legacy browser support is explicitly required. Removing it eliminates redundancy and potential conflict.

Which product detects this

Probeo checks this on every page of your site as part of Site Clarity. This page explains one instance; the product tells you every page that has it.