下有对策 - CORS

前言

虽然还没实际碰过 CORS 错误,但实在太好奇了,所以到处看了文章,得出两个感想:

  1. 查不到解法的时候就是要看规范了。CORS的规范:Fetch
  2. 需要由後端设定 Header 解决,前端则要了解基础概念和知道为什麽会发生问题

因此这篇文章不会针对个别 CORS 错误该如何解决做讨论,只会涵盖什麽时候会踩到这个雷以及初步认识请求的类型。

什麽时候会遇到 CORS


图片来源:MDN

以上图为例:这个网页的来源是http://domain-a.com,而网页中的 canvas 要向http://domain-b.com请求资源,这种跨来源的请求就会受到 CORS 的管控。

CORS 机制提供网页服务器跨来源的存取控制,具体方法是透过 HTTP-header 的设定,让网页服务器允许哪些来源可以存取它的资料

MDN 将请求类型分成三大类:简单请求、预检请求和带有身份验证(cookie)的请求,以下只先介绍前两类

简单请求

需要符合以下两个条件才算简单请求

  • 允许的请求方法:GETHEADPOST
  • 自定义的 Header 只允许以下几种:
    • Accept
    • Accept-Language
    • Content-Language
    • Content-Type 的内容只能是以下三种:
      • application/x-www-form-urlencoded
      • multipart/form-data
      • text/plain
    • 请求中不能包含 ReadableStream 物件
    • 如果以 XMLHttpRequest物件发送请求,不能在此物件上注册事件监听器


图片来源:JAVASCRIPT.INFO

对照上图我们来看看一个跨来源的简单请求会经历哪些步骤:

  1. JavaScript 使用 fetch() 请求跨来源的资源
  2. 浏览器确认请求方法及 Header 後,向服务器发送请求
  3. 服务器回传讯息和资源
  4. 浏览器确认回应中有包含Access-Control-Allow-Origin设有发送请求的来源*,允许JS读取资料,换句话说,如果没有设定就会发生CORS 错误

* 表示允许任何网域跨站存取资源

预检请求

MDN有详细列出哪些状况会被归类为预检请求,我目前倾向记只要是非简单请求都可以用预检请求的步骤去思考。

以下也用图示来理解预检请求过程


图片来源:JAVASCRIPT.INFO

  1. JavaScript 使用 fetch()
  2. 浏览器确认不是简单请求,所以必须以OPTIONS方法向服务器先发送讯息
  3. 服务器确认来源和请求方法,如果通过,服务器会传送状态码200 OK资料告知浏览器可以发送HTTP请求
  4. 浏览器正式发送HTTP请求
  5. 服务器确认请求来源,回传资料
  6. 浏览器确认回应中的Access-Control-Allow-Origin是否包含请求来源*

Access-Control-XXX 的部分一开始看觉得很可怕,但只要专注在後面的文字就好,会发现就是在注记哪些来源,方法或资料格式是被允许的

小结:

  • 遇到 CORS 错误先区分发送的请求是属於哪个类型
  • 可以观察到无论是哪一种请求,都需要有 Access-Control-Allow-Origin 这个 Header,浏览器才会将资源给 JavaScript 取用

参考资料:
MDN
JAVASCRIPT.INFO
CORS 完全手册
Deep Dive in CORS
CORS 是什麽? 如何设定 CORS?


<<:  [ Day 22 ] React 中的 State 管理 - Redux

>>:  [Day22] HTB Blue

Day 12:AWS是什麽?30天从动漫/影视作品看AWS服务应用 -《JoJo的奇妙冒险》第三季 part 2

希望前一日的吉良吉影解说还是够ㄎ一ㄤ,大家不要向大会检举有人在呼麻写文章QQ 虽说Jojo不相称的经...

连续 30 天 玩玩看 ProtoPie - Day 6

终於要从 Beginner 迈向 Intermediate 了。 这次的讲者讲话好清楚,转 1.75...

简单建立一个银行系统

创建你的钱包 一样,对比前面的match档,现在新增一个bank的json档案 回到bot档,现在我...

[Day08] Let's Build!

接续昨天提到的,我们今天将会实际跑一次指令,如果看到这里的你还在犹豫的话,别犹豫了,跟我一起开始吧!...

[DAY 21] 真实分数模型

还记得以前在大学修教程时有一门课 叫做「教育测验与评量」(简称「教测评」) 一直觉得那是一门很有趣也...