Vue 使用proxy代理解决跨域问题

什么是跨域

首先,要明白什么是同源策略。同源就是指协议、域名、端口都要相同,其中任何一个不同都会出现跨域。例如:

http://www.baidu.com:8000
// http 是协议
// www.baidu.com 是域名
// 8000 是端口

跨域问题,是由浏览器的同源策略造成的,是浏览器对JavaScript实施的安全限制。

同源策略限制了以下行为

  1. 无法读取非同源网页的 Cookie、LocalStorage 和 IndexedDB
  2. 无法接触非同源网页的 DOM
  3. 无法向非同源地址发送 AJAX 请求

当我们开发完前端一个功能之后,需要进行调试 ,通常前后端分离情况下,两套程序都运行起来之后,肯定会出现协议、域名、端口不一致的形况。(H5运行在本地,后端代码又运行另外一台机器上)
那么前端调用后端接口时就会产生跨域问题。

跨域的解决方案

解决跨域的方案有很多,比如:jsonp、cors、Node代理、nginx反向代理。
vue中的proxy就是利用了Node代理。

vue proxy代理解决跨域

原理:通过请求本地的服务器,然后本地的服务器再去请求远程的服务器(后端部署接口的服务器),最后本地服务器再将请求回来的数据返回给浏览器(本地服务器和浏览器之前不存在跨域)

关键点在于:

  • 本地服务器(利用node.js创建的本地服务器进行代理,也叫代理服务器)和浏览器之间不存在跨域
  • 服务器和服务器之间不存在跨域

proxy配置

我们知道,前端axios在本地发送的请求如果你不把路径写全,它都是会默认加上自己项目所在的端口,就比如说:

axios.get(‘/login’)

当发送之后,以上代码实际请求为:

http://localhost:8080/login

其中 localhost:8080就是自己项目所在的地址了。实际前端就会根据以上的地址来访问后端程序了。

假如我现在想请求后端的 一个接口,例如:http://www.aaabbbccc.com/login,这样我们应该怎样配置代理服务器呢?以vue cli3.0为例:

// vue.config.js
  devServer: {
    
      //开启代理服务器
    proxy:{
    
    
      "/api": {
    
      // /api是自行设置的请求前缀,按照这个来匹配请求,有这个字段的请求,就会走到代理来。
          target: "http://www.aaabbbccc.com", // 需要代理的域名,目标域名,会替换掉匹配字段之前的路径
           ws: false, // 是否启用websockets
          changeOrigin: true, //控制服务器接收到的请求头中host字段的值
          /*
	      	changeOrigin设置为true时,服务器收到的请求头中的host为:localhost:5000
	      	changeOrigin设置为false时,服务器收到的请求头中的host为:localhost:3000
	      	changeOrigin默认值为false,但我们一般将changeOrigin值设为true
	      */
          pathRewrite: {
    
      //去除请求前缀,保证交给后台服务器的是正常请求地址(必须配置)
              "^/api": ""
          }
      },
   
  },
  }
 
  //vue cli2 .0 的放在 config文件夹中的index.js  中
    dev: {
    
    
    proxyTable:{
    
    
      "/api": {
    
    
          target: "http://www.aaabbbccc.com", // 需要代理的域名
           ws: false, // 是否启用websockets
          changeOrigin: true, //开启跨域
          pathRewrite: {
    
      //重写请求路径上匹配到的字段,如果不需要在请求路径上,重写为""
              "^/api": ""}
      },
  },
  }

以上配置中,我配置了一个 /api,只有包含这个请求的路径才会走代理,例如:

http://localhost:8080/api/login //这个就可以走代理
http://localhost:8080/login //这个就不行

可以看到,要想所有的请求都进入代理中,就必须包含/api这个路径,那么可以对axios进行二次封装,给所有的请求加这个前缀,代码如下:

const requests = axios.create({
    
    

  baseURL:'/api', // 设置通用请求的地址前缀
  timeout:10000  //请求超时的时间
  
});
export default requests  //将requests实例,对外进行暴露

发送请求可以写为:

requests.get('/login').then((response) => {
    
    })
requests.get('/getlist').then((response) => {
    
    })
requests.get('/user/hello').then((response) => {
    
    })

此时发送的请求就是:

http://localhost:8080/api/login
http://localhost:8080/api/getlist
http://localhost:8080/api/user/hello

通过代理的target属性加工之后就是:

http://www.aaabbbccc.com/api/login
http://www.aaabbbccc.com/api/getlist
http://www.aaabbbccc.com/api/user/hello

就是把/api 之前的路径修改成了target里配置的目标服务器的路径。
在通过pathRewrite属性将/api 替换为空为:

http://www.aaabbbccc.com/login
http://www.aaabbbccc.com/getlist
http://www.aaabbbccc.com/user/hello

这样就可以访问到后端的对应接口了。

猜你喜欢

转载自blog.csdn.net/qq_36162336/article/details/130561308