web-dev-qa-db-ja.com

HTTPClient POST JSON以外の応答を解析しようとします

私はAngularでリクエストを作成しようとしていますが、HTTPレスポンスはJSONではないことを知っていますが、ただし、Angularは、JSON応答を予期しているようです。エラーは次のとおりです。

SyntaxError:JSONのXMLHttpRequest.cのJSON.parse()の位置0にある予期しないトークン<

と同様

http:// localhost:9 ...の解析中のHTTPエラー.

これはpostメソッドです。

return this.http.post(this.loginUrl, this.createLoginFormData(username, password), this.httpOptions)
  .pipe(
    tap( // Log the result or error
      data => console.log(data);
      error => console.log(error)
    )
  );

およびヘッダー。

private httpOptions = {

  headers: new HttpHeaders({
    'Accept': 'text/html, application/xhtml+xml, */*',
    'Content-Type': 'application/x-www-form-urlencoded',
    responseType: 'text'
  },

) };

responseType: 'text'は、Angular JSON以外の応答を予期するのに十分です。

16
Amy

responseType: 'text'httpOptionsの間違ったセクションに配置しました-これはoutside of headersのように配置する必要があります。

private httpOptions = {
  headers: new HttpHeaders({
    'Accept': 'text/html, application/xhtml+xml, */*',
    'Content-Type': 'application/x-www-form-urlencoded'
  }),
  responseType: 'text'
};

以前のバージョンでは、応答をテキストとして実際に処理するためのAngular)の指示だけではなく、responseTypeのリクエストヘッダーがサーバーに送信されていました。

16
Kirk Larkin

このコードは、pdfファイルをxhrダウンロードするために最終的に機能しました(Angular 6/Laravel 5.6)。PDF file vs text file 'responseType': 'blob' as 'json'

showPdf(filename: String){
  this.restService.downloadFile(
     'protected/getpdf',
     {'filename': filename}
  )
}

//method from restService
public downloadFile(endpoint:String, postData:Object){

  var restService = this

  var HTTPOptions = {
     headers: new HttpHeaders({
        'Accept':'application/pdf'
     }),
     'responseType': 'blob' as 'json'
  }

  this.http.post(this.baseurl+endpoint,postData,HTTPOptions )
  .subscribe(
     res => {
        console.log(res) //do something with the blob
     },
     error => {
        console.error('download error:', error)
     }, 
     () => {
        console.log('Completed file download.')
     }
  )
}

Kirk Larkins Answer(ありがとうございます!)と長いangular github issueスレッド https://github.com/angular/angular/issues/18586 #issuecomment-323216764

8
Martin Eckleben

プレーンテキストを受け取りたいだけの場合。ヘッダーなしでHttpオプションを設定できます。

this.http.get("http://localhost:3000/login",{responseType: 'text'})
.subscribe((result)=>console.log(result))
1
Joe

以下は、IEおよびchromeと互換性のある、blobをダウンロードするコンポーネントからの呼び出しです。

    this.subscribe(this.reportService.downloadReport(this.reportRequest, this.password), response => {
        let blob = new Blob([response], { type: 'application/Zip' });
        let fileUrl = window.URL.createObjectURL(blob);
        if (window.navigator.msSaveOrOpenBlob) {
            window.navigator.msSaveOrOpenBlob(blob, fileUrl.split(':')[1] + '.Zip');
        } else {
            this.reportDownloadName = fileUrl;
            window.open(fileUrl);
        }
        this.spinner = false;
        this.changeDetectorRef.markForCheck();
    },
    error => {
        this.spinner = false;
    });

以下は、応答タイプを「blob」に指定するサービスメソッドです。

downloadReport(reportRequest: ReportRequest, password: string): Observable<any> {
    let servicePath = `${basePath}/request/password/${password}`;
    this.httpOptions.responseType = 'blob';
    return this.endpointService.post(endpoint, servicePath, reportRequest, this.httpOptions);
}

以下は、httpClientを呼び出すコードです。

    //Make the service call:
    let obs = this.httpClient.request(method, url, options);
    //Return the observable:
    return obs;
0
Dilip Nannaware