Access-Control-Allow-Origin 标头如何工作? [英] How does Access-Control-Allow-Origin header work?

查看:51
本文介绍了Access-Control-Allow-Origin 标头如何工作?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

显然,我完全误解了它的语义.我想到了这样的事情:

Apparently, I have completely misunderstood its semantics. I thought of something like this:

  1. 客户端从 http://siteA - 下载 javascript 代码 MyCode.js.
  2. MyCode.js 的响应头包含 Access-Control-Allow-Origin: http://siteB,我认为这意味着 MyCode.js 被允许对站点 B 进行跨域引用.
  3. 客户端触发 MyCode.js 的某些功能,然后向 http://siteB 发出请求,尽管是跨域请求,但应该没问题.
  1. A client downloads javascript code MyCode.js from http://siteA - the origin.
  2. The response header of MyCode.js contains Access-Control-Allow-Origin: http://siteB, which I thought meant that MyCode.js was allowed to make cross-origin references to the site B.
  3. The client triggers some functionality of MyCode.js, which in turn make requests to http://siteB, which should be fine, despite being cross-origin requests.

好吧,我错了.它根本不是这样工作的.所以,我已经阅读了跨域资源共享并试图阅读w3c 推荐中的跨源资源共享

Well, I am wrong. It does not work like this at all. So, I have read Cross-origin resource sharing and attempted to read Cross-Origin Resource Sharing in w3c recommendation

有一件事是肯定的 - 我仍然不明白我应该如何使用这个标题.

One thing is sure - I still do not understand how am I supposed to use this header.

我对站点 A 和站点 B 拥有完全控制权.如何启用从站点 A 下载的 javascript 代码以使用此标头访问站点 B 上的资源?

I have full control of both site A and site B. How do I enable the javascript code downloaded from the site A to access resources on the site B using this header?

附言

我不想使用 JSONP.

I do not want to utilize JSONP.

推荐答案

Access-Control-Allow-Origin 是一个 CORS(跨源资源共享)标头.

当站点 A 尝试从站点 B 获取内容时,站点 B 可以发送一个 Access-Control-Allow-Origin 响应标头来告诉浏览器该页面的内容可被某些来源访问.(来源是一个域,加上方案和端口号.)默认情况下,站点B 的页面任何其他来源都无法访问;使用 Access-Control-Allow-Origin 标头为特定请求源的跨域访问打开了一扇门.

When Site A tries to fetch content from Site B, Site B can send an Access-Control-Allow-Origin response header to tell the browser that the content of this page is accessible to certain origins. (An origin is a domain, plus a scheme and port number.) By default, Site B's pages are not accessible to any other origin; using the Access-Control-Allow-Origin header opens a door for cross-origin access by specific requesting origins.

对于站点 B 想让站点 A 访问的每个资源/页面,站点 B 应为其页面提供响应标头:

For each resource/page that Site B wants to make accessible to Site A, Site B should serve its pages with the response header:

Access-Control-Allow-Origin: http://siteA.com

现代浏览器不会完全阻止跨域请求.如果站点 A 从站点 B 请求页面,浏览器实际上会在网络级别获取请求的页面,并检查响应标头是否将站点 A 列为允许的请求者域.如果站点 B 没有表明允许站点 A 访问此页面,浏览器将触发 XMLHttpRequesterror 事件并拒绝对请求的 JavaScript 代码的响应数据.

Modern browsers will not block cross-domain requests outright. If Site A requests a page from Site B, the browser will actually fetch the requested page on the network level and check if the response headers list Site A as a permitted requester domain. If Site B has not indicated that Site A is allowed to access this page, the browser will trigger the XMLHttpRequest's error event and deny the response data to the requesting JavaScript code.

在网络级别发生的事情可能比上面解释的稍微复杂.如果请求是 "non-simple"请求,浏览器首先发送一个无数据的预检"OPTIONS请求,以验证服务器是否会接受请求.当其中一个(或两者):

What happens on the network level can be slightly more complex than explained above. If the request is a "non-simple" request, the browser first sends a data-less "preflight" OPTIONS request, to verify that the server will accept the request. A request is non-simple when either (or both):

  • 使用 GET 或 POST 以外的 HTTP 动词(例如 PUT、DELETE)
  • 使用非简单的请求头;唯一的简单请求标头是:
    • 接受
    • 接受语言
    • 内容语言
    • Content-Type(只有在其值为 application/x-www-form-urlencodedmultipart/form-data 时才简单>, 或 text/plain)
    • using an HTTP verb other than GET or POST (e.g. PUT, DELETE)
    • using non-simple request headers; the only simple requests headers are:
      • Accept
      • Accept-Language
      • Content-Language
      • Content-Type (this is only simple when its value is application/x-www-form-urlencoded, multipart/form-data, or text/plain)

      如果服务器使用适当的响应标头(Access-Control-Allow-Headers 对于非简单标头,Access-Control-Allow-Methods)响应 OPTIONS 预检对于非简单动词)匹配非简单动词和/或非简单标头,然后浏览器发送实际请求.

      If the server responds to the OPTIONS preflight with appropriate response headers (Access-Control-Allow-Headers for non-simple headers, Access-Control-Allow-Methods for non-simple verbs) that match the non-simple verb and/or non-simple headers, then the browser sends the actual request.

      假设站点A想发送一个/somePage的PUT请求,带有一个非简单的Content-Typeapplication/json,浏览器会首先发送一个预检请求:

      Supposing that Site A wants to send a PUT request for /somePage, with a non-simple Content-Type value of application/json, the browser would first send a preflight request:

      OPTIONS /somePage HTTP/1.1
      Origin: http://siteA.com
      Access-Control-Request-Method: PUT
      Access-Control-Request-Headers: Content-Type
      

      注意Access-Control-Request-MethodAccess-Control-Request-Headers是浏览器自动添加的;您不需要添加它们.此 OPTIONS 预检获得成功的响应标头:

      Note that Access-Control-Request-Method and Access-Control-Request-Headers are added by the browser automatically; you do not need to add them. This OPTIONS preflight gets the successful response headers:

      Access-Control-Allow-Origin: http://siteA.com
      Access-Control-Allow-Methods: GET, POST, PUT
      Access-Control-Allow-Headers: Content-Type
      

      发送实际请求时(预检完成后),行为与处理简单请求的方式相同.换句话说,预检成功的非简单请求被视为与简单请求相同(即,服务器仍必须再次发送 Access-Control-Allow-Origin 以获得实际响应).

      When sending the actual request (after preflight is done), the behavior is identical to how a simple request is handled. In other words, a non-simple request whose preflight is successful is treated the same as a simple request (i.e., the server must still send Access-Control-Allow-Origin again for the actual response).

      浏览器发送实际请求:

      PUT /somePage HTTP/1.1
      Origin: http://siteA.com
      Content-Type: application/json
      
      { "myRequestContent": "JSON is so great" }
      

      服务器发回一个Access-Control-Allow-Origin,就像一个简单的请求一样:

      And the server sends back an Access-Control-Allow-Origin, just as it would for a simple request:

      Access-Control-Allow-Origin: http://siteA.com
      

      有关非简单请求的更多信息,请参阅了解基于 CORS 的 XMLHttpRequest.

      See Understanding XMLHttpRequest over CORS for a little more information about non-simple requests.

      这篇关于Access-Control-Allow-Origin 标头如何工作?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