Hinzufügen einer CORS-Anforderung im Header in Angular 5

85

Ich habe das CORS in der Kopfzeile hinzugefügt, erhalte jedoch immer noch das CORS-Problem in meiner Anfrage. Was ist der richtige Weg, um CORS und andere Anforderungen in den Headern hinzuzufügen und zu verarbeiten?

Hier ist der Code der Servicedatei:

import { HttpClient, HttpHeaders, HttpClientModule } from '@angular/common/http';
const httpOptions = {
  headers: new HttpHeaders({ 
    'Access-Control-Allow-Origin':'*',
    'Authorization':'authkey',
    'userid':'1'
  })
};

public baseurl = 'http://localhost/XXXXXX';

userAPI(data): Observable<any> {
  return this.http.post(this.baseurl, data, httpOptions)
    .pipe(
      tap((result) => console.log('result-->',result)),
      catchError(this.handleError('error', []))
    );
}

Error:

Die Antwort auf die Preflight-Anforderung besteht die Zugriffssteuerungsprüfung nicht: In der angeforderten Ressource ist kein Header 'Access-Control-Allow-Origin' vorhanden. Origin ' http: // localhost: 4200 ' ist daher kein Zugriff gestattet

fehlgeschlagen: HTTP-Fehlerantwort für (unbekannte URL): 0 Unbekannter Fehler

In meinem serverseitigen Code habe ich CORS zur Indexdatei hinzugefügt.

header('Access-Control-Allow-Origin: *');
header('Access-Control-Allow-Methods: GET, POST, PATCH, PUT, DELETE, OPTIONS');
header('Access-Control-Allow-Headers: Origin, Content-Type, X-Auth-Token');
Aman Kumar
quelle
3
Die Cors-Header müssen auf der Serverseite hinzugefügt werden.
Sachila Ranawaka
@SachilaRanawaka Ja, ich habe es in meine Indexdatei aufgenommen.
Aman Kumar
Post , die Server - Datei
Sachila Ranawaka
Diese Antwort kann nützlich sein: stackoverflow.com/a/58064366/7059557
AmirReza-Farahlagha

Antworten:

50

Nach meiner Erfahrung funktionierten die Plugins mit HTTP, jedoch nicht mit dem neuesten httpClient. Außerdem war das Konfigurieren der CORS-Antwortheader auf dem Server keine Option. Also habe ich eine proxy.conf.jsonDatei erstellt, die als Proxyserver fungiert.

Lesen Sie mehr dazu hier .

proxy.conf.json Datei:

{
  "/posts": {
    "target": "https://example.com",
    "secure": true,
    "pathRewrite": {
    "^/posts": ""
  },
    "changeOrigin": true
  }
}

Ich habe die proxy.conf.jsonDatei direkt neben der package.jsonDatei im selben Verzeichnis abgelegt.

Dann habe ich den Startbefehl in der Datei package.json geändert:

"start": "ng serve --proxy-config proxy.conf.json"

Der HTTP-Aufruf von meiner App-Komponente:

return this._http.get('/posts/pictures?method=GetPictures')
.subscribe((returnedStuff) => {
  console.log(returnedStuff);
});

Zuletzt müsste ich npm startoder verwenden , um meine App auszuführenng serve --proxy-config proxy.conf.json

rgantla
quelle
13
Es funktioniert nur für Entwicklungszwecke. Sie können Ihre App nicht mit diesem Proxy-Tool
erstellen
Könnte jemand hier bitte einen Blick auf die Frage unter stackoverflow.com/questions/55429787/…
Nelson King
Wie sollen wir das targetin der Datei proxy.config einstellen?
A-Sharabiani
Ich habe es gebunden und den Status OK angezeigt, aber jetzt wird ein neuer Fehler angezeigt. HttpErrorResponse {headers: HttpHeaders, status: 200, statusText: "OK", url: "http://localhost:4200/", ok: false, …} error: SyntaxError: Unexpected token < in JSON at position 0 at JSON.parse (<anonymous>) message: "Unexpected token < in JSON at position 0" "
Aman Gupta
7
Dies funktioniert nicht in Produktions-Builds, daher kann es keine richtige Lösung sein
Aaron Matthews
4

Sie können auch die fetchFunktion und den no-corsModus ausprobieren . Ich finde es manchmal einfacher, es zu konfigurieren als Angulars integriertes http-Modul. Sie können auf der Netzwerkregisterkarte der Chrome Dev-Tools mit der rechten Maustaste auf Anforderungen klicken und diese in die Abrufsyntax kopieren.

import { from } from 'rxjs';

// ...

result = from( // wrap the fetch in a from if you need an rxjs Observable
  fetch(
    this.baseurl,
    {
      body: JSON.stringify(data)
      headers: {
        'Content-Type': 'application/json',
      },
      method: 'POST',
      mode: 'no-cors'
    }
  )
);
Metakermit
quelle
Der Code in der Frage versucht, die Antwort zu lesen . no-corsblockiert das. Es blockiert auch das Setzen des Inhaltstyps auf application/json.
Quentin
Sehr spezieller Fall, für api.github.com/orgs/nesign/repos , ich sah Access to XMLHttpRequest at '..' from origin '..' has been blocked by CORS policy: Request header field x-timezone is not allowed by Access-Control-Allow-Headers in preflight response.nicht in Access-Control-Request-Headers: cache-control,x-timezoneder Lage zu überschreiben, was standardmäßig hinzugefügt wurde :( und Github hat dies als Antwort Access-Control-Allow-Headers: Authorization, Content-Type, If-Match, If-Modified-Since, If-None-Match, If-Unmodified-Since, Accept-Encoding, X-GitHub-OTP, X-Requested-With, User-AgentAbruf funktioniert
Anand Rockzz
Hoppla! x-Zeitzone von mir hinzugefügt wurde - ich hatte über engineered die httpclientmit Abfangjäger lange Zeit zurück :)
Anand rockzz
3

