What does CORS really do? πŸ€”

Pelle Nilsen - Oct 30 - - Dev Community

Table of Contents

CORS (Cross-Origin Resource Sharing) is often misunderstood as just another security headache for developers. Let's break down what it actually does and why it's crucial for web security.

The Same-Origin Policy Problem πŸ”’

Imagine you're at app1.com and your JavaScript code tries to fetch data from app2.com. Without CORS, this request would be blocked by the browser's same-origin policy. This policy prevents a malicious website from reading sensitive data from another website - like your banking details or private messages.

Enter CORS: The Security Guard πŸ’‚

CORS acts like a security guard that allows controlled access between different domains. Here's how it works:

  1. The Request: Your frontend code makes a request to a different domain:
// Frontend at app1.com
fetch('http://api.app2.com/data', {
    method: 'GET',
    headers: {
        'Content-Type': 'application/json'
    }
});
Enter fullscreen mode Exit fullscreen mode
  1. The Preflight: For certain requests, the browser first sends an OPTIONS request to check if the actual request is allowed:
OPTIONS /data HTTP/1.1
Host: api.app2.com
Origin: https://app1.com
Access-Control-Request-Method: GET
Access-Control-Request-Headers: Content-Type
Enter fullscreen mode Exit fullscreen mode
  1. The Permission: The server responds with what's allowed:
HTTP/1.1 200 OK
Access-Control-Allow-Origin: https://app1.com
Access-Control-Allow-Methods: GET, POST
Access-Control-Allow-Headers: Content-Type
Access-Control-Max-Age: 86400
Enter fullscreen mode Exit fullscreen mode

Common CORS Headers Explained πŸ“‹

  • Access-Control-Allow-Origin: Who can access the resource
    • * means everyone (use cautiously‼️)
    • https://app1.com means only that specific domain
  • Access-Control-Allow-Methods: Allowed HTTP methods
    • Example: GET, POST, PUT, DELETE
  • Access-Control-Allow-Headers: Allowed request headers
    • Example: Content-Type, Authorization
  • Access-Control-Max-Age: How long to cache preflight results
    • Example: 86400 (24 hours)

Quick Node.js/Express Implementation πŸ› οΈ

Here's how to implement CORS in a Node.js/Express server:

const express = require('express');
const app = express();

app.use((req, res, next) => {
    res.header('Access-Control-Allow-Origin', 'https://app1.com');
    res.header('Access-Control-Allow-Methods', 'GET, POST, PUT, DELETE');
    res.header('Access-Control-Allow-Headers', 'Content-Type, Authorization');

    // Handle preflight
    if (req.method === 'OPTIONS') {
        return res.sendStatus(200);
    }
    next();
});

// Or use the cors package
const cors = require('cors');
app.use(cors({
    origin: 'https://app1.com',
    methods: ['GET', 'POST', 'PUT', 'DELETE'],
    allowedHeaders: ['Content-Type', 'Authorization']
}));
Enter fullscreen mode Exit fullscreen mode

Common CORS Gotchas 🎯

  1. Credentials: If you're sending cookies or auth headers, you need:
// Frontend
fetch(url, {
    credentials: 'include'
});

// Backend
res.header('Access-Control-Allow-Credentials', 'true');
Enter fullscreen mode Exit fullscreen mode
  1. Wildcard Limitations: You can't use * with credentials
// This won't work with credentials
res.header('Access-Control-Allow-Origin', '*');

// Use specific origins instead
res.header('Access-Control-Allow-Origin', 'https://app1.com');
Enter fullscreen mode Exit fullscreen mode

Best Practices 🌟

  1. Be Specific: Avoid using * for Access-Control-Allow-Origin
  2. Limit Methods: Only allow necessary HTTP methods
  3. Cache Preflights: Set appropriate Access-Control-Max-Age
  4. Secure Credentials: Be extra careful when allowing credentials
  5. Validate Origins: Maintain a whitelist of allowed domains

Conclusion 🎬

CORS isn't just a barrier - it's a crucial security feature that protects users while enabling controlled cross-origin communication. Understanding how it works helps you implement it correctly and debug issues more effectively.

Remember: CORS is enforced by browsers, not servers. Server-to-server communication doesn't use CORS, so make sure to implement proper security measures for those scenarios.

. . . . . . . .