Ursprungsübergreifende Anforderungsheader (CORS) mit PHP-Headern


146

Ich habe ein einfaches PHP-Skript, mit dem ich eine domänenübergreifende CORS-Anfrage versuche:

<?php
header("Access-Control-Allow-Origin: *");
header("Access-Control-Allow-Headers: *");
...

Trotzdem bekomme ich immer noch den Fehler:

Anforderungsheaderfeld X-Requested-Withist von nicht zulässigAccess-Control-Allow-Headers

Fehlt mir etwas?

Antworten:


59

Access-Control-Allow-Headerserlaubt nicht *als akzeptierten Wert, siehe die Mozilla-Dokumentation hier .

Anstelle des Sternchens sollten Sie die akzeptierten Header senden (zuerst, X-Requested-Withwie der Fehler sagt).


289

Der richtige Umgang mit CORS-Anfragen ist etwas komplizierter. Hier ist eine Funktion, die vollständiger (und korrekter) reagiert.

/**
 *  An example CORS-compliant method.  It will allow any GET, POST, or OPTIONS requests from any
 *  origin.
 *
 *  In a production environment, you probably want to be more restrictive, but this gives you
 *  the general idea of what is involved.  For the nitty-gritty low-down, read:
 *
 *  - https://developer.mozilla.org/en/HTTP_access_control
 *  - http://www.w3.org/TR/cors/
 *
 */
function cors() {

    // Allow from any origin
    if (isset($_SERVER['HTTP_ORIGIN'])) {
        // Decide if the origin in $_SERVER['HTTP_ORIGIN'] is one
        // you want to allow, and if so:
        header("Access-Control-Allow-Origin: {$_SERVER['HTTP_ORIGIN']}");
        header('Access-Control-Allow-Credentials: true');
        header('Access-Control-Max-Age: 86400');    // cache for 1 day
    }

    // Access-Control headers are received during OPTIONS requests
    if ($_SERVER['REQUEST_METHOD'] == 'OPTIONS') {

        if (isset($_SERVER['HTTP_ACCESS_CONTROL_REQUEST_METHOD']))
            // may also be using PUT, PATCH, HEAD etc
            header("Access-Control-Allow-Methods: GET, POST, OPTIONS");         

        if (isset($_SERVER['HTTP_ACCESS_CONTROL_REQUEST_HEADERS']))
            header("Access-Control-Allow-Headers: {$_SERVER['HTTP_ACCESS_CONTROL_REQUEST_HEADERS']}");

        exit(0);
    }

    echo "You have CORS!";
}

32
Beachten Sie, dass das Zurücksenden des HTTP-Ursprungswerts als zulässiger Ursprung es jedem ermöglicht, Anforderungen mit Cookies an Sie zu senden, wodurch möglicherweise eine Sitzung von einem Benutzer gestohlen wird, der sich auf Ihrer Website angemeldet und dann die Seite eines Angreifers angezeigt hat. Sie möchten entweder '*' senden (wodurch Cookies nicht zugelassen werden, wodurch Sitzungsdiebstahl verhindert wird) oder die spezifischen Domains, für die die Site funktionieren soll.
Jules

1
Einverstanden. In der Praxis würden Sie wahrscheinlich nicht zulassen, dass nur eine alte Domain Ihren CORS-Dienst verwendet. Sie würden ihn auf einen Satz beschränken, dem Sie vertrauen möchten.
Hiebwaffe

Zu Ihrer Information, diese Lösung funktionierte nur für mich in einem Linux server, in IISirgendeinem Grund einfach nicht funktioniert, ich weiß nicht, ob es mein Hosting ist oder einfach nicht geeignet fürIIS
ncubica

1
Danke dir! Müssen diese Antwort bookmarken. Schade, dass wir dies nicht als neue Antwort markieren können
Ascherer

1
Das einzige, was wirklich funktioniert! .. Ändern Sie einfach Access-Control-Allow-Origin: * TO Access-Control-Allow-Origin: {$ _SERVER ['HTTP_ORIGIN']}
Renan Franca

60

Ich habe den gleichen Fehler erhalten und ihn mit dem folgenden PHP in meinem Back-End-Skript behoben:

header('Access-Control-Allow-Origin: *');

header('Access-Control-Allow-Methods: GET, POST');

header("Access-Control-Allow-Headers: X-Requested-With");

35

Viele Beschreibungen im Internet erwähnen nicht, dass die Angabe Access-Control-Allow-Originnicht ausreicht. Hier ist ein vollständiges Beispiel, das für mich funktioniert:

<?php
    if ($_SERVER['REQUEST_METHOD'] === 'OPTIONS') {
        header('Access-Control-Allow-Origin: *');
        header('Access-Control-Allow-Methods: POST, GET, DELETE, PUT, PATCH, OPTIONS');
        header('Access-Control-Allow-Headers: token, Content-Type');
        header('Access-Control-Max-Age: 1728000');
        header('Content-Length: 0');
        header('Content-Type: text/plain');
        die();
    }

    header('Access-Control-Allow-Origin: *');
    header('Content-Type: application/json');

    $ret = [
        'result' => 'OK',
    ];
    print json_encode($ret);

