Checklist · September 6, 2026
HTTP security headers checklist
Security headers are instructions your server sends with every response, telling the browser what your page is and isn't allowed to do. They take minutes to add, they don't change how your app looks, and they shut down entire categories of attack. Most AI-generated apps ship with none of them.
The seven that matter
Content-Security-Policy
Controls which scripts, styles, images and frames may load. The single strongest defence against cross-site scripting.
Content-Security-Policy: default-src 'self'; img-src 'self' data: https:; style-src 'self' 'unsafe-inline'; script-src 'self'; frame-ancestors 'none'; base-uri 'self'; form-action 'self'Strict-Transport-Security
Forces HTTPS for a year, so a downgrade or coffee-shop Wi-Fi attack can't strip your encryption.
Strict-Transport-Security: max-age=31536000; includeSubDomains; preloadX-Content-Type-Options
Stops browsers from guessing a file's type — the trick behind uploads that execute as scripts.
X-Content-Type-Options: nosniffReferrer-Policy
Keeps full URLs (which often contain tokens or IDs) out of the Referer header sent to third parties.
Referrer-Policy: strict-origin-when-cross-originPermissions-Policy
Denies powerful browser features to your page and to any embedded third-party code.
Permissions-Policy: camera=(), microphone=(), geolocation=(), interest-cohort=()Cross-Origin-Opener-Policy
Isolates your browsing context so a window you open (or that opens you) can't poke at your page.
Cross-Origin-Opener-Policy: same-originX-Frame-Options
Legacy clickjacking protection. frame-ancestors in your CSP supersedes it, but it costs nothing to keep for old browsers.
X-Frame-Options: DENYRolling out a CSP without breaking your site
Content-Security-Policy is the one header that can visibly break things, because it blocks anything you forgot to allow. Do it in three passes:
- Ship it as
Content-Security-Policy-Report-Onlyfirst. Nothing is blocked; violations appear in the browser console. - Click through your whole app — sign-in, checkout, embeds, analytics — and add each legitimately blocked origin to the matching directive.
- When the console is quiet, rename the header to
Content-Security-Policyto start enforcing.
Two traps: 'unsafe-inline' in script-src removes most of the protection, so use a nonce or hash instead; and a policy that allows a wildcard CDN for scripts is only as safe as everything hosted on that CDN.
Don't forget cookies
Headers protect the page; cookie flags protect the session. Every session cookie should carry Secure, HttpOnly and SameSite=Lax (or Strict). If your cookie is same-origin only, the __Host- name prefix locks it to your exact host and path and is worth adopting.
Where to set them
- Static hosts (Netlify, Vercel, Cloudflare Pages) — a headers config file or edge middleware.
- Node/edge servers — set them once in a response middleware so no route can forget.
- Nginx / Apache —
add_header/Header always setin the server block.
Set them in one place, not per route. Headers applied inconsistently are the most common finding we see after headers applied not at all.
Check which headers you're missing
Paste your URL and VibeCoden't reports every missing or weak header, plus cookie flags and TLS configuration, with a copy-paste fix for each.
Run a free scan