Stack guide
Next.js HSTS configuration — Strict-Transport-Security in App Router
HSTS is one header, but Next.js gives you four reasonable places to add it: `next.config.js#headers()`, `vercel.json`, `middleware.ts`, or the upstream CDN. This guide picks the right one for each deployment shape, shows the exact value to use, and explains why preloading is rarely the right first move.
Set HSTS in next.config.js
For a Next.js project hosted on Vercel or as a Node server, the canonical HSTS surface is `next.config.js#headers()`. The framework merges your headers with platform defaults at build time, which means previews and production behave identically. Use a 6-month `max-age` first; bump to 1 year + `includeSubDomains` only after a full release cycle proves nothing on a subdomain still requires HTTP.
HSTS missing — nginx (server / location) (nginx)
add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always; # If TLS terminates at a CDN, set the header there instead.
HSTS missing — Express (helmet) (typescript)
import helmet from "helmet";
app.use(helmet.hsts({ maxAge: 31_536_000, includeSubDomains: true }));HSTS missing — Apache (vhost) (apache)
Header always set Strict-Transport-Security "max-age=31536000; includeSubDomains"
Related Scorifya checks: missing_hsts, weak_hsts
Why not preload yet?
Preloading adds your domain to a static list shipped with browsers. Removing yourself takes weeks. It's a great signal of confidence, but it's also a footgun on shared parent domains where another team might still need HTTP. Wait until 1) the year-long max-age has been live for at least a month, 2) every subdomain is HTTPS-ready, then submit at hstspreload.org. Until then, plain HSTS is enough.
Related Scorifya checks: hsts_preload_hint, hsts_preload_max_age
Background
What is HSTS? HTTP Strict Transport Security explained →
How HSTS works, why the bootstrap window matters, what max-age and includeSubDomains do, and when (or whether) to submit your domain to the browser preload list.
Read more
Verify with a fresh scan
After deploy, run the scanner on the affected hostname. Headers and TLS settings update on the very next request, so you should see the score move within seconds.