How to Add Missing HTTP Security Headers to Your Website
Security headers are HTTP response headers that instruct browsers how to behave when handling your site's content — preventing clickjacking, MIME sniffing, cross-origin attacks, and information leakage. Most are a single line of config. Here's what each one does and how to add it.
The headers, what they do, and the values to use
X-Content-Type-Options
Purpose: Prevents browsers from MIME-sniffing a response away from the declared content type. Stops certain attacks where a file is uploaded as one type but executed as another.
X-Content-Type-Options: nosniff
This is the only valid value. Always use nosniff.
Referrer-Policy
Purpose: Controls how much referrer information is included when a user navigates from your site to another. Without it, the full URL (including paths and query strings with sensitive data) can be leaked.
Referrer-Policy: strict-origin-when-cross-origin
This sends the full URL as referrer for same-origin requests, and only the origin (no path) for cross-origin requests.
Permissions-Policy
Purpose: Controls which browser features and APIs your page is allowed to use (camera, microphone, geolocation, etc.). Prevents malicious injected scripts from accessing features you don't use.
Permissions-Policy: camera=(), microphone=(), geolocation=(), payment=()
List only the features your site actually uses. Empty () denies access entirely.
X-Frame-Options
Purpose: Prevents your page from being embedded in an iframe on another site (clickjacking defence).
X-Frame-Options: DENY
Or if you need to allow embedding on your own domain:
X-Frame-Options: SAMEORIGIN
Note: If you have a Content-Security-Policy header with a frame-ancestors directive, that takes precedence over X-Frame-Options in modern browsers.
Cross-Origin-Opener-Policy (COOP)
Purpose: Prevents other sites from accessing your window object if they open your page, protecting against cross-origin attacks.
Cross-Origin-Opener-Policy: same-origin
How to add headers — by platform
Cloudflare (Transform Rules)
Security → Transform Rules → Modify Response Header → Add new rule → Add each header as a Set action.
Nginx
add_header X-Content-Type-Options "nosniff" always; add_header Referrer-Policy "strict-origin-when-cross-origin" always; add_header Permissions-Policy "camera=(), microphone=(), geolocation=()" always; add_header X-Frame-Options "DENY" always; add_header Cross-Origin-Opener-Policy "same-origin" always;
Apache
Header always set X-Content-Type-Options "nosniff" Header always set Referrer-Policy "strict-origin-when-cross-origin" Header always set Permissions-Policy "camera=(), microphone=(), geolocation=()" Header always set X-Frame-Options "DENY" Header always set Cross-Origin-Opener-Policy "same-origin"
Vercel (vercel.json)
{
"headers": [
{
"source": "/(.*)",
"headers": [
{ "key": "X-Content-Type-Options", "value": "nosniff" },
{ "key": "Referrer-Policy", "value": "strict-origin-when-cross-origin" },
{ "key": "Permissions-Policy", "value": "camera=(), microphone=(), geolocation=()" },
{ "key": "X-Frame-Options", "value": "DENY" },
{ "key": "Cross-Origin-Opener-Policy", "value": "same-origin" }
]
}
]
}Netlify (netlify.toml)
[[headers]]
for = "/*"
[headers.values]
X-Content-Type-Options = "nosniff"
Referrer-Policy = "strict-origin-when-cross-origin"
Permissions-Policy = "camera=(), microphone=(), geolocation=()"
X-Frame-Options = "DENY"
Cross-Origin-Opener-Policy = "same-origin"Verify it worked
Scan your domain at mydomainrisk.com — the Security Headers card will show pass/fail status for each individual header, and your score will update to reflect the fixes.
Check your security headers
MyDomainRisk scores each header individually and explains exactly what's missing — free.
Scan your domain free →