跨域
产生原因
同源策略是浏览器的一种安全策略,所谓同源是指域名,协议,端口完全相同,只有同源的地址才可以相互通过 AJAX 的方式请求。同源或者不同源说的是两个地址之间的关系,不同源地址之间请求我们称之为跨域请求,在没有做跨域请求处理的前提下,前端是无法获取响应内容的。
跨域解决方案
JSONP
JSON with Padding
,是一种借助于 script 标签发送跨域请求的技巧。其原理就是在客户端借助 script 标签请求服务端的一个url地址,服务端的这个动态网页返回一段带有函数调用的JavaScript
全局函数调用的脚本,将原本需要返回给客户端的数据传递进去。能实现的原因就是script标签的src属性不受同源策略影响的特性实现
客户端处理
<script src="http://api.zce.me/testJSONP?callback=receiveFn"></script>
服务端处理
receiveFn(['我', '是', '你', '原', '本', '需', '要', '的', '数', '据'])
JSONP问题
- 需要后端同学进行配合,服务端按照客户端的要求返回一段 JavaScript 调用客户端的函数
- 由于是通过src地址栏进行接口请求,只能发送GET类型请求,有参数数据大小的限制
- 不是一个真正的ajax请求
CORS
Cross Origin Resource Share
,跨域资源共享Cross Origin Resource Share,跨域资源共享,这种方案无需客户端作出任何变化(客户端不用改代码),整个CORS通信过程,都是浏览器自动完成,对于开发者来说,CORS通信与同源的AJAX通信没有差别,浏览器一旦发现AJAX请求跨源,就会自动添加一些附加的头信息,有时还会多出一次附加的请求,但用户不会有感觉,,只是在被请求的服务端响应的时候添加一个 AccessControl-Allow-Origin 的响应头,表示这个资源是否允许指定域请求。
cors的两种请求方式
-
简单请求 只要同时满足以下两大条件,就属于简单请求:
(1) 请求方法是以下三种方法之一: - HEAD - GET - POST (2)HTTP的头信息不超出以下几种字段: - Accept - Accept-Language - Content-Language - Last-Event-ID - Content-Type:只限于三个值 application/x-www-form-urlencoded、multipart/form-data、text/plain
-
非简单请求
非简单请求是那种对服务器有特殊要求的请求,比如请求方法是
PUT
或DELETE
,或者Content-Type
字段的类型是application/json
,非简单请求的CORS请求,会在正式通信之前,增加一次HTTP查询请求,称为"预检"请求(preflight)。浏览器先询问服务器,当前网页所在的域名是否在服务器的许可名单之中,以及可以使用哪些HTTP动词和头信息字段。只有得到肯定答复,浏览器才会发出正式的
XMLHttpRequest
请求,返回状态码204, 否则就报错,返回状态码405。
proxy代理
实现方法
本地开启代理服务器,前端代码在代理环境下进行开发,请求由代理服务器进行转发,服务器与服务器之间不涉及到跨域问题。
常见的代理方式
- liveServer => IDE的三方插件
- webpack devServer => 前端工程化构建工具
- nginx => nginx服务器代理
liveServer代理服务配置方法
- visual studio code 安装live-server插件
- 在设置中进行找到liveServer的配置项
- 添加proxy代理设置
- 选项信息: enable => 是否可使用代理,选择 true ; baseUri => 当前项目中的需要代理地址的基础路径 => proxyUri => 需要代理到哪一个服务器
- 选择完成之后,重新启动liveServer 实现代理成功
![image-20210410112817548](https://adminimg.hyfarsight.com/image-20210410112817548.png)
聊天室案例
Demo访问地址: https://test-1259079405.cos-website.ap-beijing.myqcloud.com
小练习
完成下列接口的数据器请求操作,接口有返回值的情况下,将返回值渲染到界面(使用fetch方法)
请求地址 | 请求方法 | 请求参数 | 响应值 | 是否支持跨域请求 |
---|---|---|---|---|
https://duyi.hyfarsight.com/test/study/lyrics | GET | 无 | {code :0,data:{lyrics:‘some string’}} | 是 (后端cors跨域) |
https://duyi.hyfarsight.com/test/study/userinfo | POST | 请求头:application/json 参数 : {name:string,age:number} // 为可选参数 | {code:0,data:{txt:anyString}} | 是(后端cors跨域) |
https://duyi.hyfarsight.com/test/study/jsonpInterface | JSONP | { callback : fn,name : string, age :string} callback为必须参数,参数值为前端创建的全局函数 其余参数为非必选参数 | {code : 0,data:{text : anyString}} | 否 前端需要使用JSONP形式进行测试 |
http://123.56.119.225:6006/test/proxy/testProxy | GET | 无 | {code:0,data:{txt:anyString}} | 否 前端需要时用proxy进行跨域处理 |
http://123.56.119.225:6006/test/proxy/testProxy | POST | 请求头:application/x-www-form-urlencoded 参数 : name=string&age=number // 为可选参数 | {code:0,data:{txt:anyString}} | 否 前端需要时用proxy进行跨域处理 |
判断下面的地址哪些是跨域的地址
基础路径:http://www.example.com/detail.html
对比路径: