Security headers protect your application from common web attacks. Set them on every response.
Content-Security-Policy (CSP)
Controls which resources the browser is allowed to load.
Content-Security-Policy: default-src 'self'; script-src 'self' 'unsafe-inline'; style-src 'self' 'unsafe-inline'; img-src 'self' data: https:; font-src 'self'; connect-src 'self' https://api.example.com
Directive
Controls
default-src
Fallback for all resource types
script-src
JavaScript sources
style-src
CSS sources
img-src
Image sources
connect-src
Fetch, XHR, WebSocket targets
frame-ancestors
Who can embed this page (replaces X-Frame-Options)
Start strict, loosen as needed. Use report-uri to catch violations without blocking.
Strict-Transport-Security (HSTS)
Forces HTTPS for all future requests.
Strict-Transport-Security: max-age=63072000; includeSubDomains; preload
max-age=63072000 — Enforce for 2 years
includeSubDomains — Apply to all subdomains
preload — Submit to browser preload list
X-Frame-Options
Prevents clickjacking by controlling iframe embedding.
X-Frame-Options: DENY
Value
Meaning
DENY
Cannot be embedded anywhere
SAMEORIGIN
Only same-origin embedding
Note: frame-ancestors in CSP is the modern replacement.
X-Content-Type-Options
Prevents MIME type sniffing.
X-Content-Type-Options: nosniff
Without this, browsers may interpret a file as a different type than declared, enabling XSS attacks.
Referrer-Policy
Controls how much referrer information is sent.
Referrer-Policy: strict-origin-when-cross-origin
Value
Behavior
no-referrer
Never send referrer
strict-origin-when-cross-origin
Full URL for same-origin, origin-only for cross-origin, none for downgrade
same-origin
Only send for same-origin requests
Permissions-Policy
Controls which browser features the page can use.
Permissions-Policy: camera=(), microphone=(), geolocation=(self), payment=()
Empty () disables the feature entirely.
X-DNS-Prefetch-Control
X-DNS-Prefetch-Control: off
Disables DNS prefetching to prevent information leakage.
Next.js Configuration
// next.config.ts
const securityHeaders = [
{ key: "X-DNS-Prefetch-Control" , value: "on" },
{ key: "Strict-Transport-Security" , value: "max-age=63072000; includeSubDomains; preload" },
{ key: "X-Frame-Options" , value: "SAMEORIGIN" },
{ key: "X-Content-Type-Options" , value: "nosniff" },
{ key: "Referrer-Policy" , value: "strict-origin-when-cross-origin" },
{ key: "Permissions-Policy" , value: "camera=(), microphone=(), geolocation=()" },
];
export default {
async headers () {
return [
{
source: "/(.*)" ,
headers: securityHeaders,
},
];
} ,
} ;
securityheaders.com — Scan and grade your headers
Mozilla Observatory — Comprehensive security audit
curl -I https://yoursite.com — Quick check from terminal
Minimum Recommended Set
At minimum, every production site should have:
Strict-Transport-Security
X-Content-Type-Options: nosniff
X-Frame-Options: DENY
Referrer-Policy: strict-origin-when-cross-origin