Clickjacking e X-Frame-Options: tieni le tue pagine fuori dagli iframe
Il clickjacking induce gli utenti a cliccare controlli nascosti sulla tua pagina caricandola dentro un iframe trasparente su un sito controllato dal malintenzionato. X-Frame-Options — o la moderna direttiva frame-ancestors della CSP — dice ai browser di rifiutarsi di incorporare la tua pagina, chiudendo del tutto l'attacco.
Che cos'è
Un attacco di clickjacking funziona incorniciando il tuo sito dentro un iframe invisibile o traslucido sulla pagina di un malintenzionato. La vittima vede un contenuto esca e clicca su quello che sembra un pulsante innocuo; l'iframe nascosto cattura il clic reale sulla tua pagina — un bonifico bancario, una modifica alle impostazioni, un'autorizzazione OAuth — senza che l'utente se ne accorga.
X-Frame-Options è un header di risposta HTTP con due valori utili: DENY (rifiuta l'incorniciamento da parte di chiunque) e SAMEORIGIN (consente l'incorniciamento solo da pagine sulla tua stessa origine). La direttiva frame-ancestors della CSP svolge lo stesso compito con un controllo più fine — puoi elencare origini attendibili specifiche e sostituisce X-Frame-Options nei browser che supportano la CSP.
Perché è importante
Qualsiasi pagina con un'azione significativa — impostazioni dell'account, conferma di pagamento, preferenze email o un interruttore di amministrazione — è un bersaglio del clickjacking. Un utente connesso che finisce su una pagina dannosa può essere indotto a compiere azioni reali mai volute, senza alcun segno visibile che qualcosa non va.
Aggiungere X-Frame-Options non costa nulla ed è supportato da ogni browser moderno. Ometterlo sulle pagine che compiono azioni sensibili è una vera e propria configurazione errata, non una funzionalità mancante.
Come risolverlo
Imposta l'header in next.config.js così che si applichi a ogni route. DENY è il valore predefinito sicuro per le app che non devono essere incorporate.
// next.config.js
module.exports = {
async headers() {
return [
{
source: "/:path*",
headers: [{ key: "X-Frame-Options", value: "DENY" }],
},
];
},
};La direttiva frame-ancestors della CSP sostituisce X-Frame-Options nei browser moderni e ti dà un controllo per origine. Aggiungila all'header Content-Security-Policy che imposti già.
// extend your existing CSP string
const csp = [
// ... your other directives ...
"frame-ancestors 'none'",
].join("; ");Se incorpori legittimamente delle pagine nel tuo stesso sito — un iframe di anteprima o un widget incorporato sulla stessa origine — usa X-Frame-Options: SAMEORIGIN invece di DENY, oppure frame-ancestors 'self'.
Se servi le risposte tramite un proxy nginx, aggiungi l'header nel tuo blocco server.
add_header X-Frame-Options "DENY" always;FAQ
X-Frame-Options o frame-ancestors della CSP — quale dovrei usare?
Usali entrambi. X-Frame-Options copre i browser più vecchi; frame-ancestors nella CSP ti dà una granularità per origine ed è lo standard moderno. Coesistono in sicurezza: i browser che supportano la CSP usano frame-ancestors e ignorano X-Frame-Options.
DENY impedisce di incorporare i miei widget o le mie dashboard di analytics?
Sì: DENY blocca ogni incorniciamento, inclusa la tua stessa origine. Se devi incorporare una pagina specifica in un iframe sul tuo dominio, usa SAMEORIGIN o frame-ancestors 'self'. Allentalo solo per le pagine che hanno davvero bisogno di essere incorporate.
Quale gravità segnala AppSafe per un X-Frame-Options mancante?
Media. Da solo non è un vettore immediato di furto di dati, ma qualsiasi pagina che compie azioni sull'account è un vero rischio di clickjacking senza di esso.
La tua app è interessata?
AppSafe controlla questo e decine di altri problemi in un'unica scansione gratuita.
Scansiona la mia app gratisGuide correlate
Content-Security-Policy (CSP): cos'è e come aggiungerla
L'header che impedisce l'esecuzione degli script iniettati.
I flag dei cookie Secure, HttpOnly e SameSite
Tre flag che impediscono il furto dei cookie di sessione.
Configurazione CORS errata: le trappole del wildcard e della riflessione
Consenti ogni origine e qualsiasi sito potrà leggere la tua API.