一、简介

CORS(跨域资源共享 Cross-origin resource sharing)是实现跨域的一种常用方式。实现CORS通信的关键是服务器。只要服务器实现了CORS接口,就可以跨源通信

二、CORS的两种请求

(1)简单请求(simple request

(2)非简单请求(not-so-simple request)

简单请求必须同时满足以下两大条件:

1、请求方式是:GETPOSTHEAD中的一种

2、http请求头限制为这几种字段:AcceptAccept-LanguageContent-LanguageLast-Event-IDContent-Type:只限于三个值application/x-www-form-urlencoded(表单提交格式)multipart/form-data(文件上传格式)text/plain(纯文本格式)

凡是不同时满足上面两个条件,就属于非简单请求。

三、浏览器对简单请求的处理方式

对于简单请求,浏览器直接发出CORS请求。即在请求头信息之中,增加一个Origin字段(Origin字段用来说明,本次请求来自哪个源(协议 + 域名 + 端口))。

服务器通过Origin值来判断是否接受此次请求。

如果同意:则服务器返回响应

响应头会多出以下几个信息字段

Access-Control-Allow-Origin

Access-Control-Allow-Credentials

Content-Type: text/html

如果服务器拒绝:服务器会返回一个正常的HTTP回应(http状态吗有可能是200,所以无法通过状态码判断此类错误),响应头中不包含Access-Control-Allow-Origin字段,浏览器没有接收到Access-Control-Allow-Origin字段时就会抛出一个错误,被XMLHttpRequestonerror回调函数捕获。

四、浏览器对非简单请求的处理方式

非简单请求是那种对服务器有特殊要求的请求,比如请求方法是PUTDELETE,或者Content-Type字段的类型是application/json

CORS非简单请求会在正式通信之前,增加一次HTTP请求,称为“预检”请求。浏览器会先询问服务器,当前网页所在域名是否在服务器的许可名单之中,服务器允许之后,浏览器才会发出正式的XMLHttpRequest请求,否则会报错。

"预检"请求用的请求方法是OPTIONS,表示这个请求是用来询问的。

预检请求请求头一般包含这几个字段信息

1、Origin:   关键字段(必需),表示请求来自哪个源

2、Access-Control-Request-Method :该字段是必需的,用来列出浏览器的CORS请求会用到哪些HTTP方法

3、Access-Control-Request-Headers:该字段可选,是一个用逗号分隔的字符串,指定浏览器CORS请求会额外发送的请求头信息字段

预检请求的回应:

(1)服务器确认允许跨源请求

服务器做出相应的响应,返回的响应头信息中包含以下几项重要信息字段:

1、Access-Control-Allow-Origin(该字段是必需的。它的值要么是请求时Origin字段的值,要么是一个*,表示接受任意域名的请求。)

2、Access-Control-Allow-Methods(该字段必需,它的值是逗号分隔的一个字符串,表明服务器支持的所有跨域请求的方法)

3、Access-Control-Allow-Headers(如果浏览器请求包括Access-Control-Request-Headers字段,则Access-Control-Allow-Headers字段是必需的。它也是一个逗号分隔的字符串,表明服务器支持的所有头信息字段)

、Access-Control-Allow-Credentials(该字段可选。它的值是一个布尔值,表示是否允许发送Cookie。)

5、Access-Control-Max-Age(该字段可选,用来指定本次预检请求的有效期,单位为秒。)

一旦服务器通过了“预检”请求,以后每次浏览器正常的CORS请求,就都跟简单请求一样。

PS:如下两张图是“预检”请求和正式请求http的一些响应

图一、“预检”请求

图二、正式请求

(2)服务器不同意预检请求

如果浏览器否定了"预检"请求,会返回一个正常的HTTP回应,但是没有任何CORS相关的头信息字段。这时,浏览器就会报出以下错误:

XMLHttpRequest cannot load ...(这里是要访问的来源)

Origin ...(这里是要访问的来源) is not allowed by Access-Control-Allow-Origin.

CORS请求的更多相关文章

  1. 从零开始学 Java - Spring 支持 CORS 请求踩的坑

    谁没掉进过几个大坑 记得好久之前,总能时不时在某个地方看到一些标语,往往都是上面一个伟人的头像,然后不管是不是他说的话,下面总是有看起来很政治正确且没卵用的屁话,我活到目前为止,最令我笑的肚子痛得是下 ...

  2. 从零开始学 Java - Spring MVC 实现跨域资源 CORS 请求

    论职业的重要性 问:为什么所有家长都希望自己的孩子成为公务员? 答:体面.有权.有钱又悠闲. 问:为什么所有家长都希望自己的孩子成为律师或医生? 答:体面.有钱.有技能. 问:为什么所有家长都不怎么知 ...

  3. Java - Spring MVC 实现跨域资源 CORS 请求

    拦截器设置响应头 这种方式原理就是利用拦截器在方法执行前,我们增加请求的响应头,用来支持跨域请求.这种方案是可行的,大部分都是采用这种方案.我当时也是打算采用这种方案,直到我发现原来 Spring 框 ...

  4. Spring MVC 实现跨域资源 CORS 请求

    说到 AJAX 跨域,很多人最先想到的是 JSONP.的确,JSONP 我们已经十分熟悉,也使用了多年,从本质上讲,JSONP 的原理是给页面注入一个 <script>,把远程 JavaS ...

  5. Angular2,Springboot,Zuul,Shiro跨域CORS请求踩坑实录

    前言:前后端分离,业务分离,网关路由等已经成为当下web application开发的流行趋势.前端以单页面路由为核心的框架为主体,可以单独部署在nodejs或nginx上.后端以springboot ...

  6. Ajax操作如何实现跨域请求 (JSONP和CORS实现Ajax跨域的原理)

    由于浏览器存在同源策略机制,同源策略阻止ajax (XMLHttpRequest) 从一个源加载的文档或脚本获取或设置另一个源加载的文档的属性. 特别的:由于同源策略是浏览器的限制,所以请求的发送和响 ...

  7. 利用CORS实现跨域请求(转载)

    跨域请求一直是网页编程中的一个难题,在过去,绝大多数人都倾向于使用JSONP来解决这一问题.不过现在,我们可以考虑一下W3C中一项新的特性--CORS(Cross-Origin Resource Sh ...

  8. 解决ajax请求cors跨域问题

    ”已阻止跨源请求:同源策略禁止读取位于 ***** 的远程资源.(原因:CORS 头缺少 'Access-Control-Allow-Origin').“ ”已阻止跨源请求:同源策略禁止读取位于 ** ...

  9. Java实现CORS跨域请求

    问题 使用前后端分离模式开发项目时,往往会遇到这样一个问题 -- 无法跨域获取服务端数据 这是由于浏览器的同源策略导致的,目的是为了安全.在前后端分离开发模式备受青睐的今天,前端和后台项目往往会在不同 ...

随机推荐

  1. spring boot tomcat 线程数 修改初始线程数 统计性能 每百次请求耗时

    [root@f java]# tail -30 nohup.outsearchES-TimeMillisSpent:448P->1602@fT->http-nio-8080-exec-3t ...

  2. CSRF攻击详解(转)

    原文:http://www.django-china.cn/topic/580/ 一.CSRF是什么? CSRF(Cross-site request forgery),中文名称:跨站请求伪造,也被称 ...

  3. 'ascii' codec can't decode byte 0xc4 in position 27: ordinal not in range(128)

    This error happens when I try to run d:\linux\linuxkernel\android\内核\blog\BlogBackup(v1.1)source\htm ...

  4. 7.如何将python脚本打包为exe形式

    先安装pyinstaller,pip install pyinstaller 然后 pyinstaller -F combine.py打包即可

  5. linux创建新用户后shell无法自动补全命令或使用基本的shell命令

    新建一用户lqding,切换到该用户下 root@lqding:~# su - lqding$$ echo $USERlqding$ ^[[A 提示符仅仅是一个$,很奇怪.输入命令,用TAB键也无法补 ...

  6. 爬取51job职位信息之编码问题

    兴趣来潮,爬了下51job,但是遇到编码问题!以下是简单的一段代码 获取整个页面数据 # -*- coding:utf-8 -*- import requests import sysreload(s ...

  7. Mybatis使用generatedKey在插入数据时返回自增id始终为1,自增id实际返回到原对象当中的问题排查

    今天在使用数据库的时候,遇到一个场景,即在插入数据完成后需要返回此数据对应的自增主键id,但是在使用Mybatis中的generatedKey且确认各项配置均正确无误的情况下,每次插入成功后,返回的都 ...

  8. 按月、按日进行数据统计的Mysql语句

    <select id="getCustomerTJByUser" parameterType="map" resultType="map&quo ...

  9. 离线安装Cloudera Manager5.2.0和CDH5 2.0

    第一次安装出现了各种问题,尤其是对于不是太熟悉linux系统的更是头疼不已呀!特此记录一下,希望能够让小伙伴们少走点弯路. 1.给机器添加路由 (根据自己的机器情况,可以忽略)   route add ...

  10. HUE配置文件hue.ini 的zookeeper模块详解(图文详解)(分HA集群)

    不多说,直接上干货! 我的集群机器情况是 bigdatamaster(192.168.80.10).bigdataslave1(192.168.80.11)和bigdataslave2(192.168 ...