前端基础技术_跨域资源共享(Cross-origin resource sharing)CORS

原文地址:https://blog.csdn.net/badmoonc/article/details/82706246

简介

CORS:全称"跨域资源共享"(Cross-origin resource sharing)。

CORS需要浏览器和服务器同时支持,才可以实现跨域请求,目前几乎所有浏览器都支持CORS,IE则不能低于IE10。CORS的整个过程都由浏览器自动完成,前端无需做任何设置,跟平时发送ajax请求并无差异。so,实现CORS的关键在于服务器,只要服务器实现CORS接口,就可以实现跨域通信。

请求类型:

CORS分为简单请求和非简单请求(需预检请求)两类

符合以下条件的,为简单请求

 
  1. 请求方式使用下列方法之一:

  2. GET

  3. HEAD

  4. POST

  5.  
  6. Content-Type 的值仅限于下列三者之一:

  7. text/plain

  8. multipart/form-data

  9. application/x-www-form-urlencoded

对于简单请求,浏览器会直接发送CORS请求,具体说来就是在header中加入origin请求头字段。同样,在响应头中,返回服务器设置的相关CORS头部字段,Access-Control-Allow-Origin字段为允许跨域请求的源。请求时浏览器在请求头的Origin中说明请求的源,服务器收到后发现允许该源跨域请求,则会成功返回,具体如下:

在这里,http://localhost:3001为我们当前发送请求的源,如果服务器发现请求在指定的源范围内,则会返回响应的请求结果, 否则会在控制台报错,如下图所示,在这里需要注意的是,尽管请求失败,但返回的状态码依然可能为200。所以在做处理时需要格外注意。

非简单请求(预检请求)

 
  1. 使用了下面任一 HTTP 方法:

  2. PUT

  3. DELETE

  4. CONNECT

  5. OPTIONS

  6. TRACE

  7. PATCH

  8.  
  9. Content-Type 的值不属于下列之一:

  10. application/x-www-form-urlencoded

  11. multipart/form-data

  12. text/plain

当发生符合非简单请求(预检请求)的条件时,浏览器会自动先发送一个options请求,如果发现服务器支持该请求,则会将真正的请求发送到后端,反之,如果浏览器发现服务端并不支持该请求,则会在控制台抛出错误,如下:

如果非简单请求(预检请求)发送成功,则会在头部多返回以下字段

 
  1. Access-Control-Allow-Origin: http://localhost:3001 //该字段表明可供那个源跨域

  2. Access-Control-Allow-Methods: GET, POST, PUT // 该字段表明服务端支持的请求方法

  3. Access-Control-Allow-Headers: X-Custom-Header // 实际请求将携带的自定义请求首部字段

下图为一个预检请求实例:

红框标注的为预检请求发送的查询,服务端支持我们的请求后,将会发送我们真正的请求,图中绿框所示。可以看到,真正的请求响应头字段多处蓝框中所圈字段。这为服务器所支持cors请求类型和允许的自定义请求首部字段,以及支持跨域的源。

实例代码

前端代码与发送普通请求没有差异,我们只需在服务端设置即可,以node为例:

 
  1. var express = require('express');

  2. var app = express();

  3. var allowCrossDomain = function (req, res, next) {

  4. res.header('Access-Control-Allow-Origin', 'http://localhost:3001');

  5. res.header('Access-Control-Allow-Methods', 'GET,PUT,POST,DELETE');

  6. res.header('Access-Control-Allow-Headers', 'Content-Type');

  7. next();

  8. }

  9. app.use(allowCrossDomain);

接下来,http://localhost:3001下的GET,PUT,POST,DELETE请求,自定义首部字段为Content-Type的非简单请求则会被正常访问,当然,你也可以将Access-control-Allow-Methods和Access-Control-Allow-Headers这两个配置删掉,删掉之后,将仅支持简单请求进行跨域。

CORS字段介绍:

(1)Access-Control-Allow-Methods

该字段必需,它的值是逗号分隔的一个字符串,表明服务器支持的所有跨域请求的方法。注意,返回的是所有支持的方法,而不单是浏览器请求的那个方法。这是为了避免多次"预检"请求。

(2)Access-Control-Allow-Headers

如果浏览器请求包括Access-Control-Request-Headers字段,则Access-Control-Allow-Headers字段是必需的。它也是一个逗号分隔的字符串,表明服务器支持的所有头信息字段,不限于浏览器在"预检"中请求的字段。

(3)Access-Control-Allow-Credentials

该字段与简单请求时的含义相同。

(4)Access-Control-Max-Age

该字段可选,用来指定本次预检请求的有效期,单位为秒。上面结果中,有效期是20天(1728000秒),即允许缓存该条回应1728000秒(即20天),在此期间,不用发出另一条预检请求。

总结:

总的来说,使用CORS简单请求,非常容易,对于前端来说无需做任何配置,与发送普通ajax请求无异。唯一需要注意的是,需要携带cookie信息时,需要将withCredentials设置为true即可。CORS的配置,完全在后端设置,配置起来也比较容易,目前对于大部分浏览器兼容性也比较好。CORS优势也比较明显,可以实现任何类型的请求,相较于JSONP跨域只能使用get请求来说,也更加的便于我们使用。关于jsonp跨域请求的实现,可以参照作者的另外一篇文章jsonp跨域原理

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值