Fix CORS in Express Without Allowing Every Origin

The Express corsmiddleware manages the response headers browsers need for cross-origin requests. A production-ready setup should use an explicit origin allowlist, handle preflight requests, and configure credentials only when required.

1. Install

npm install express cors npm install -D @types/express @types/cors 

2. Create a reusable middleware

import cors, { type CorsOptions } from 'cors'; const allowedOrigins = new Set([ 'http://localhost:4200', 'https://app.example.com', ]); const options: CorsOptions = { origin(origin, callback) { callback( null, !origin ? false : allowedOrigins.has(origin) ? origin : false, ); }, methods: ['GET', 'POST', 'PUT', 'PATCH', 'DELETE'], allowedHeaders: ['Content-Type', 'Authorization'], maxAge: 600, }; export const corsMiddleware = cors(options); 

3. Register it before routes

import express from 'express'; import { corsMiddleware } from './cors.middleware.js'; const app = express(); app.use(corsMiddleware); app.use(express.json()); app.get('/api/products', (_req, res) => { res.json([{ id: 1, name: 'Keyboard' }]); }); app.listen(3000); 

Application-level middleware handles preflight requests automatically.

4. What about cookies?

For cookie-based authentication, use a specific trusted origin and enable credentials:

const options: CorsOptions = { origin: ['https://app.example.com'], credentials: true, }; 

On the frontend:

fetch('https://api.example.com/api/profile', { credentials: 'include', }); 

Remember: credentialed CORS requests cannot use Access-Control-Allow-Origin: *. Cookie settings and CSRF protection still matter.

Key takeaways

  • Keep CORS configuration in one reusable middleware.
  • Allow known frontend origins instead of reflecting arbitrary origins.
  • Let application-level CORS middleware handle preflight requests.
  • Treat CORS and API authentication as separate security concerns.

I wrote about this in much more detail on Medium if you want to dive deeper: https://medium.com/@vetriselvan_11/cors-in-node-js-and-express-a-typescript-implementation-ff259e2bb884?sharedUserId=vetriselvan_11

A question for backend developers: Do you configure CORS globally in Express, or do you prefer separate policies for public APIs, admin routes, and authentication endpoints?





Share your approach in the comments.