HTTP Header

CORS im HTTP verständlich erklärt: Cross-Origin Resource Sharing

CORS (Cross-Origin Resource Sharing) ist ein wichtiger Sicherheits-Mechanismus, der über HTTP-Header gesteuert wird. Er regelt, ob und wie Webanwendungen, die auf einer bestimmten Domain laufen (z. B. https://allerate.com), auf Ressourcen oder APIs einer anderen Domain (z. B. https://api.allerate.dev) zugreifen dürfen. CORS bricht somit die standardmässig im Browser aktive, sehr strenge Same-Origin-Policy (SOP) gezielt auf.

CORS ist damit kein Angriffsvektor, sondern eine kontrollierte Lockerung der Browser-Schutzregeln. Es greift nur im Browser-Kontext und ist von echten Sicherheits-Antwortheadern wie der Content-Security-Policy zu unterscheiden, die ein gänzlich anderes Schutzziel verfolgt.

Same-Origin-Policy (SOP) als Sicherheitsbasis

Ohne die Same-Origin-Policy wäre das Web extrem unsicher. Origin (Herkunft) definiert sich über die Kombination aus Protokoll (http/https), Domain und Port.

  • Besuchen Sie eine bösartige Website, könnte diese sonst im Hintergrund ein JavaScript ausführen, das Ihre Session-Cookies ausliest und geheime Kontodaten von der API Ihrer Bank abruft.
  • Die SOP verhindert dies: Sie blockiert jeden Versuch eines Skripts, Ressourcen von einer fremden Origin zu lesen.

CORS ist die kontrollierte Ausnahme von dieser Regel. Es teilt dem Browser über HTTP-Antwort-Header mit: „Ich kenne die anfragende Domain und erlaube ihr den Zugriff auf meine Daten.“


Die wichtigsten CORS-Header des Servers

Wenn ein Browser eine Cross-Origin-Anfrage stellt, prüft er die Antwort des Servers auf spezifische Header:

  • Access-Control-Allow-Origin: Gibt an, welche Domains auf die API zugreifen dürfen.
    • Sicher: Access-Control-Allow-Origin: https://allerate.com
    • Unsicher (für geschützte APIs): Access-Control-Allow-Origin: * (erlaubt jeder Website der Welt den Zugriff).
  • Access-Control-Allow-Methods: Listet die erlaubten HTTP-Methoden auf (z. B. GET, POST, DELETE, OPTIONS).
  • Access-Control-Allow-Headers: Definiert, welche benutzerdefinierten Header der Client mitsenden darf (z. B. Authorization, Content-Type).
  • Access-Control-Allow-Credentials: Teilt dem Browser mit, ob er sensible Anmeldeinformationen (wie Session-Cookies oder Authorization-Header) mitsenden darf (true oder false).

Der Ablauf: Einfache vs. Preflight-Anfragen

Der Browser unterscheidet bei CORS-Anfragen zwei Abläufe:

1. Einfache Anfragen (Simple Requests)

Bei einfachen Anfragen (z. B. ein normales GET- oder ein einfaches POST-Formular) sendet der Browser die Anfrage direkt ab. Nach Erhalt der Antwort prüft er, ob der Header Access-Control-Allow-Origin die Absenderdomain enthält. Wenn nicht, blockiert der Browser den Zugriff des JavaScripts auf die Antwortdaten (die Anfrage wurde auf dem Server dennoch ausgeführt!).

2. Preflight-Anfragen (OPTIONS)

Bei komplexeren Anfragen (z. B. POST-Anfragen mit JSON-Body und passendem Content-Type oder Anfragen mit Auth-Tokens) geht der Browser auf Nummer sicher. Er schaltet eine Preflight-Anfrage mit der HTTP-Methode OPTIONS vor:

sequenceDiagram
    participant B as Browser
    participant S as Webserver (API)
    B->>S: 1. OPTIONS /api/data (Darf ich POST mit JSON senden?)
    Note right of S: 2. Prüfe CORS-Regeln (erlaubt!)
    S-->>B: 3. HTTP 200 OK + Access-Control-Allow-Origin
    B->>S: 4. POST /api/data (tatsächlicher Request)
    Note right of S: 5. Verarbeite Daten
    S-->>B: 6. HTTP 200 OK + JSON-Daten

Erst wenn die Preflight-Anfrage (OPTIONS) vom Server mit den passenden Erlaubnis-Headern beantwortet wird, führt der Browser den tatsächlichen POST-Request aus. Dies schützt den Server vor unerwünschten Zustandsänderungen durch Fremdseiten.


Einfache vs. Preflight-Anfrage im Überblick

Ob der Browser eine Vorab-Anfrage (Preflight) schickt, hängt von Methode, Headern und Content-Type ab:

KriteriumEinfache AnfragePreflight (OPTIONS)
MethodenGET, HEAD, einfaches POSTPUT, DELETE, PATCH
Content-Typetext/plain, form-urlencodedapplication/json
Eigene HeaderKeinez. B. Authorization
Zusätzliche AnfrageNeinJa, OPTIONS vorab

Faustregel: Sobald Sie JSON senden oder einen Authorization-Header mitgeben, löst der Browser eine Preflight-Anfrage aus – der Server muss dann auch auf OPTIONS korrekt antworten.


Häufige CORS-Fehler und ihre Ursachen

Die meisten CORS-Probleme lassen sich auf wenige, wiederkehrende Fehlkonfigurationen zurückführen:

Fehlermeldung / SymptomUrsacheLösung
«No ‘Access-Control-Allow-Origin’ header»Server sendet den Header gar nichtCORS serverseitig aktivieren
Wildcard * trotz Cookies blockiertAllow-Credentials: true + *Konkrete Origin statt * setzen
Preflight schlägt mit 405 fehlServer beantwortet OPTIONS nichtOPTIONS-Route hinzufügen
Eigener Header wird abgelehntHeader fehlt in Allow-HeadersHeader explizit auflisten

Praxisbeispiel: korrekte CORS-Antwort für eine geschützte API

Für eine API, die Cookies oder Tokens verarbeitet, muss der Server die konkrete Origin nennen und Credentials erlauben:

Access-Control-Allow-Origin: https://allerate.com
Access-Control-Allow-Methods: GET, POST, OPTIONS
Access-Control-Allow-Headers: Authorization, Content-Type
Access-Control-Allow-Credentials: true
Access-Control-Max-Age: 86400

Der Header Access-Control-Max-Age weist den Browser an, das Ergebnis der Preflight-Anfrage 24 Stunden zwischenzuspeichern. Das spart bei vielen API-Aufrufen unnötige OPTIONS-Anfragen und verbessert die Performance spürbar.

[!TIP] Fehlkonfigurationen bei CORS gehören zu den häufigsten Fehlern in der modernen Webentwicklung und blockieren oft die Kommunikation zwischen Frontend und Backend. Prüfen Sie die CORS- und HTTP-Header Ihrer APIs live mit dem HTTP Header Check auf balou.tools.

Häufig gestellte Fragen (FAQ)

Was ist die Same-Origin-Policy (SOP)?

SOP ist ein grundlegendes Sicherheitskonzept im Browser. Es verbietet Webseiten standardmässig, Skripte auszuführen, die Daten von einer anderen Domain abrufen (z. B. darf eine Schadseite keinen API-Request an Ihre Onlinebanking-Domain senden).

Darf man „Access-Control-Allow-Origin: *“ nutzen?

Für öffentliche APIs ohne Registrierung (wie Wetterdaten) ist dies in Ordnung. Für Systeme, die Authentifizierung (Cookies, JWTs) verlangen, ist der Wildcard-Eintrag `*` verboten. Es muss zwingend die konkrete Origin des Frontends deklariert werden.

Warum bekomme ich einen CORS-Fehler, obwohl der Server antwortet?

CORS ist eine reine Browser-Schutzmassnahme. Der Server führt die Anfrage oft aus und sendet eine Antwort, aber der Browser blockiert anschliessend den Zugriff des JavaScripts auf diese Antwort, weil der passende Access-Control-Allow-Origin-Header fehlt. Der Fehler erscheint deshalb nur im Browser, nicht in Werkzeugen wie curl oder Postman.

Löst die Wildcard * auch Anfragen mit Cookies?

Nein. Sobald Access-Control-Allow-Credentials auf true steht, verbietet die Spezifikation den Wildcard-Wert *. Der Server muss dann die konkrete Origin zurückgeben und sie bei mehreren erlaubten Domains dynamisch aus dem Origin-Request-Header spiegeln. Andernfalls blockiert der Browser die Antwort.