详解vue或uni-app的跨域问题解决方案


Posted in Javascript onFebruary 21, 2020

常见解决方案有两种

服务器端解决方案

服务器告诉浏览器:你允许我跨域

具体如何告诉浏览器,请看:

// 告诉浏览器,只允许 http://bb.aaa.com:9000 这个源请求服务器
$response->header('Access-Control-Allow-Origin', 'http://bb.aaa.com:9000');
// 告诉浏览器,请求头里只允许有这些内容
$response->header('Access-Control-Allow-Headers', 'Authorization, Content-Type, Depth, User-Agent, X-File-Size, X-Requested-With, X-Requested-By, If-Modified-Since, X-File-Name, X-File-Type, Cache-Control, Origin');
// 告诉浏览器,只允许暴露'Authorization, authenticated'这两个字段
$response->header('Access-Control-Expose-Headers', 'Authorization, authenticated');
// 告诉浏览器,只允许GET, POST, PATCH, PUT, OPTIONS方法跨域请求
$response->header('Access-Control-Allow-Methods', 'GET, POST, PATCH, PUT, OPTIONS');
// 预检
$response->header('Access-Control-Max-Age', 3600);

将以上代码写入中间件:

// /app/Http/Middleware/Cors.php
<?php
namespace App\Http\Middleware;

use Closure;
use Illuminate\Http\Response;
class Cors {

  /**
   * Handle an incoming request.
   *
   * @param \Illuminate\Http\Request $request
   * @param \Closure $next
   * @return mixed
   */
  public function handle($request, Closure $next)
  {
    $response = $next($request);
    // 告诉浏览器,只允许 http://bb.aaa.com:9000 这个源请求服务器
    $response->header('Access-Control-Allow-Origin', 'http://bb.aaa.com:9000');
    // 告诉浏览器,请求头里只允许有这些内容
    $response->header('Access-Control-Allow-Headers', 'Authorization, Content-Type, Depth, User-Agent, X-File-Size, X-Requested-With, X-Requested-By, If-Modified-Since, X-File-Name, X-File-Type, Cache-Control, Origin');
    // 告诉浏览器,只允许暴露'Authorization, authenticated'这两个字段
    $response->header('Access-Control-Expose-Headers', 'Authorization, authenticated');
    // 告诉浏览器,只允许GET, POST, PATCH, PUT, OPTIONS方法跨域请求
    $response->header('Access-Control-Allow-Methods', 'GET, POST, PATCH, PUT, OPTIONS');
    // 预检
    $response->header('Access-Control-Max-Age', 3600);
    return $response;
  }

}

在路由上添加跨域中间件,告诉客户端:服务器允许跨域请求

$api->group(['middleware'=>'cors','prefix'=>'doc'], function ($api) {
  $api->get('userinfo', \App\Http\Controllers\Api\UsersController::class.'@show');
  
})

客户器端解决方案

欺骗浏览器,让浏览器觉得你没有跨域(其实还是跨域了,用的是代理)

在manifest.json里添加如下代码:

// manifest.json
"devServer" : {
  "port" : 9000,
  "disableHostCheck" : true,
  "proxy": {
    "/api/doc": {
      "target": "http://www.baidu.com",
      "changeOrigin": true,
      "secure": false
    },
    "/api2": {
     .....
    }
  },
  
},

参数说明

'/api/doc'

捕获API的标志,如果API中有这"/api/doc"个字符串,那么就开始匹配代理,
比如API请求"/api/doc/userinfo",
会被代理到请求 "http://www.baidu.com/api/doc"
即:将匹配到的"/api/doc"替换成"http://www.baidu.com/api/doc"
客户端浏览器最终请求链接表面是:"http://192.168.0.104:9000/api/doc/userinfo",
实际上是被代理成了:"http://www.baidu.com/api/doc/userinfo"去向服务器请求数据

target

代理的API地址,就是需要跨域的API地址。
地址可以是域名,如:http://www.baidu.com
也可以是IP地址:http://127.0.0.1:9000
如果是域名需要额外添加一个参数changeOrigin: true,否则会代理失败。

pathRewrite

路径重写,也就是说会修改最终请求的API路径。
比如访问的API路径:/api/doc/userinfo,
设置pathRewrite: {'^/api' : ''},后,
最终代理访问的路径:"http://www.baidu.com/doc/userinfo",
将"api"用正则替换成了空字符串,
这个参数的目的是给代理命名后,在访问时把命名删除掉。

changeOrigin

这个参数可以让target参数是域名。

secure

secure: false,不检查安全问题。
设置后,可以接受运行在 HTTPS 上,可以使用无效证书的后端服务器

其他参数配置查看文档
https://webpack.docschina.org/configuration/dev-server/#devserver-proxy

请求封装

