在请求http.GET时发送Angular2 OPTIONS方法

ama*_*iny 45 http cors angular

我正在尝试为我的angular2应用添加基本身份验证.

public login() {
    // Set basic auth headers
    this.defaultHeaders.set('Authorization', 'Basic ' + btoa(this.username + ':' + this.password));

    console.log('username', this.username)
    console.log('password', this.password)
    console.log(this.defaultHeaders)

    // rest is copy paste from monbanquetapiservice
    const path = this.basePath + '/api/v1/development/order';        

    let req = this.http.get(path, { headers: this.defaultHeaders });
    req.subscribe(
        _ => { },
        err => this.onError(err)
    );
}
Run Code Online (Sandbox Code Playgroud)

我期望看到的是带有Authorization我放置的标题的GET请求.

但我看到的首先是带有此标题的OPTIONS:

OPTIONS /api/v1/development/order HTTP/1.1
Host: localhost:8080
Connection: keep-alive
Access-Control-Request-Method: GET
Origin: http://localhost:3000
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_3) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/49.0.2623.110 Safari/537.36
Access-Control-Request-Headers: authorization, content-type
Accept: */*
Referer: http://localhost:3000/
Accept-Encoding: gzip, deflate, sdch
Accept-Language: en-GB,en-US;q=0.8,en;q=0.6,fr;q=0.4
Run Code Online (Sandbox Code Playgroud)

由于我的服务器不允许此URL上的OPTIONS,我收到错误.

我知道像PUT或POST这样的方法首先发送一个OPTIONS方法来预检请求,但是GET没有.

为什么angular2的http首先发送一个OPTIONS?

谢谢.

Thi*_*ier 76

这是CORS的工作方式(使用跨域请求时).使用CORS,远程Web应用程序(此处是域mydomain.org)可以选择是否可以通过一组特定标头来提供请求.

CORS规范区分了两个不同的用例:

  • 简单的要求.如果我们使用HTTP GET,HEAD和POST方法,则此用例适用.对于POST方法,仅支持具有以下值的内容类型:text/plain,application/x-www-form-urlencoded和multipart/form-data.
  • 预先请求.当"简单请求"用例不适用时,会发出第一个请求(使用HTTP OPTIONS方法)来检查在跨域请求的上下文中可以执行的操作.

发送OPTIONS请求的是Angular2,而不是浏览器本身.这与Angular无关.

有关更多详细信息,您可以查看本文:

  • 我认为这是因为`Authorization`标题...因为它,你是在预检请求而不是简单请求的情况下. (9认同)
  • 我正在发送一个'GET`请求,但我仍然有这个预检.我知道PUT的预检,有时候是POST方法,但GET不应该有.这就是为什么我认为这是一个有点角色的东西,它增加了这个OPTIONS预检 (2认同)
  • 事实上,当你有一个自定义标题(不是由浏览器在引擎盖下发送的东西)时就是这种情况...... (2认同)
  • 如果您的内容类型不在上面的列表中,则GET请求也会使用预检,例如application / json。即使使用JSON源,我也通过使用文本/纯文字成功避免了OPTIONS请求。 (2认同)

Gün*_*uer 6

为什么我收到OPTIONS请求而不是GET请求?

这是由浏览器本身生成的CORS预检请求.

另请参阅
- 如何禁用OPTIONS请求?

需要将服务器配置为支持CORS请求,然后在GET请求后浏览器发送实际OPTIONS请求.

另请参阅
- "请求的资源上没有'Access-Control-Allow-Origin'标头" - https://developer.mozilla.org/en-US/docs/Web/HTTP/Access_control_CORS

访问控制允许的凭据

指示凭证标志为true时是否可以公开对请求的响应.当用作对预检请求的响应的一部分时,这指示是否可以使用凭证进行实际请求.请注意,简单的GET请求不是预检的,因此如果对具有凭据的资源发出请求,如果该资源未返回此标头,则浏览器将忽略响应,而不返回到Web内容.

  • 如果进行预检请求取决于某些标准.请参阅Thierry关于简单和预检请求的答案. (2认同)