表现
XMLHttpRequest,Fetch API 等限制了不同域之间的数据调用.
原因
跨域的直接原因是浏览器的同源策略限制, 根本原因还是基于安全的考虑.
跨域本身就是浏览器端进行的限制, 我们设置可以通过更改浏览器的设置来关闭跨域限制, 但是不推荐关闭
常见解决方法及优缺点
JSONP
jsonp 的本质是通过不受同源策略限制的 script 标签加载数据 (其实是 js 代码), 用在页面中实现定义好一个处理函数处理数据, 它用这样的方式绕过了同源策略.
- <script src="http://xxx//xxx.js?callback=callback"></script>
- // js 文件中的内容
- callback({"name":"我是数据"});
- function callback (data) {
- // 拿到数据
- var name = data.name;
- }
优点:
简单
缺点:
需要接口支持才行
只支持 get 方式
因为 url 长度限制, 所以 jsonp 也不能传输太多数据
不能设置请求头, 毕竟是借助 script 标签请求数据, 没办法随意的设置请求头
CORS
跨域资源共享
可以参考:
MDN-HTTP 访问控制 (CORS) https://developer.mozilla.org/zh-CN/docs/web/HTTP/Access_control_CORS
阮一峰老师的博文 - 跨域资源共享 CORS 详解 http://www.ruanyifeng.com/blog/2016/04/cors.html
- // 设置允许跨域的域名
- header('Access-Control-Allow-Origin', 'xxx');
- // 是否允许带上认证信息 (httpAuth,cookie)
- header('Access-Control-Allow-Credentials', true);
- // 设置允许带上的响应头
- header('Access-Control-Expose-Headers', 'xxx');
- // 设置允许带上的请求头
- header('Access-Control-Request-Headers', 'xxx');
- // 设置允许的请求方法
- header('Access-Control-Request-Method', 'GET,POST,PUT,DELETE,OPTIONS');
- var xhr = new XMLHttpRequest();
- // 我要带上认证信息
- xhr.withCredentials = true;
非简单请求会事先发送一个 OPTIONS 请求确认是否允许跨域
兼容性说明 https://caniuse.com/#search=cors
优点:
支持所有请求方式
支持设置请求头
缺点:
需要服务端在响应头中添加字段
对请求头和相应头都有限制
存在兼容性的问题
限制了 httpAuth,cookie, 需要配置 xhr 对象和响应头
使用辅助手段代理成同域
使用 nginx 反向代理不同域的接口, 转换成同域的接口.
如果不使用反向代理, 也可以直接后端写代码去请求接口后返回给前端, 原理和反向代理相同.
优点:
请求同域, 想怎么玩就怎么玩.
缺点:
需要维护代理
来源: https://juejin.im/entry/5b5b4ab051882519a42691ed