Skip to Content
πŸŽ‰ Welcome to my notes πŸŽ‰
Express.jsCORS Explained 🌐

CORS Explained 🌐

If you’ve ever built a front-end application that tries to fetch data from an API on a different domain, you’ve likely encountered a CORS error. Understanding CORS is essential for building web APIs that can be used by other websites.

πŸ›‘οΈ The Problem: The Same-Origin Policy (SOP)

The Same-Origin Policy (SOP) is a fundamental security feature built into all modern web browsers. It restricts a web page from making requests to a domain different from the one that served the web page.

An β€œorigin” is defined by the combination of protocol, domain, and port. If any of these three differ, the origins are considered different.

  • https://my-app.com -> Origin A
  • https://api.my-app.com -> Origin B (different domain)
  • http://my-app.com -> Origin C (different protocol)
  • https://my-app.com:3000 -> Origin D (different port)

For example, JavaScript code running on https://my-app.com cannot make a fetch request to an API at https://api.theirs.com. The browser will block the request to prevent malicious behavior.

βœ… The Solution: CORS (Cross-Origin Resource Sharing)

CORS is the mechanism that allows a server to relax the Same-Origin Policy. It’s a system of HTTP headers that a server can use to tell the browser which other origins are permitted to access its resources.

It’s not a server-side error; it’s the browser enforcing security. The server just needs to send the right headers to give the browser permission.

How CORS Works in Practice

CORS works through a conversation of HTTP headers between the browser and the server. This conversation can be simple or involve a β€œpreflight” check.

1. Simple Requests

For simple requests (like GET or POST with standard headers), the flow is straightforward:

  1. The browser sends the cross-origin request to the server.
  2. The server must include the Access-Control-Allow-Origin header in its response.
  3. The browser checks this header. If the origin of the requesting website is allowed, the browser allows the JavaScript code to access the response. If not, it throws a CORS error.

Access-Control-Allow-Origin: https://my-app.com (allows one specific origin) Access-Control-Allow-Origin: * (allows any origin)

2. Preflight Requests (OPTIONS)

For more complex requests (e.g., methods like DELETE or PUT, or requests with custom headers like Authorization), the browser performs a preflight request for safety.

  1. Preflight: Before sending the actual request, the browser sends a special OPTIONS request to the server URL. This request β€œasks for permission.”
  2. Server Response: The server must respond to this OPTIONS request with headers that grant permission, such as:
    • Access-Control-Allow-Origin: Which origin is allowed.
    • Access-Control-Allow-Methods: Which HTTP methods are allowed (e.g., GET, POST, DELETE).
    • Access-Control-Allow-Headers: Which custom headers are allowed (e.g., Content-Type, Authorization).
  3. Actual Request: If the server’s response to the preflight is permissive, the browser then sends the actual (DELETE, PUT, etc.) request. If permission is denied, the actual request is never sent.

Implementing CORS in Express

The easiest and most secure way to handle CORS in Express is by using the official cors middleware package. After installing it with npm install cors, you can apply it to your application. Using app.use(cors()) enables CORS for all origins, which is good for public APIs. For better security, you can configure it to only allow specific origins, like app.use(cors({ origin: 'https://my-specific-frontend.com' })). The cors middleware automatically handles both simple and preflight requests for you.

app.js
const express = require("express"); const cors = require("cors"); // Import the cors package const app = express(); // --- Basic Usage: Enable All CORS Requests --- // This allows requests from any origin. Good for public APIs. app.use(cors()); // --- Configured Usage: Allow a Specific Origin --- // This is more secure and is recommended for most applications. const corsOptions = { origin: "https://my-specific-frontend.com", optionsSuccessStatus: 200, // For legacy browser support }; // app.use(cors(corsOptions)); // Uncomment to use specific options app.get("/api/data", (req, res) => { res.json({ message: "This data is now accessible from other origins!" }); }); app.listen(3000, () => console.log("Server running with CORS enabled"));

✨ Summary

  • Browsers enforce the Same-Origin Policy (SOP) for security.
  • CORS is the mechanism for servers to grant cross-origin access using special HTTP headers.
  • Complex requests (like DELETE or those with custom headers) will trigger a preflight OPTIONS request that the server must approve.
  • In Express, the easiest and most robust way to manage CORS is with the cors middleware package.
Last updated on