uni.docajax = function (url, data = {}, method = "GET") {
 return new Promise((resolve, reject) => {
  var type = 'application/json'
  if (method == "GET") {
   if (data !== {}) {
    var arr = [];
    for (var key in data) {
     arr.push(`${key}=${data[key]}`);
    }
    url += `?${arr.join("&")}`;
   }
   type = 'application/x-www-form-urlencoded'
  }
  var access_token = uni.getStorageSync('access_token')
  console.log('token:',access_token)
  var baseUrl = '/api/doc/'
  uni.request({
   url: baseUrl + url,
   method: 'GET',
   data: data,
   header: {
    'content-type': type,
    'Accept':'application/x..v1+json',
    'Authorization':'Bearer '+access_token,
   },
   success: function (res) {
    if (res.data) {
     resolve(res.data)
    } else {
     console.log("请求失败", res)
     reject(res)
    }
   },
   fail: function (res) {
    console.log("发起请求失败~")
    console.log(res)
   }
  })
 })
}

请求示例:

//获取用户信息
uni.docajax("userinfo",{},'GET')
.then(res => {
  this.nickname = res.nickname
  this.avatar = res.avatar
});

到此这篇关于详解vue或uni-app的跨域问题解决方案的文章就介绍到这了,更多相关vue或uni-app的跨域问题解决方案内容请搜素三水点靠木以前的文章或下面相关文章,希望大家以后多多支持三水点靠木!

Javascript 相关文章推荐
js设置文本框中焦点位置在最后的示例代码(简单实用)
Mar 04 Javascript
JS的encodeURI和java的URLDecoder.decode使用介绍
May 08 Javascript
js创建对象的方式总结
Jan 10 Javascript
Bootstrap表单布局样式源代码
Jul 04 Javascript
JS匹配日期和时间的正则表达式示例
May 12 Javascript
详解vue数据渲染出现闪烁问题
Jun 29 Javascript
JS随机排序数组实现方法分析
Oct 11 Javascript
vue slot 在子组件中显示父组件传递的模板
Mar 02 Javascript
vue移动端轻量级的轮播组件实现代码
Jul 12 Javascript
jQuery属性选择器用法实例分析
Jun 28 jQuery
微信小程序如何修改radio和checkbox的默认样式和图标
Jul 24 Javascript
vue.js实现数据库的JSON数据输出渲染到html页面功能示例
Aug 03 Javascript
如何基于js判断浏览器版本
Feb 20 #Javascript
微信小程序webSocket的使用方法
Feb 20 #Javascript
Javascript Worker子线程代码实例
Feb 20 #Javascript
vue中音频wavesurfer.js的使用方法
Feb 20 #Vue.js
Javascript原生ajax请求代码实例
Feb 20 #Javascript
webpack中的模式(mode)使用详解
Feb 20 #Javascript
jquery向后台提交数组的代码分析
Feb 20 #jQuery
You might like
PHP实现页面静态化的超简单方法
2016/09/06 PHP
在Mac OS下搭建LNMP开发环境的步骤详解
2017/03/10 PHP
PHP实现Session入库/存入redis的方法
2017/05/04 PHP
javascript 常用关键字列表集合
2007/12/04 Javascript
我见过最全的个人js加解密功能页面
2007/12/12 Javascript
js中关于new Object时传参的一些细节分析
2011/03/13 Javascript
浅谈JavaScript之事件绑定
2013/07/08 Javascript
JS Date函数整理方便使用
2013/10/23 Javascript
原生JS实现图片左右轮播
2016/12/30 Javascript
AngularJS报错$apply already in progress的解决方法分析
2017/01/30 Javascript
简单实现jQuery弹幕效果
2017/05/06 jQuery
微信小程序scroll-view组件实现滚动动画
2018/01/31 Javascript
Vue Socket.io源码解读
2018/02/07 Javascript
jQuery实现标签子元素的添加和赋值方法
2018/02/24 jQuery
JS伪继承prototype实现方法示例
2018/06/20 Javascript
jQuery Ajax实现Select多级关联动态绑定数据的实例代码
2018/10/26 jQuery
JavaScript多种页面刷新方法小结
2019/04/04 Javascript
解决Vue+Electron下Vuex的Dispatch没有效果问题
2019/05/20 Javascript
基于vue.js实现购物车
2020/01/15 Javascript
使用React-Router实现前端路由鉴权的示例代码
2020/07/26 Javascript
python获取android设备的GPS信息脚本分享
2015/03/06 Python
使用Python编写基于DHT协议的BT资源爬虫
2016/03/19 Python
python分批定量读取文件内容,输出到不同文件中的方法
2018/12/08 Python
Python imutils 填充图片周边为黑色的实现
2020/01/19 Python
Numpy 理解ndarray对象的示例代码
2020/04/03 Python
python实现简单遗传算法
2020/09/18 Python
定义一结构体变量,用其表示点坐标,并输入两点坐标,求两点之间的距离
2015/08/17 面试题
教师的实习自我鉴定
2013/12/17 职场文书
小学生秋游活动方案
2014/02/23 职场文书
部门年终奖分配方案
2014/05/07 职场文书
中华魂演讲稿
2014/05/13 职场文书
党的群众路线教育实践活动个人自我剖析材料
2014/10/07 职场文书
小学教师师德师风承诺书
2015/04/28 职场文书
初婚未育证明样本
2015/06/18 职场文书
Vue组件化(ref,props, mixin,.插件)详解
2022/05/15 Vue.js
DQL数据查询语句使用示例
2022/12/24 MySQL