Security Headers Generator
Features
About this tool
Generate HTTP security headers for Apache, Nginx, and Next.js
Every browser request to your site arrives without any security guarantees unless your server explicitly adds them as HTTP response headers. This Security Headers Generator builds a complete, copy-ready header set — Strict-Transport-Security, Content-Security-Policy, X-Content-Type-Options, X-Frame-Options, Referrer-Policy, and Permissions-Policy — and formats it for Apache .htaccess, Nginx server blocks, or a Next.js headers() function, so you don't have to hand-translate the same six header names into three different config syntaxes.
How the header set is assembled. X-Content-Type-Options: nosniff is always included since it has no compatibility downside — it simply stops browsers from guessing a file's MIME type from its content, which closes off a class of MIME-sniffing attacks. The other headers are configurable: X-Frame-Options toggles between DENY and SAMEORIGIN, Referrer-Policy and Permissions-Policy take free-text values you edit directly, and HSTS can be switched off entirely for local development or staging environments that don't yet have HTTPS everywhere.
Content-Security-Policy and the diagnostics row. CSP is the most powerful and most failure-prone header here, so the tool surfaces three live diagnostics pulled straight from the policy you're editing: whether 'unsafe-inline' is present (weakens protection against inline-script XSS), whether object-src 'none' is set (blocks legacy Flash/plugin-based attacks), and whether frame-ancestors is defined (the modern, origin-list-aware replacement for X-Frame-Options). Toggling CSP report-only switches the header name to Content-Security-Policy-Report-Only, which logs violations to the browser console instead of blocking resources — the safe way to discover what a new policy would break before it actually breaks it.
Balanced vs. Strict presets. The Balanced preset allows self-hosted scripts/styles plus 'unsafe-inline' for styles and data:/https: images — a realistic starting point for sites with existing inline styling or third-party widgets. The Strict preset removes 'unsafe-inline', adds object-src 'none', base-uri 'self', frame-ancestors 'none', and form-action 'self', and locks Permissions-Policy down to nearly every sensor and capability. Applying a preset overwrites both the CSP and Permissions-Policy fields in one click, which you can then hand-edit to re-allow specific domains your site actually depends on.
HSTS and why preload is a one-way door. When enabled, HSTS is generated as max-age=31536000; includeSubDomains; preload — a full year, applied to every subdomain, with the preload flag requesting inclusion in browsers' built-in HTTPS-only list. preload is the strongest setting because it protects even the very first request a user ever makes to your domain, before any header could be read, but reversing it is slow: once a domain is baked into browser preload lists, removal can take months to roll out across releases. Confirm every subdomain serves valid HTTPS before turning it on.
Output format differences. Apache uses Header always set Name "value" lines for .htaccess or a VirtualHost block. Nginx uses add_header Name "value" always; — the always flag matters because, without it, Nginx skips the header on error responses like 404s and 500s. Next.js gets an async headers() function returning a source: '/(.*)' rule with a headers array, matching the exact shape next.config.js expects, ready to merge into an existing config or drop in as-is.
How to Use
- 1Choose your deployment targetSelect Apache, Nginx, or Next.js so the output matches your hosting configuration.
- 2Pick a baseline presetStart with Balanced for most sites or Strict for apps that can handle tighter CSP rules.
- 3Customize CSP and permissionsAdd domains for real scripts, styles, images, fonts, APIs, and embeds used by your site.
- 4Use report-only firstDeploy CSP in report-only mode before enforcing it on production traffic.
- 5Copy and testApply the snippet on staging, then verify headers with browser devtools or an external header scanner.
Common Use Cases
Frequently Asked Questions
A solid baseline is Strict-Transport-Security (forces HTTPS), Content-Security-Policy (restricts where scripts/styles/images can load from), X-Content-Type-Options: nosniff (stops MIME-type sniffing), X-Frame-Options or frame-ancestors (blocks clickjacking), Referrer-Policy (limits referrer leakage), and Permissions-Policy (disables unused browser features like camera or geolocation). The Balanced preset in this tool sets all six with safe defaults; Strict tightens CSP and Permissions-Policy further.
CSP blocks inline <script> and <style> blocks by default unless your script-src or style-src explicitly allows 'unsafe-inline'. The tool flags this in the diagnostics row — if "unsafe-inline" shows yes, any inline handlers or inline CSS will still execute, which weakens XSS protection. The safer fix is to move inline code into external files or use a nonce/hash, but if that is not feasible yet, keep 'unsafe-inline' temporarily and tighten it later.
Enable the CSP report-only toggle — this switches the header to Content-Security-Policy-Report-Only, which logs violations to the browser console without blocking any resource. Deploy it to production, open devtools on key pages, and check the Console and Network tabs for blocked-resource warnings. Once you have allow-listed every legitimate script, style, font, and embed your site actually uses, turn report-only off to enforce the policy for real.
Strict-Transport-Security with preload tells browsers to hardcode your domain into a built-in HTTPS-only list shipped with the browser itself, so even the very first request never touches HTTP. This is stronger than a normal HSTS header, but it is hard to reverse — once submitted to the preload list, removal can take months to propagate across browsers. Only enable preload after confirming every subdomain reliably serves valid HTTPS.
Select the Next.js output format — the tool generates an async headers() function for next.config.js that returns a source/headers array matching every path. Paste it into your existing config (merge the headers array if you already export one) and redeploy; Next.js applies these headers at the edge or server layer on every matching route automatically.
Nginx uses add_header directives inside a server or location block, and needs the always flag so headers are also sent on error responses (4xx/5xx) — this tool includes always automatically. Apache uses Header always set directives inside .htaccess or a VirtualHost block. The header names and values are identical; only the server-specific syntax wrapping them differs, which is exactly what switching the output format changes.
Yes, but plain static HTML files cannot set HTTP headers by themselves — headers must be sent by whatever serves the files: your web server, a reverse proxy, or a static host's edge config. If you self-host with Apache or Nginx, paste the generated snippet into .htaccess or your server block. On platforms like Vercel, Netlify, or Cloudflare Pages, use their headers configuration file/dashboard with the same header names and values.
Both prevent clickjacking by controlling which sites can embed your page in an <iframe>, but frame-ancestors is the modern CSP directive and supports a list of allowed origins, while X-Frame-Options only supports DENY or SAMEORIGIN. Browsers that understand CSP prefer frame-ancestors when both are present. The Strict preset sets frame-ancestors 'none' in the CSP; keep X-Frame-Options alongside it for older browsers that ignore CSP.