Medium severity · Next.js

Missing X-Frame-Options on Next.js

Your site is missing X-Frame-Options (or CSP frame-ancestors), which means any other site can embed yours in an iframe. Attackers use this for clickjacking — overlaying an invisible copy of your site on a decoy page so users unknowingly click buttons on your app. Fix it with one of two headers: `X-Frame-Options: DENY` (blocks all iframe embedding) or the modern equivalent `Content-Security-Policy: frame-ancestors 'none'`. If you need to allow embedding on specific domains, use `frame-ancestors` with a list.

The fix for Next.js

Next.js

Add both headers for belt-and-suspenders protection.

headers: [
  { key: 'X-Frame-Options', value: 'DENY' },
  { key: 'Content-Security-Policy', value: "frame-ancestors 'none'" }
]

Why it matters

Clickjacking is especially dangerous for apps with one-click destructive actions — subscribe, pay, share, delete. An attacker can make users perform these without realizing. Browsers no longer display a warning when a site is framed.

Confirm the fix worked

Scan your Next.js site to confirm this finding is gone.

AI prompt

Apply across your codebase

Paste this into Cursor, Lovable, Bolt, v0, or Claude Code.

Add X-Frame-Options: DENY to my app, plus a Content-Security-Policy header with frame-ancestors 'none'. If I already have a CSP header, merge the frame-ancestors directive into it. Apply to all routes.

FAQ

Frequently asked questions

What if I want to embed my own app in a subdomain?
Use `frame-ancestors 'self'` or list specific domains: `frame-ancestors 'self' https://app.example.com`. `DENY` blocks all embedding, including from your own site.
Is X-Frame-Options deprecated?
Modern browsers prefer CSP `frame-ancestors`, but X-Frame-Options still works and some older browsers only respect that one. Ship both; they do not conflict.
Do SameSite cookies replace this?
No. SameSite protects against CSRF by blocking third-party cookie use. Clickjacking does not need cookies — the attacker tricks the user into clicking while logged in normally. You need both.