no-permissive-cors-response
Detects permissive CORS headers in Lambda API Gateway responses. This rule is part of [`eslint-plugin-lambda-security`](https://www.npmjs.com/package/eslint-plu
Keywords: CORS, Lambda, API Gateway, CWE-942, security, Access-Control-Allow-Origin, wildcard, auto-fix
Detects permissive CORS headers in Lambda API Gateway responses. This rule is part of eslint-plugin-lambda-security.
⚠️ This rule errors by default in the recommended config.
Quick Summary
| Aspect | Details |
|---|---|
| CWE Reference | CWE-942 (Permissive Cross-domain Policy) |
| Severity | 🔴 High |
| Auto-Fix | ✅ Yes |
| Category | Security |
| Best For | Lambda functions returning API Gateway responses |
Vulnerability and Risk
Vulnerability: Lambda functions that return responses with Access-Control-Allow-Origin: * allow any website to access the API.
Risk: Combined with credentials, attackers can steal authentication tokens or session data from users who visit malicious sites.
Rule Logic Flow
Examples
❌ Incorrect
// Lambda handler with wildcard CORS - VULNERABLE
export const handler = async (event) => {
return {
statusCode: 200,
headers: {
'Access-Control-Allow-Origin': '*',
'Content-Type': 'application/json',
},
body: JSON.stringify({ data: 'sensitive' }),
};
};
// Also vulnerable in error responses
export const handler = async () => {
return {
statusCode: 500,
headers: {
'Access-Control-Allow-Origin': '*',
},
body: JSON.stringify({ error: 'Internal error' }),
};
};✅ Correct
// Specific origin - SAFE
export const handler = async (event) => {
return {
statusCode: 200,
headers: {
'Access-Control-Allow-Origin': 'https://app.example.com',
'Content-Type': 'application/json',
},
body: JSON.stringify({ data: 'sensitive' }),
};
};
// Dynamic origin validation - SAFE
const ALLOWED_ORIGINS = [
'https://app.example.com',
'https://admin.example.com',
];
export const handler = async (event) => {
const origin = event.headers?.origin || event.headers?.Origin;
const allowedOrigin = ALLOWED_ORIGINS.includes(origin)
? origin
: ALLOWED_ORIGINS[0];
return {
statusCode: 200,
headers: {
'Access-Control-Allow-Origin': allowedOrigin,
Vary: 'Origin',
},
body: JSON.stringify({ data: 'sensitive' }),
};
};Options
| Option | Type | Default | Description |
|---|---|---|---|
allowInTests | boolean | false | Allow permissive CORS in test files |
{
"rules": {
"lambda-security/no-permissive-cors-response": "error"
}
}Best Practices
1. Use Environment Variable for Origin
const ALLOWED_ORIGIN = process.env.CORS_ORIGIN || 'https://app.example.com';
return {
statusCode: 200,
headers: {
'Access-Control-Allow-Origin': ALLOWED_ORIGIN,
},
body: JSON.stringify(data),
};2. Add Vary Header for Dynamic Origins
headers: {
'Access-Control-Allow-Origin': validatedOrigin,
'Vary': 'Origin' // Important for caching
}Related Rules
no-permissive-cors-middy- CORS in Middy middleware
Known False Negatives
The following patterns are not detected due to static analysis limitations:
Headers from Variable
Why: Headers stored in variables are not analyzed.
// ❌ NOT DETECTED - Headers from variable
const headers = { 'Access-Control-Allow-Origin': '*' };
return { statusCode: 200, headers, body: '...' };Mitigation: Use inline headers. Validate config at startup.
Headers from Spread
Why: Spread hides actual header values.
// ❌ NOT DETECTED - Headers spread
const baseHeaders = getBaseHeaders(); // May include origin: '*'
return { statusCode: 200, headers: { ...baseHeaders }, body: '...' };Mitigation: Explicitly define CORS headers inline.
Response Factory Functions
Why: Response helpers are not recognized.
// ❌ NOT DETECTED - Response factory
function createResponse(body) {
return {
statusCode: 200,
headers: { 'Access-Control-Allow-Origin': '*' }, // Hidden
body: JSON.stringify(body),
};
}
export const handler = async () => createResponse({ data: 'test' });Mitigation: Apply rule to response helper modules.
API Gateway Configuration
Why: CORS configured at API Gateway level is not visible.
// ❌ NOT DETECTED (correctly) - API Gateway handles CORS
// serverless.yml or SAM template has CORS: '*'
return { statusCode: 200, body: '...' };Mitigation: Review API Gateway CORS configuration separately.
Resources
Error Message Format
The rule provides LLM-optimized error messages (Compact 2-line format) with actionable security guidance:
🔒 CWE-942 OWASP:A01 CVSS:7.5 | CORS Misconfiguration detected | HIGH
Fix: Review and apply the recommended fix | https://owasp.org/Top10/A01_2021/Message Components
| Component | Purpose | Example |
|---|---|---|
| Risk Standards | Security benchmarks | CWE-942 OWASP:A01 CVSS:7.5 |
| Issue Description | Specific vulnerability | CORS Misconfiguration detected |
| Severity & Compliance | Impact assessment | HIGH |
| Fix Instruction | Actionable remediation | Follow the remediation steps below |
| Technical Truth | Official reference | OWASP Top 10 |
no-permissive-cors-middy
Detects permissive CORS configurations in Middy middleware. This rule is part of [`eslint-plugin-lambda-security`](https://www.npmjs.com/package/eslint-plugin-l
no-secrets-in-env
Detects secrets defined directly in environment variable configurations. This rule is part of [`eslint-plugin-lambda-security`](https://www.npmjs.com/package/es