CORS properly configured
Why it matters
A wildcard Access-Control-Allow-Origin: * on an authenticated endpoint completely voids same-origin protection: any page on any domain can read the response from a cross-origin fetch, bypassing the browser's security model (CWE-942, OWASP A05:2021). Pairing Allow-Credentials: true with Allow-Origin: * is a misconfiguration that browsers reject, breaking legitimate cross-origin authenticated requests. Missing CORS configuration on APIs that have external consumers silently fails for those clients, producing hard-to-debug network errors.
Severity rationale
High because wildcard CORS on authenticated routes enables cross-origin data theft from any attacker-controlled website that can lure an authenticated user into a browser.
Remediation
Configure CORS explicitly in next.config.ts via the headers() function, pinning the allowed origin to your actual domain:
// next.config.ts
async headers() {
return [{
source: '/api/:path*',
headers: [
{ key: 'Access-Control-Allow-Origin', value: process.env.ALLOWED_ORIGIN! },
{ key: 'Access-Control-Allow-Methods', value: 'GET,POST,PUT,PATCH,DELETE,OPTIONS' },
{ key: 'Access-Control-Allow-Headers', value: 'Content-Type,Authorization' },
],
}]
},
Never use * on authenticated routes. Use an environment variable for the origin so staging and production can differ. If you need cookie-based cross-origin auth, add Access-Control-Allow-Credentials: true only alongside the specific origin allowlist — never alongside *.
Detection
- ID:
cors-configured - Severity:
high - What to look for: Enumerate all CORS configuration locations. Quote the actual
Access-Control-Allow-Originheader value found. Check the CORS configuration for API routes. Look for:Access-Control-Allow-Originheader settings in framework config, middleware, or individual route handlers; use ofcorsnpm package with anoriginallowlist; Vercel/Netlify header config; wildcard*on routes that require authentication (this is a security issue — authenticated endpoints should never use*). Also check:Access-Control-Allow-Credentials— if this istrue,Access-Control-Allow-Originmust not be*. Explicit signals for cross-origin consumers include: comments describing external callers or integrations in route handlers, CORS headers already set,Access-Control-*headers in middleware, a separate/api/public/or/api/external/route namespace, or documentation referencing third-party integrations calling your API. - Pass criteria: CORS is explicitly configured with at least 1 specific domain in the allowlist. Authenticated routes use a specific domain allowlist (not
*). Unauthenticated public API routes may use*if intentional.Allow-Credentials: trueis never paired withAllow-Origin: *. - Fail criteria: No CORS configuration (relying on browser defaults, which may fail for cross-origin clients); or wildcard
*on authenticated routes; orAllow-Credentials: truepaired withAllow-Origin: *. - Skip (N/A) when: The API is only called from the same origin (no cross-origin clients, no mobile app, no third-party integrations). Signal: no CORS headers configured anywhere AND no evidence of cross-origin clients (all API calls are server-side or same-origin fetch).
- Detail on fail: Describe the CORS issue (e.g., "No CORS configuration found for /api/ routes; Access-Control-Allow-Origin: * set on authenticated /api/user routes"). Max 500 chars.
- Remediation: Configure CORS explicitly in
next.config.tsorsrc/middleware.tsrather than relying on defaults. For Next.js, add CORS headers innext.config.tsvia theheaders()function, or use a middleware wrapper. Specify the exact origin(s) that should be allowed:Access-Control-Allow-Origin: https://yourapp.com. If you have multiple environments (staging, production), use an environment variable for the origin. Never use wildcard*on routes that read or write authenticated user data. If you need to support credentials (cookies) cross-origin, use a specific origin allowlist.
External references
- cwe · CWE-942 — Permissive Cross-domain Policy with Untrusted Domains
- owasp:2021 · A05 — Security Misconfiguration
Taxons
History
- 2026-04-18·v1.0.0·Initial import from saas-api-design·automated