跨域产生原因和跨域解决方案
跨域产生原因和跨域解决方案
一、为什么会出现跨域问题?
出于浏览器的同源策略限制,同源策略是一种约定,它是浏览器最核心也就是最基本的安全功能,如果缺少了同源策略,浏览器的正常功能会受到影响,可以说WEB是构建在同源策略基础之上的,浏览器只是针对同源策略的一种实现。同源策略会阻止一个域的js脚本和另外一个域的内容进行交互,所谓同源(即在同一个域)就是两个页面具有相同的协议(protocol)、主机(host)和接口号(port)
同源策略限制以下几种行为:
- Cookie、LocalStorage 和 IndexDB 无法读取
- DOM和JS对象无法获得
- AJAX 请求不能发送
二、什么是跨域?
当浏览器与后端服务器地址不一致,就会存在跨域问题,虽然请求会发送出去,但是不让你的JS拿到响应内容,也就形成了不能跨过这个域去访问其他域的功能,这里的域指的是协议、端口号和主机都需要一致的url,换句话说这两个url必须同源才允许交互。
报以下错误就是出现了跨域问题:
三、解决方案:
1.jsonp
原理:动态生成script标签,通过src属性加载,发送带有callback参数的GET请求,服务端将接口返回数据拼凑到callback函数中,返回给浏览器,浏览器解析执行,从而前端拿到callback函数返回的数据。
缺点:只支持get,不支持post
应用场景:有些第三方数据接口会使用jsonp解决跨域问题,工作中不常用
2.cors 跨域资源共享
服务器端进行配置 前端直接请求服务器,工作中常用的。
原理:当浏览器在进行跨域请求的时候,会在请求里添加头部origin:协议+主机+端口,表明自己的主机、协议和端口号,也可以用“*”来表示,服务端一般都会设置好使用方法,常用的就是get和post两个方法;如果服务器允许能够访问,就得添加头部Access-Control-Allow-Origin到响应里面;浏览器看到服务器传回来的这个头部就知道能不能进行跨域请求了,要注意兼容问题
3.中间服务器代理
搭建一个中间服务器(代理服务器),后端做。前端请求中间服务器,中间服务器去请求目标服务器不存在跨域问题
4.vue的反向代理跨域解决
请求自身服务器 => 代理 解决的跨域,如何配置?
4.1 在vue.config.js中,加一个devServe
module.exports = {
devServer: {
// 配置代理服务器(帮助请求时进行跨域)
proxy: {
'/api': {
target: '服务器根地址',
//ws:true, //是否代理websocked
changOrigin:true,
pathRewrite:{
"/api":"" //将地址中的"/api"换成"/"
}
}
}
},
}
//‘/api’:以 /api 开头的路径请求, 认为需要走代理
//target:‘服务器的根地址’
//changOrigin:true,开启代理:在本地会创建一个虚拟服务器,发送请求的数据,并接收请求的数据,这样服务端和服务端进行数据交互就不会有跨域问题
4.2 发请求 axios.get(‘api/sys/login’)
实际请求会拼接基地址,api就会被替换成空,地址变成:完成服务器地址+/sys/login
发请求正常发
- request.post('/sys/login', data)
实际的请求会拼接上基地址
- /api/sys/login => 本机地址 + /api/sys/login => 走代理了
走代理会将本机地址进行替换
- 实际请求地址 => 代理地址 + /api/sys/login
小tip: 如果实际请求地址, 不需要 /api 标识, 配置pathRewrite进行重写
4.3 结论:
- 不走代理, env 文件, 配置完整地址
- 走代理, env 文件, 配置 /api, 配置vue.config.js proxy(3行代码)
5.nginx反向代理接口跨域解决
跨域问题:同源策略仅是针对浏览器的安全策略。服务器端调用HTTP接口只是使用HTTP协议,不需要同源策略,也就不存在跨域问题。
5.1 在request.js中配置基地址,使用了环境变量:baseURL: process.env.VUE_APP_BASE_API
5.2 在开发环境(.env.development)中配置:VUE_APP_BASE_API = “/api”
5.3 在生产环境(.env.production)中配置:VUE_APP_BASE_API = “/prod-api”
5.4生产环境打包出来的地址与后端接口地址不一样,需要使用nginx代理解决跨域问题,解决方法:
//修改nginx配置文件:nginx--conf--nginx.conf
server{
location /prod-api {
proxy_ pass 接口服务器地址;
}
}
5.5重启服务
// mac重启服务
$ /opt/homebrew/Cellar/nginx/1.23.3/bin/nginx -s reload #重启
// windows重启服务
$ ./nginx -s reload #重启
![Logo](https://devpress.csdnimg.cn/79de2bf0b7994defa4242ef90d5513fa.jpg)
开放原子开发者工作坊旨在鼓励更多人参与开源活动,与志同道合的开发者们相互交流开发经验、分享开发心得、获取前沿技术趋势。工作坊有多种形式的开发者活动,如meetup、训练营等,主打技术交流,干货满满,真诚地邀请各位开发者共同参与!
更多推荐
所有评论(0)