1
Bitte erklären , warum es nicht genug ist , und was minimal Beispiel ist genug.
halfpastfour.am

Leider erinnere ich mich nicht genau und ich habe jetzt keine Zeit, es erneut zu untersuchen, aber soweit ich mich erinnere, gab es einige grundlegende Annahmen von der Seite des Webservers / Browsers, die dazu führten, dass es nicht funktionierte. Dies war der minimale Code, der für mich funktioniert hat.
Csongor Halmai

24

Ich habe es einfach geschafft, Dropzone und andere Plugins mit diesem Fix zum Laufen zu bringen (AngularJS + PHP Backend).

 header('Access-Control-Allow-Origin: *'); 
    header("Access-Control-Allow-Credentials: true");
    header('Access-Control-Allow-Methods: GET, PUT, POST, DELETE, OPTIONS');
    header('Access-Control-Max-Age: 1000');
    header('Access-Control-Allow-Headers: Origin, Content-Type, X-Auth-Token , Authorization');

füge dies in deine upload.php ein oder wohin du deine Anfrage senden würdest (zum Beispiel wenn du upload.html hast und die Dateien an upload.php anhängen musst, dann kopiere und füge diese 4 Zeilen ein). Auch wenn Sie CORS-Plugins / Addons in Chrome / Mozilla verwenden, müssen Sie diese mehrmals umschalten, damit CORS aktiviert wird


15

Wenn Sie einen CORS-Dienst aus PHP erstellen möchten, können Sie diesen Code als ersten Schritt in Ihrer Datei verwenden, der die Anforderungen verarbeitet:

// Allow from any origin
if(isset($_SERVER["HTTP_ORIGIN"]))
{
    // You can decide if the origin in $_SERVER['HTTP_ORIGIN'] is something you want to allow, or as we do here, just allow all
    header("Access-Control-Allow-Origin: {$_SERVER['HTTP_ORIGIN']}");
}
else
{
    //No HTTP_ORIGIN set, so we allow any. You can disallow if needed here
    header("Access-Control-Allow-Origin: *");
}

header("Access-Control-Allow-Credentials: true");
header("Access-Control-Max-Age: 600");    // cache for 10 minutes

if($_SERVER["REQUEST_METHOD"] == "OPTIONS")
{
    if (isset($_SERVER["HTTP_ACCESS_CONTROL_REQUEST_METHOD"]))
        header("Access-Control-Allow-Methods: POST, GET, OPTIONS, DELETE, PUT"); //Make sure you remove those you do not want to support

    if (isset($_SERVER["HTTP_ACCESS_CONTROL_REQUEST_HEADERS"]))
        header("Access-Control-Allow-Headers: {$_SERVER['HTTP_ACCESS_CONTROL_REQUEST_HEADERS']}");

    //Just exit with 200 OK with the above headers for OPTIONS method
    exit(0);
}
//From here, handle the request as it is ok

8

CORS kann zu Kopfschmerzen werden, wenn wir seine Funktionsweise nicht richtig verstehen. Ich benutze sie in PHP und sie funktionieren ohne Probleme. Referenz hier

header("Access-Control-Allow-Origin: *");
header("Access-Control-Allow-Credentials: true");
header("Access-Control-Max-Age: 1000");
header("Access-Control-Allow-Headers: X-Requested-With, Content-Type, Origin, Cache-Control, Pragma, Authorization, Accept, Accept-Encoding");
header("Access-Control-Allow-Methods: PUT, POST, GET, OPTIONS, DELETE");

7

So viel Code funktioniert für mich, wenn ich Angular 4 als Client-Seite und PHP als Server-Seite verwende.

header("Access-Control-Allow-Origin: *");

3

das sollte funktionieren

header("Access-Control-Allow-Origin: *");
header("Access-Control-Allow-Headers: X-Requested-With, Content-Type, Origin, Cache-Control, Pragma, Authorization, Accept, Accept-Encoding");

0

Fügen Sie diesen Code in .htaccess hinzu

Fügen Sie im Header benutzerdefinierte Authentifizierungsschlüssel wie app_key, auth_key..etc hinzu

Header set Access-Control-Allow-Origin "*"
Header set Access-Control-Allow-Headers: "customKey1,customKey2, headers, Origin, X-Requested-With, Content-Type, Accept, Authorization"

-1

Fügen Sie diesen Befehl in Windows vorerst in das Ausführungsfenster ein, um den Code zu testen

chrome.exe --user-data-dir = "C: / Chrome-Entwicklersitzung" --disable-web-security


Es ist eine schreckliche Idee, die
Websicherheit
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.