3_Vue中的跨域问题

1、同源策略

同源策略限制了从同一个源加载的文档或者脚本如何与另一个源的资源进行交互,用于隔离潜在恶意文件。

同源指的是:协议、域名、端口号必须一致

 

2、解决跨域问题

2.1 CORS

使用额外的HTTP头来告诉浏览器,被准许访问来自不同源服务器上的指定资源

 

 

 

2.2 JSONP

jsonp的原理就是利⽤<script> 标签没有跨域限制,通过<script> 标签src属性,发送带有callback参数的GET请求,服务端将接⼝返回数据拼凑到callback函数中,返回给浏览器,浏览器解析执⾏,从⽽前端拿到callback函数返回的数据。

2.2.1 原生js实现
 1 <script>
 2 var script = document.createElement('script');
 3 script.type = 'text/javascript';
 4 // 传参⼀个回调函数名给后端,⽅便后端返回时执⾏这个在前端定义的回调函数
 5 script.src = 'http://www.domain2.com:8080/login?
 6 user=admin&callback=handleCallback';
 7 document.head.appendChild(script);
 8 // 回调执⾏函数
 9 function handleCallback(res) {
10 alert(JSON.stringify(res));
11 }
12 </script>
View Code
2.2.2 vue axios实现
1 this.$http = axios;
2 this.$http.jsonp('http://www.domain2.com:8080/login', {
3 params: {},
4 jsonp: 'handleCallback'
5 }).then((res) => {
6 console.log(res);
7 })
View Code
2.2.3 缺点
  • 具有局限性, 仅⽀持get⽅法
  • 不安全,可能会遭受XSS攻击

2.3 postMessage跨域

postMessage是HTML5 XMLHttpRequest Level 2中的API,且是为数不多可以跨域操作的window属性之⼀,它可⽤于解决以下⽅⾯的问题:

  • ⻚⾯和其打开的新窗⼝的数据传递
  • 多窗⼝之间消息传递
  • ⻚⾯与嵌套的iframe消息传递
  • 上⾯三个场景的跨域数据传递

⽤法:postMessage(data,origin)⽅法接受两个参数:

data: html5规范⽀持任意基本类型或可复制的对象,但部分浏览器只⽀持字符串,所以传参时最
好⽤JSON.stringify()序列化。
origin: 协议+主机+端⼝号,也可以设置为"' ",表示可以传递给任意窗⼝,如果要指定和当前窗
⼝同源的话设置为"/"。

 1 <iframe id="iframe" src="http://www.domain2.com/b.html"
 2 style="display:none;"></iframe>
 3 <script>
 4 var iframe = document.getElementById('iframe');
 5 iframe.onload = function() {
 6 var data = {
 7 name: 'aym'
 8 };
 9 // 向domain2传送跨域数据
10 iframe.contentWindow.postMessage(JSON.stringify(data),
11 'http://www.domain2.com');
12 };
13 // 接受domain2返回数据
14 window.addEventListener('message', function(e) {
15 alert('data from domain2 ---> ' + e.data);
16 }, false);
17 </script>
1)a.html:(domain1.com/a.html)
 1 <script>
 2 // 接收domain1的数据
 3 window.addEventListener('message', function(e) {
 4 alert('data from domain1 ---> ' + e.data);
 5 var data = JSON.parse(e.data);
 6 if (data) {
 7 data.number = 16;
 8 // 处理后再发回domain1
 9 window.parent.postMessage(JSON.stringify(data),
10 'http://www.domain1.com');
11 }
12 }, false);
13 </script>
2)b.html:(domain2.com/b.html)

 

2.4 Nginx代理跨域

nginx代理跨域,实质和CORS跨域原理⼀样,通过配置⽂件设置请求响应头Access-Control-Allow-Origin…等字段。

nginx反向代理接⼝跨域

跨域问题:同源策略仅是针对浏览器的安全策略。服务器端调⽤HTTP接⼝只是使⽤HTTP协议,不需要同源策略,也就不存在跨域问题。


实现思路:通过Nginx配置⼀个代理服务器域名与domain1相同,端⼝不同)做跳板机,反向代理访问domain2接⼝,并且可以顺便修改cookie中domain信息,⽅便当前域cookie写⼊,实现跨域访问。

 

 1 #proxy服务器
 2 server {
 3 listen 81;
 4 server_name www.domain1.com;
 5 location / {
 6 proxy_pass http://www.domain2.com:8080; #反向代理
 7 proxy_cookie_domain www.domain2.com www.domain1.com; #修改cookie⾥域名
 8 index index.html index.htm;
 9 # 当⽤webpack-dev-server等中间件代理接⼝访问nignx时,此时⽆浏览器参与,故没有
10 同源限制,下⾯的跨域配置可不启⽤
11 add_header Access-Control-Allow-Origin http://www.domain1.com; #当前
12 端只跨域不带cookie时,可为*
13 add_header Access-Control-Allow-Credentials true;
14 }
15 }
View Code

 

2.5 nodejs 中间件代理跨域

node中间件实现跨域代理,原理⼤致与nginx相同,都是通过启⼀个代理服务器,实现数据的转发,也可以通过设置cookieDomainRewrite参数修改响应头中cookie中域名,实现当前域的cookie写⼊,⽅便接⼝登录认证。

2.5.1 非vue框架的跨域

2.5.2 vue框架的跨域

node + vue + webpack + webpack-dev-server搭建的项⽬,跨域请求接⼝,直接修改webpack.config.js配置。开发环境下,vue渲染服务和接⼝代理服务都是webpack-dev-server同⼀个,所以⻚⾯与代理接⼝之间不再跨域。

 1 module.exports = {
 2 entry: {},
 3 module: {},
 4 ...
 5 devServer: {
 6 historyApiFallback: true,
 7 proxy: [{
 8 context: '/login',
 9 target: 'http://www.domain2.com:8080', // 代理跨域⽬标接⼝
10 changeOrigin: true,
11 secure: false, // 当代理某些https服务报错时⽤
12 cookieDomainRewrite: 'www.domain1.com' // 可以为false,表示不修改
13 }],
14 noInfo: true
15 }
16 }
webpack.config.js部分配置:

2.6。。。待完成

 

posted @ 2022-03-08 16:48  踏燕白梅  阅读(214)  评论(0)    收藏  举报