Clickjacking: when your site is hidden inside someone else's
An attacker can load your page invisibly inside theirs and trick people into clicking things they cannot see. One header stops it.
The short version
X-Frame-Options (or the frame-ancestors rule in a Content Security Policy), tells browsers never to let your pages be embedded like that. It takes two minutes to add.How the trick works
Web pages can embed other web pages inside themselves using an <iframe> — that is how a YouTube video or a Google Map appears on a site. Normally harmless. But the page doing the embedding controls how the embedded page is displayed, including making it completely transparent.
So the attacker builds a page that says "Click here to claim your prize", puts your site inside an invisible frame on top of it, and scrolls and positions that frame so your "Confirm" button sits exactly under the fake prize button. The visitor — who is already logged in to your site in the same browser — clicks. The browser dutifully sends the click to your page, with their login cookie attached, and the action happens. They never see your site at all.
Variations include "likejacking" (tricking people into liking or following a social account), tricking people into enabling webcam or microphone permissions, and silently changing account settings on sites with one-click actions.
Who is actually at risk
The attack needs two things: your site has to be embeddable, and it has to have something worth clicking while logged in. So the risk is highest for sites with customer accounts, admin panels, checkouts, booking systems and anything with a "confirm" or "delete" button. A plain brochure site has little for an attacker to hijack — but the fix costs nothing and is standard practice, so there is no reason to leave it open.
It is worth remembering that WordPress admin, cPanel, webmail and most e-commerce platforms are all pages that can be clickjacked if the header is missing.
The fix
Send one of these headers with every page. The modern way is the frame-ancestors directive in your Content Security Policy:
Content-Security-Policy: frame-ancestors 'none'
The older header, which every browser still understands and is fine to send alongside, is:
X-Frame-Options: DENY
DENY means nobody may embed your pages. If you *need* to embed your own pages in other pages on your own site (some page builders do), use SAMEORIGIN instead, or frame-ancestors 'self'. If a specific partner site legitimately embeds you — say a booking widget on a venue's site — list them: frame-ancestors 'self' https://partner.example.
On Apache or LiteSpeed hosting, add to .htaccess:
Header always set X-Frame-Options "SAMEORIGIN" Header always set Content-Security-Policy "frame-ancestors 'self'"
On Cloudflare, use Rules → Transform Rules → Modify Response Header. On WordPress, most security plugins (Wordfence, Solid Security) have a headers section, or use a dedicated "HTTP Headers" plugin.
What VigilScan checks
We request your homepage and look for either X-Frame-Options or a Content-Security-Policy containing frame-ancestors. If neither is present, we flag it. If X-Frame-Options is set to the obsolete ALLOW-FROM value (browsers ignore it), we tell you to switch to frame-ancestors. The report shows the exact header value we received so you can compare it with what you intended.
Common questions
Will this stop my own YouTube or Google Maps embeds from working?
I have X-Frame-Options already. Do I also need frame-ancestors?
My site has no logins at all. Does this matter?
Not sure if this affects your site?
Run a free check — it takes about 90 seconds and tells you exactly where you stand.