美文网首页xzf_vue前端编程
Vue-cli proxyTable 解决开发环境的跨域问题

Vue-cli proxyTable 解决开发环境的跨域问题

作者: almon123 | 来源:发表于2016-07-11 15:33 被阅读95371次

和后端联调时总是会面对恼人的跨域问题,最近基于Vue开发项目时也遇到了这个问题,两边各自想了一堆办法,查了一堆资料,加了一堆参数,最后还得我把自己的localhost映射成上线时将要使用的域名。
今天翻看代码时,突然发现vue-cli的config文件里有一个参数叫proxyTable,看这个名字就感觉能解决问题,于是我就去搜了一下,果然。在vuejs-templates,也就是vue-cli的使用的模板插件里,有关于API proxy的说明,使用的就是这个参数。
https://vuejs-templates.github.io/webpack/proxy.html
这个参数主要是一个地址映射表,你可以通过设置将复杂的url简化,例如我们要请求的地址是api.xxxxxxxx.com/list/1,可以按照如下设置:

proxyTable: {
  '/list': {
    target: 'http://api.xxxxxxxx.com',
    pathRewrite: {
      '^/list': '/list'
    }
  }
}

这样我们在写url的时候,只用写成/list/1就可以代表api.xxxxxxxx.com/list/1.
那么又是如何解决跨域问题的呢?其实在上面的'list'的参数里有一个changeOrigin参数,接收一个布尔值,如果设置为true,那么本地会虚拟一个服务端接收你的请求并代你发送该请求,这样就不会有跨域问题了,当然这只适用于开发环境。增加的代码如下所示:

proxyTable: {
  '/list': {
    target: 'http://api.xxxxxxxx.com',
    changeOrigin: true,
    pathRewrite: {
      '^/list': '/list'
    }
  }
}

vue-cli的这个设置来自于其使用的插件http-proxy-middleware
github:https://github.com/chimurai/http-proxy-middleware
深入了解的话可以看该插件配置说明,似乎还支持websocket,很强大的插件。

相关文章

