CORS policy generator · headers + 14 server & framework configs
Build a correct, secure Cross-Origin Resource Sharing policy from a few choices, then copy ready-to-paste config for Nginx, Apache, Express, Node, FastAPI, Flask, Django, ASP.NET Core, Spring Boot, Caddy, Traefik, HAProxy, IIS and Cloudflare Workers, plus the raw response headers. Start from a preset, and watch the live security review flag dangerous combinations (the classic wildcard-with-credentials hole) before they reach production. Everything runs in your browser; nothing is sent anywhere.
https://app.example.com
X-Request-Id, X-RateLimit-Remaining
How this CORS generator works
Cross-Origin Resource Sharing is a set of HTTP response headers that tell a browser which other origins are allowed to read responses from your server. The browser enforces it; your server only declares the policy. Pick a preset or set your origins, methods and headers, decide whether requests carry credentials, and the tool writes the exact headers plus the configuration for thirteen common stacks. The preview updates as you type, and the security review explains any risky combination in plain language.
The CORS response headers explained
| Header | What it does |
|---|---|
Access-Control-Allow-Origin | The single origin allowed to read the response, or * for any. With credentials it must be an exact origin, never *. |
Access-Control-Allow-Methods | HTTP methods permitted in the actual request, returned on the preflight. |
Access-Control-Allow-Headers | Request headers the client may send (for example Authorization, Content-Type). |
Access-Control-Allow-Credentials | Set to true to allow cookies and the Authorization header. Forces an exact origin. |
Access-Control-Expose-Headers | Response headers JavaScript is allowed to read beyond the default safelist. |
Access-Control-Max-Age | How long (seconds) the browser caches the preflight result. Browsers cap it (Chromium 7200, Firefox 86400). |
Vary: Origin | Required when you reflect the origin, so caches do not serve one origin’s response to another. |
The wildcard-with-credentials trap
The most common CORS security mistake is allowing credentials while reflecting any origin. The specification forbids Access-Control-Allow-Origin: * together with Access-Control-Allow-Credentials: true, so developers work around it by echoing back whatever Origin the browser sent. That effectively lets any website make authenticated requests with the victim’s cookies and read the response, which is the same as having no cross-origin protection at all. If you need credentials, always match the incoming origin against a strict allowlist, which is exactly what this tool generates when you list specific origins.
Preflight requests
For anything beyond a simple request (a custom header, a JSON content type, or a method other than GET, POST or HEAD) the browser first sends an OPTIONS preflight. Your server must answer it with the CORS headers and a 2xx status before the real request is sent. The Nginx, Node, Caddy and HAProxy outputs include the short-circuit that returns 204 for OPTIONS so preflights succeed.
Frequently asked questions
Why is my CORS policy not working even though I set the header?
The three usual causes are: the preflight OPTIONS request is not answered with a 2xx and the headers; you are using Access-Control-Allow-Origin: * together with credentials (forbidden, so the browser blocks it); or a proxy or CDN strips the headers. Use the raw-headers tab to confirm what should be sent, then check the response in your browser network panel.
Can I use a wildcard origin with cookies or Authorization?
No. When Access-Control-Allow-Credentials is true, the browser rejects Access-Control-Allow-Origin: * and also rejects * for Allow-Headers and Expose-Headers. You must return the exact requesting origin, validated against an allowlist, and add Vary: Origin. This generator does that automatically when you choose specific origins and enable credentials.
What is a preflight request and when does it happen?
A preflight is an automatic OPTIONS request the browser sends before a non-simple cross-origin request, to ask permission. It is triggered by methods other than GET, POST or HEAD, by a Content-Type such as application/json, or by custom request headers. Your server must reply with the Allow-Methods and Allow-Headers and a 2xx status.
Does CORS protect my server?
No. CORS is enforced by the browser to protect users, not your server. It controls whether browser JavaScript on another origin can read your responses. It is not authentication or a firewall: anyone can still call your API directly with curl or Postman. Keep your real authorization and rate limiting on the server.
How long should Access-Control-Max-Age be?
Long enough to avoid a preflight on every request, but remember browsers cap it: Chromium honours up to 7200 seconds (2 hours) and Firefox up to 86400 (24 hours). A value of 86400 is a sensible default; the browser simply clamps it to its own maximum.
Which framework or server should I configure CORS in?
Set it in one place, as close to the application as is practical. If you terminate TLS and route at a proxy (Nginx, Caddy, Traefik, HAProxy), configuring CORS there keeps it consistent across services. If a single app owns the API, the framework middleware (Express, FastAPI, Flask, Django, ASP.NET Core, Spring) is clearer. Avoid setting it in two layers at once, which produces duplicated headers that browsers reject.













