【问题标题】:Add a custom header to Aurelia Fetch request向 Aurelia Fetch 请求添加自定义标头
【发布时间】:2017-11-06 10:27:05
【问题描述】:

我正在尝试使用 Aurelia 的 Fetch Client 向所有 GET 和 POST 请求添加自定义标头。以下代码(在 app.js 构造函数中)用于设置基本 URL,但标头没有按我想要的方式工作:

constructor(httpClient) {
  // set up httpClient
  httpClient.configure(config => {
    config
      .withBaseUrl(localsettings.api)
      .withDefaults({
        credentials: 'include',
        headers: {
          'my_appkey': 'f2eabc5e7de-a4cdc857e'
        }
      })
  });
  this.httpClient = httpClient;
}

用法:

this.httpClient.fetch(suburl, {
    credentials: 'include'
  }).then(response => { ... });

通过 Chrome 的开发工具,我可以看到“my_appkey”标头存在,但它没有被创建,因为它是自己的标头,并且它的值不可见:

请求标头:

OPTIONS /index.php/api/v1/keys HTTP/1.1
Host: localhost:8080
Connection: keep-alive
Access-Control-Request-Method: GET
Origin: http://localhost:9000
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.36
Access-Control-Request-Headers: my_appkey
Accept: */*
Referer: http://localhost:9000/
Accept-Encoding: gzip, deflate, sdch, br
Accept-Language: en-US,en;q=0.8,es-419;q=0.6,es;q=0.4

我做错了什么?为什么我的自定义标头被移动到Access-Control-Request-Headers

【问题讨论】:

    标签: javascript cors aurelia fetch-api


    【解决方案1】:

    my_appkey 标头添加到请求会触发浏览器首先执行a CORS preflight OPTIONS request,然后再尝试您要发出的实际GET/POST 请求。

    OPTIONS /index.php/api/v1/keys HTTP/1.1
    ^^^^^^^
    

    作为预检OPTIONS 的一部分,浏览器会发送一个Access-Control-Request-Headers header,其值包括您从代码添加到请求的标头名称。

    在发出预检请求时使用 Access-Control-Request-Headers 请求标头,以让服务器知道在发出实际请求时将使用哪些 HTTP 标头。

    所以你看到的都是预期的行为。

    为了让浏览器认为预检OPTIONS 请求成功,发出请求的服务器必须发送一个包含Access-Control-Allow-Headers response header 的响应,该Access-Control-Allow-Headers response header 的值还包括“my_appkey”。如果没有,则浏览器会停在那里,永远不会继续发送您想要发出的实际 GET/POST 请求。

    【讨论】:

    • 因此,分析这一点,也许添加自定义标头不是最好的方法,因为它会减慢请求(似乎预检请求会增加更多延迟)。什么是通过所有请求传递 appkey 的更快方法?只是把它作为身体的一部分?
    • 是的,如果您想避免额外的请求,我想将 appkey 作为请求正文的一部分而不是标头发送将是最简单的方法。也就是说,如果您真的想要快速,您可以将您的应用代码托管在与 API 端点相同的服务器/源上
    • 如果它们托管在同一个子域(例如 myapp.school.edu)上,那么 fetch 将发送标头而不需要进行预检请求?
    • 是的,如果它们托管在同一个源(方案 + 主机 + 端口)上,那么它就不是跨域请求,因此浏览器不会施加任何跨域限制,并且根本不会使用 CORS 协议——这意味着即使不需要 Access-Control-Allow-Origin 响应标头,请求也会成功。
    猜你喜欢
    • 2012-11-15
    • 2013-11-13
    • 2021-08-25
    • 2015-12-18
    • 1970-01-01
    • 1970-01-01
    • 2015-10-02
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多