Wenn Sie wie ich sind und einen lokalen SMS-Gateway-Server verwenden und eine GET-Anfrage an eine IP wie 192.168.0.xx senden, erhalten Sie mit Sicherheit einen CORS-Fehler.

Leider konnte ich keine Angular-Lösung finden, aber mit Hilfe einer früheren Wiederholung habe ich meine Lösung erhalten und veröffentliche eine aktualisierte Version für Angular 7 8 9

import {from} from 'rxjs';

getData(): Observable<any> {
    return from(
      fetch(
        'http://xxxxx', // the url you are trying to access
        {
          headers: {
            'Content-Type': 'application/json',
          },
          method: 'GET', // GET, POST, PUT, DELETE
          mode: 'no-cors' // the most important option
        }
      ));
  }

Einfach wie gewohnt abonnieren.

Avram Virgil
quelle
2

Stellen Sie sicher, dass der Header für HttpClient in NG5 so aussieht:

let httpOptions = {
      headers: new HttpHeaders({
        'Content-Type': 'application/json',
        'apikey': this.apikey,
        'appkey': this.appkey,
      }),
      params: new HttpParams().set('program_id', this.program_id)
    };

Sie können mit Ihrer localhost-URL einen API-Anruf tätigen. Das funktioniert bei mir.

  • Bitte vergessen Sie niemals Ihre params-Spalte in der Kopfzeile: wie params: new HttpParams (). Set ('program_id', this.program_id)
Damon Wu
quelle
2

Ein POST mit httpClient in Angular 6 führte auch eine OPTIONS-Anforderung aus:

Überschriften Allgemein:

URL anfordern: https: //hp-probook/perl-bin/muziek.pl/=/postData
Anforderungsmethode: OPTIONEN
Statuscode: 200 OK
Remote-Adresse: 127.0.0.1: 443
Referrer-Richtlinie: Kein Referrer beim Downgrade

Mein Perl-REST-Server implementiert die OPTIONS-Anforderung mit dem Rückkehrcode 200.

Der nächste POST-Anforderungsheader:

Akzeptieren:*/*
Accept-Encoding: gzip, deflate, br
Akzeptiersprache: nl-NL, nl; q = 0,8, en-US; q = 0,6, en; q = 0,4
Access-Control-Request-Header: Inhaltstyp
Zugriffssteuerungs-Anforderungsmethode: POST
Verbindung: am Leben bleiben
Host: HP-Probook
Herkunft: http: // localhost: 4200
Referer: http: // localhost: 4200 /
User-Agent: Mozilla / 5.0 (X11; Linux x86_64) AppleWebKit / 537.36 (KHTML, wie Gecko) Chrome / 59.0.3071.109 Safari / 537.36

Hinweis Access-Control-Request-Header: Inhaltstyp.

Mein Backend-Perl-Skript verwendet also die folgenden Header:

 - "Access-Control-Allow-Origin" => '*',
 - "Access-Control-Allow-Methods" => 'GET, POST, PATCH, DELETE, PUT, OPTIONS',
 - "Access-Control-Allow-Headers" => 'Herkunft, Inhaltstyp, X-Auth-Token, Inhaltstyp',

Mit diesem Setup haben GET und POST für mich funktioniert!

Rob Lassche
quelle
1

Bitte importieren Sie Anforderungsoptionen von eckigen Kors

    import {RequestOptions, Request, Headers } from '@angular/http';

und fügen Sie Ihrem Code Anforderungsoptionen hinzu, wie unten angegeben

    let requestOptions = new RequestOptions({ headers:null, withCredentials: 
    true });

Anfrageoption in Ihrer API-Anfrage senden

Code-Snippet unten-

     let requestOptions = new RequestOptions({ headers:null, 
     withCredentials: true });
     return this.http.get(this.config.baseUrl + 
     this.config.getDropDownListForProject, requestOptions)
     .map(res => 
     {
      if(res != null)
      { 
        return res.json();
        //return true;
      }
    })
  .catch(this.handleError);
   }  

und fügen Sie CORS in Ihren Backend-PHP-Code ein, wobei alle API-Anfragen zuerst landen.

Versuchen Sie dies und lassen Sie mich wissen, ob es funktioniert oder nicht. Ich hatte das gleiche Problem. Ich habe CORS von angle5 hinzugefügt, das nicht funktioniert hat. Dann habe ich CORS zum Backend hinzugefügt und es hat bei mir funktioniert

Raj Yadav
quelle
-5

Das Folgende funktionierte für mich nach stundenlangem Versuch

      $http.post("http://localhost:8080/yourresource", parameter, {headers: 
      {'Content-Type': 'application/json', 'Access-Control-Allow-Origin': '*' } }).

Der folgende Code hat jedoch nicht funktioniert. Ich bin mir nicht sicher, warum, hoffentlich kann jemand diese Antwort verbessern.

          $http({   method: 'POST', url: "http://localhost:8080/yourresource", 
                    parameter, 
                    headers: {'Content-Type': 'application/json', 
                              'Access-Control-Allow-Origin': '*',
                              'Access-Control-Allow-Methods': 'POST'} 
                })
MG Entwickler
quelle
1
$ http? Ist es AngularJS, weil wir dort über Angular 5 sprechen. Dieser Code konnte nicht funktionieren
Victor Jozwicki
@ VictorJozwicki Sie haben Recht, es ist nicht Angular 5. In meinem package.json zeigt es Angular Version 1.7.5.
MG Developer