网友评论

  • 天晴_675f:config/index.js:
    proxyTable: {
    '/mock':{
    target: 'https://easy-mock.com',
    changeOrigin: true,
    secure: false //接受运行在https上的服务
    }
    }
    home.vue:
    this.$axios.get('/mock/5a27ff63817b456c2ecd0cc0/example/user')
    .then((response)=>{
    console.log(response)
    })
    .catch((error)=>{
    console.log(error)
    })
    我用axios发布请求,但是代理失败,会请求到本地,请问是什么原因啊
    于美美:我也是这个问题,请问你解决了么
  • _执着执着再执着:您好,我发现文章有些问题.
    您这里原话是 "这样我们在写url的时候,只用写成/list/1就可以代表api.xxxxxxxx.com/list/1."
    而官方文档写的是 "上面的示例将代理请求/api/posts/1到http://jsonplaceholder.typicode.com/posts/1。"
    下面是官方文档地址(您文章提供的地址)
    https://vuejs-templates.github.io/webpack/proxy.html
    _执着执着再执着:@檀木木_5f26 恩呢,后面我又仔细琢磨了。专门写了篇关于这个路径重写的文章
    e55bac50e34d:作者写的没有问题,官方文档 那个pathRewrite(路径重写命令)是个空字符串,而作者加上了/list,这也就说明为什么 /list/1 代表 api.xxxxxxxx.com/list/1 而不是api.xxxxxxxx.com/1
  • 982a7b182299:你好,我如果在本地开发完整的前后端代码的话,是不是把vue代码打包到后端端口目录下,然后axios请求地址是不是写例如: http://127.0.0.1:81/admin/index这样的完整地址,然后把http://127.0.0.1:81/这个写在一个变量里,拼接url请求地址,如果是在实际生产环境下,就把这个变量改成实际域名这样啊? 意思是这个变量是要手动修改的 我理解的对吗?
  • a181cb6fa99d:webpack-dev-server 本地服务代理不就可以么
  • CJ_景元:感谢。问题解决了
    CJ_景元:@Z_96a4 有没有试过重新设置后,重新npm run dev?我重启就好了
    87567b673a27:怎么解决的 依然是localhost+/***
  • 痛并快乐着_0270:为什么那个target填什么指都对最终的请求链接没什么影响啊,求解!!!
    proxyTable: {
    '/AutomotiveTechnology': {
    target: 'http://localhost:80',
    changeOrigin: true,
    pathRewrite: {
    '^/AutomotiveTechnology': '/AutomotiveTechnology'
    }
    }
    }
  • bca3e3da31f0:proxyTable: {
    '/v2': {
    target: 'https://api.douban.com/',
    changeOrigin: true,
    pathRewrite: {
    '^/v2': ''
    }
    }
    }
    然后请求这样写得
    axios.get('/v2/loc/list').then(function (response) {
    console.log(response)
    }
    就是不生效,走过路过,谁知道的麻烦指点一下
    阿布_0caf:确保配置都正确,然后npm run dev 重新运行,我找了好几个小时的问题,重新运行就正常了
    bca3e3da31f0:@B1an_c9ba 我的可以了,我是因为安装了别的模块
    8cc8722c6e46:请问问题解决了吗?刚好遇到这个问题
  • Awesome199:post方法能不能用?
    c1c62c876a3d:@我不是你的entourage 图片转码后上传吧 我这边是post后台接收不到参数 现在还没搞明白
    Awesome199: @c1c62c876a3d 对的,Vue中如何post上传图片
    c1c62c876a3d:你用post遇到问题了吗
  • 半块:Good!
  • 就这个头:还是有问题,请求是返回200了,但是返回的数据没有了,返回的是500
  • 就这个头:非常感谢,帮了我大忙
  • 6bfe1a0ee742:楼主加个联系方式,我按照你的这种方法还是不可以
  • 6bfe1a0ee742:Vue.http.get('/auction.php/Jigou/indexlist').then(function (res) {
    commit('auction', res.body)
    })
  • 6bfe1a0ee742: proxyTable: {
    '/api': {
    target: 'http://172.16.0.111',
    changeOrigin: true,
    pathRewrite: {
    '/api': '/api'
    }
    }
  • 6bfe1a0ee742:我也是这么配置的 我请求数据,我的还是localhost::8080/auction.php 为什么 配置没有用呢?
    4af57de0ca8b:你的解决了吗
    照松林:你这个好了吗?请问
  • demo11:proxyTable: {
    '/list': {
    target: 'http://api.xxxxxxxx.com',
    pathRewrite: {
    '^/list': '/list'
    }
    }
    }有谁可以解答下,proxyTable对象中的各个属性的意思吗?如上 '/list'对象是什么意思,对象中target,changOrigin, pathRewrite各代表什么?

    我的是这么写的
    proxyTable: {
    '/notes':{
    target: 'http://www.jianshu.com/notes',
    changeOrigin: true,
    pathRewrite: {
    '^/notes': '/notes'
    }
    }
    },

    created:function(){
    this.$http.get('/notes/4749551/side_tool').then((response)=>{
    console.log(response,'111');
    })
    }
    现在是报404,,然后我把target中的/notes去掉就正常了,但是我不知道为什么是这样?
    我的理解是第一个/notes代表的不是代表target中的值?这是实际访问的地址http://www.jianshu.com/note/4749551/side_tool,那么/notes代表的是http://www.jianshu.com,那么访问的时候不是改写成/note/note/4749551/side_tool?但是现在反而是写成/note/4749551/side_tool是对的,但是这样写的话,不是少了一个notes吗?
    e55bac50e34d:说白就是将对应的字符串替换成target属性,
    pathRewrite这个属性 中的 ‘^/notes’ 代表的一个正则表达式,也就是说以/notes开始的位置会重写一个/notes, 要是 target 属性为 'http://www.jianshu.com/notes' 而请求路径为'/notes/4749551/side_tool' 这样的话实际请求地址为http://www.jianshu.com/notes/notes/4749551/side_tool
  • 后知不觉1:如果需要权限登录的情况这时候该怎么办,用的是cookie验证
    2bf21534a0bc:@后知不觉1 具体是怎么弄的呢? 代码可以看一下吗?
    后知不觉1:@尘一粒 后来解决了。在proxyTable中模拟请求头,将cookie添加到到请求头中,不过在Referer中不能写http这个,直接写代理的网址不要http字符
    21628a45b880:用楼主说的第一种方法,并用fetch发送请求
  • 50903fb8d424:想知道用于生产环境不同域名的情况下该怎么办~
    cnlinjie:这只是开发环境下的,生产环境直接将构建出来的代码给后端啊 。
    73fcbe2764cd:跨域啊。。。
  • 85d98a7ce71e:为什么我请求 成功了200 但是返回的数据里面是空的,我在其他post接口网站上测试时有数据的
    Cara_ff6a:@小良苏_e167 我现在也是遇到这个问题,请问是怎么解决的啊
    小良苏_e167:@Arey_67db 亲,你是怎么解决的呀,我也是这样的问题,要急死了
  • zz5207:var proxyMiddleware = require('http-proxy-middleware');
    //拦截一切/api的请求,后台代理获取数据,返回到前端
    var proxyTable = {
    '/api': {
    target: 'http://112.74.127.99:5000/api/index',
    changeOrigin: true,
    pathRewrite: {
    '^/api': '/api'
    }
    }
    };
    Object.keys(proxyTable).forEach(function (context) {
    var options = proxyTable[context]
    if (typeof options === 'string') {
    options = { target: options }
    }
    app.use(proxyMiddleware(context, options))
    })

    我这么写的为什么会有cart.js:6 Uncaught ReferenceError: require is not defined这种错误
    8c5e767eaa6a:感谢
    解决了困扰我一天一夜的问题
  • c33dd4b8f193:真正发布到线上环境的代码里,请求的url会不会缺了主域名呢?
    almon123:@邹毅锋 哦,如果你的项目前后端位于同一台服务器上,就不需要做任何修改。当然这时候线上环境也不会有跨域问题,所以我估计你问这个问题,你线上环境也是跨域的。如果是这样的话,其实你可以设置一个全局的域名前缀。比如
    ``` javascript
    const DEBUG_MODE = true
    const URL_PREFIX = DEBUG_MODE ? ' ' : ' http://xxx.com'
    ```
    开发环境下前缀为空,生产环境下为你需要的域。然后请求的时候拼接字符串
    ``` javascript
    `${URL_PREFIX}/api/xxx`
    ```
    就可以了。
    c33dd4b8f193:@almon123 嗯嗯,但线上环境不是一般都写完整的请求url吗?但这里写成局部的,利用插件替换成完整的url(/list --> http://xxx.com/list)。真正发布到线上环境需要做什么样的处理吗?:smile:
    almon123:这个插件不会在线上环境生效的.只是给开发时使用.
  • 9e21ec37a677:楼主,我这样配置了参数:
    proxyTable: {
    '/movie': {
    target: 'https://api.douban.com/v2/',
    changeOrigin: true,
    pathRewrite: {
    '^movie': '/movie'
    }
    }
    还是不能请求到数据,这是为什么,求解答?
    d59b988c7ebb:请问一下这个问题你是怎么解决的?我也是遇到了这样的问题,不是很懂
    9e21ec37a677:@almon123 恩,现在可以了,谢谢!:smile:
    almon123:我试了一下,可以啊,这个请求本身状态是404,但是数据是能返回的,你在地址栏输入localhost:8080/movie会跳转到豆瓣的404页面.
  • fanxl12:楼主,为什么,我设置了没有用呢?
  • Nicholasway:请问https的代理设置过吗?
  • 三年五班:只能代理localhost地址吗,我把localhost改成ip地址访问就不行了,报错:XMLHttpRequest cannot load http://localhost:7070/api/1.0/web/login. Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://172.16.1.236:7070' is therefore not allowed access. The response had HTTP status code 403.
    TaoBeier:@Sunshine_6a14 跨域而已。 后端加个 `Access-Control-Allow-Origin` 头就可以了
    TaoBeier:跨域而已。 后端加个 `Access-Control-Allow-Origin` 头就可以了
    Sunshine_6a14:你的问题解决了吗?也遇到了同样的问题
  • www000:不错。谢谢
  • v魂之挽歌:非常感谢!困扰了我好久~

本文标题:Vue-cli proxyTable 解决开发环境的跨域问题

本文链接:https://www.haomeiwen.com/subject/xzhjjttx.html