Add `SecurityHeadersMiddleware`, an ASGI middleware that automatically
adds standard HTTP security headers to every response, improving the
security posture of FastAPI applications with zero effort from
developers.
**Why this is needed:** Currently, every FastAPI developer must write
custom middleware or rely on reverse proxies to add security headers
like `Strict-Transport-Security`, `X-Content-Type-Options`, and
`X-Frame-Options`. These headers are critical for protecting against
clickjacking, MIME type sniffing, and other common web attacks. This
feature is aligned with the roadmap item "Additional security and
authentication tools to simplify common tasks" (#10370).
Enables 5 security headers by default that can be disabled by passing
`None` or `False`. Supports opt-in headers for stricter policies.
**Implementation details:**
* Uses raw ASGI middleware (not `BaseHTTPMiddleware`) — zero overhead,
following the `AsyncExitStackMiddleware` pattern.
* Pre-computes all header values as bytes at initialization — no string
operations in the hot path.
* Respects existing headers — never overwrites headers the endpoint
already set.
* Passes non-HTTP scopes (WebSocket) through untouched.
**Usage:**
```python
from fastapi import FastAPI
from fastapi.middleware.security_headers import SecurityHeadersMiddleware
app = FastAPI()
# With defaults (recommended for most apps):
app.add_middleware(SecurityHeadersMiddleware)
# Custom configuration:
app.add_middleware(
SecurityHeadersMiddleware,
hsts="max-age=63072000; includeSubDomains; preload",
content_security_policy="default-src 'self'",
cache_control="no-store, no-cache, must-revalidate",
)
```
**Default headers:**
| Header | Default SecurityHeadersMiddleware value |
|---|---|
| Strict-Transport-Security | max-age=31536000; includeSubDomains |
| X-Content-Type-Options | nosniff |
| X-Frame-Options | DENY |
| Referrer-Policy | strict-origin-when-cross-origin |
| Cross-Origin-Opener-Policy | same-origin |
**Opt-in headers:** Content-Security-Policy, Permissions-Policy,
Cross-Origin-Embedder-Policy, Cross-Origin-Resource-Policy, Cache-Control
Checklist:
* [x] I added tests for the change (15 tests covering defaults, customization, opt-in headers, header override respect, full disable, WebSocket passthrough).
* [x] All new tests pass (15/15).
* [x] Lint checks pass (ruff).
* [x] No new dependencies required.
Co-authored-by: CommandCodeBot <[email protected]>