CORS-Fehler verstehen und beheben

Kaum eine Fehlermeldung sorgt bei Webentwicklerinnen und Webentwicklern für so viel Frust wie die Zeile Access to fetch has been blocked by CORS policy in der Browser-Konsole. Der eigene Code scheint korrekt, das Backend liefert eine Antwort, und trotzdem verweigert der Browser den Zugriff. Die gute Nachricht: CORS ist kein Bug, sondern ein bewusst eingebauter Schutzmechanismus. Wer versteht, wie er funktioniert, behebt solche Fehler in wenigen Minuten und vermeidet gefährliche Schnellschüsse. Dieser Ratgeber erklärt die Grundlagen, die wichtigsten Header und die saubere Lösung – ohne riskante Abkürzungen.

Was die Same-Origin-Policy bedeutet

Browser folgen seit Langem der sogenannten Same-Origin-Policy. Sie besagt, dass JavaScript einer Webseite standardmäßig nur Daten von derselben Herkunft (Origin) lesen darf, von der die Seite selbst geladen wurde. Eine Origin setzt sich aus drei Bestandteilen zusammen: dem Protokoll (etwa https), dem Hostnamen (etwa app.example.com) und dem Port (etwa 443). Unterscheidet sich auch nur einer dieser Werte, gilt die Anfrage als Cross-Origin.

Der Sinn dahinter ist Sicherheit: Ohne diese Regel könnte eine bösartige Seite im Hintergrund auf deine eingeloggte Online-Banking-Sitzung zugreifen und Daten auslesen. Die Same-Origin-Policy verhindert genau das. CORS (Cross-Origin Resource Sharing) ist der kontrollierte Weg, diese strenge Regel gezielt zu lockern – aber nur dann, wenn der Server es ausdrücklich erlaubt.

Warum der Fehler im Browser, aber nicht in Postman auftritt

Ein häufiger Aha-Moment: Dieselbe API funktioniert in Postman, curl oder im Terminal einwandfrei, aber der Browser blockiert sie. Das liegt daran, dass die Same-Origin-Policy ausschließlich von Browsern durchgesetzt wird. Werkzeuge wie curl haben keine Origin und kümmern sich nicht um CORS. Der Server sendet die Antwort übrigens trotzdem – der Browser hält sie nur vor deinem JavaScript zurück, weil die passende Erlaubnis fehlt. Das ist ein wichtiger Punkt: CORS verhindert nicht, dass die Anfrage den Server erreicht.

Die wichtigsten CORS-Header im Überblick

CORS wird vollständig über HTTP-Antwort-Header gesteuert, die der Server mitschickt. Die folgende Tabelle fasst die zentralen Header zusammen, ihre Bedeutung und einen typischen Beispielwert.

Header Bedeutung Beispielwert
Access-Control-Allow-Origin Legt fest, welche Herkunft auf die Antwort zugreifen darf https://app.example.com
Access-Control-Allow-Methods Erlaubte HTTP-Methoden für Cross-Origin-Anfragen GET, POST, PUT, DELETE
Access-Control-Allow-Headers Erlaubte benutzerdefinierte Anfrage-Header Content-Type, Authorization
Access-Control-Allow-Credentials Erlaubt das Mitsenden von Cookies und Login-Daten true
Access-Control-Max-Age Wie lange das Preflight-Ergebnis zwischengespeichert wird (in Sekunden) 86400
Access-Control-Expose-Headers Welche Antwort-Header das JavaScript auslesen darf X-Total-Count

Der mit Abstand wichtigste Header ist Access-Control-Allow-Origin. Fehlt er oder passt sein Wert nicht zur Herkunft deiner Seite, schlägt die Anfrage fehl. Sein Wert muss exakt mit der anfragenden Origin übereinstimmen – inklusive Protokoll und Port.

Preflight-Requests und die OPTIONS-Anfrage

Bei sogenannten einfachen Anfragen (etwa ein simpler GET ohne ungewöhnliche Header) prüft der Browser CORS direkt anhand der Antwort. Sobald die Anfrage jedoch komplexer wird – zum Beispiel eine PUT- oder DELETE-Methode nutzt, einen Authorization-Header trägt oder JSON mit Content-Type: application/json sendet – schaltet der Browser einen Sicherheitsschritt davor.

Dieser Schritt heißt Preflight-Request. Der Browser schickt zuerst eine OPTIONS-Anfrage an den Server und fragt damit gewissermaßen um Erlaubnis: Welche Methoden und Header sind erlaubt? Erst wenn der Server mit den passenden Allow-Headern antwortet, sendet der Browser die eigentliche Anfrage. Ein typischer Stolperstein: Das Backend behandelt die OPTIONS-Anfrage nicht und antwortet mit einem 404 oder 405. Dann scheitert bereits der Preflight, und die eigentliche Anfrage wird nie ausgeführt.

CORS gehört ins Backend – nicht ins Frontend

Ein zentrales Missverständnis: Viele suchen die Lösung im Frontend und probieren Dinge wie mode: 'no-cors' oder spezielle fetch-Optionen. Das führt selten zum Ziel und macht die Antwort oft sogar unbrauchbar. CORS ist eine Entscheidung des Servers. Nur er kann mit den passenden Antwort-Headern festlegen, wer zugreifen darf. Die richtige Lösung lautet also fast immer: Konfiguriere die CORS-Header auf dem Backend.

  1. Identifiziere die exakte Origin deines Frontends (Protokoll, Host, Port).
  2. Setze Access-Control-Allow-Origin auf genau diese Origin.
  3. Ergänze bei Bedarf erlaubte Methoden und Header.
  4. Behandle OPTIONS-Anfragen explizit, damit der Preflight gelingt.

In den meisten Frameworks gibt es dafür fertige Middleware oder Pakete, die diese Header automatisch setzen. So vermeidest du Tippfehler und musst die Logik nicht von Hand pflegen.

Der gefährliche Wildcard-Fallstrick

Wer genervt ist, setzt schnell Access-Control-Allow-Origin: *. Das erlaubt jeder beliebigen Webseite den Zugriff. Für rein öffentliche, nicht authentifizierte APIs kann das akzeptabel sein. Für alles andere ist es ein Sicherheitsrisiko. Besonders wichtig: Der Wildcard * funktioniert nicht zusammen mit Access-Control-Allow-Credentials: true. Sobald Cookies oder Login-Daten im Spiel sind, musst du eine konkrete Origin angeben. Pflege deshalb eine Liste erlaubter Herkünfte und spiegle die anfragende Origin nur zurück, wenn sie darauf steht.

Häufiger Irrtum: CORS ist keine Authentifizierung

CORS regelt ausschließlich, welche Webseiten im Browser auf eine Antwort zugreifen dürfen. Es ist kein Ersatz für Authentifizierung oder Autorisierung. Da Werkzeuge außerhalb des Browsers CORS ignorieren, schützt es deine Daten nicht vor direktem Zugriff. Sensible Endpunkte brauchen weiterhin echte Mechanismen wie Tokens, Sessions oder API-Schlüssel. Betrachte CORS als zusätzliche Browser-Schutzschicht, niemals als alleinige Verteidigung.

Schnelle Checkliste zur Fehlersuche

Häufige Fragen

Warum funktioniert meine API in Postman, aber nicht im Browser?

Die Same-Origin-Policy wird nur von Browsern durchgesetzt. Postman, curl und ähnliche Werkzeuge haben keine Origin und ignorieren CORS daher vollständig. Der Browser blockiert die Antwort, sobald die passenden Allow-Header fehlen.

Kann ich CORS-Fehler im Frontend beheben?

In der Regel nicht. CORS wird über Antwort-Header des Servers gesteuert. Frontend-Tricks wie mode: 'no-cors' umgehen das Problem nicht, sondern machen die Antwort meist unlesbar. Die saubere Lösung liegt im Backend.

Was ist ein Preflight-Request?

Bei komplexeren Anfragen schickt der Browser zuerst eine OPTIONS-Anfrage und fragt den Server, welche Methoden und Header erlaubt sind. Erst nach erfolgreicher Antwort folgt die eigentliche Anfrage. Antwortet der Server nicht korrekt auf OPTIONS, scheitert bereits dieser Vorabschritt.

Ist Access-Control-Allow-Origin: * sicher?

Nur für öffentliche, nicht authentifizierte Endpunkte. Sobald Cookies oder Login-Daten beteiligt sind, ist der Wildcard ungeeignet und funktioniert nicht mit Allow-Credentials: true. Gib in diesen Fällen eine konkrete, geprüfte Origin an.

Schützt CORS meine Daten vor unbefugtem Zugriff?

Nein. CORS regelt nur den Browser-Zugriff auf Antworten und ersetzt keine Authentifizierung. Da Tools außerhalb des Browsers CORS ignorieren, brauchst du für sensible Endpunkte weiterhin echte Sicherheitsmechanismen wie Tokens oder Sessions.

Warum ändert sich nichts, obwohl ich die Header gesetzt habe?

Häufig liegt es an Caching: Sowohl der Browser als auch zwischengeschaltete Proxys oder CDNs können alte Antworten oder Preflight-Ergebnisse speichern. Leere den Cache, prüfe in der Netzwerk-Konsole die tatsächlich gelieferten Header und achte auf eine exakte Schreibweise der Origin.

Weitere praktische Anleitungen rund um Webentwicklung findest du in unseren News-Beiträgen. Nützliche kostenlose Helfer wie Encoder, Validatoren und Formatierer warten in der Webtools-Sammlung. Einen Überblick über alle Angebote gibt die Startseite.