Vue项目中跨域问题的解决

Vue项目中跨域问题的解决,第1张

在Web端Vue项目开发过程中,跨域问题是不可避免的;在我参与的Vue项目中,使用服务器代理的解决方案;针对不同的环境(开发环境/生产环境),采用了不同的服务器代理方案;

服务器代理的原理大概是这样:
代理服务器和访问源(请求端)是同源的,但和被访问服务器(资源端)是不同源的,但服务器之间的访问不受浏览器同源策略的影响(即不必担心是否有跨域问题),那么我们即可请求到同源服务器上的从被访问服务器上的获取到的请求资源了

这样配置完成后,我们发起的每次>这个应该是设置在M V C中的C——控制层的,比如:ResponseAddHeader("Access-Control-Allow-Origin", "");是服务端要进行的 *** 作,而不是简单的写在html页面中

什么是跨域?
跨域是通俗的说是从一个域名去请求另一个域名的资源。比如从 背后的基本思想是使用自定义的>

什么是跨域?

浏览器发送的请求地址(URL)与所在页面的地址 不同(端口/协议/域名 其一不同)。简言之,浏览器发出的请求url,与其所在页面的url不一样。此时,同源策略会让浏览器拒收 服务器响应回来的数据,报错信息如下:

最常用的四种跨域解决方案

1cors

cors跨域资源共享允许是在服务端"Access-Control-Allow-Origin"字段设置的,当将cors设置为允许某个地址访问时,该地址就可以跨域访问这个服务器地址。当cors设置为""时即允许所有地址访问时,则表示所有地址都可以跨域访问这个服务器地址的资源。

2、 通过jsonp跨域

Jsonp是Json的一种“使用模式”,他就可以解决浏览器遇到的跨域问题,我们可以动态创建script,再请求一个带参网址实现跨域通信。用Jsonp请求得到的是JavaScript,相当于直接用JavaScript解析。

3、postMessage跨域

在h5中新增了postMessage方法,postMessage可以实现跨文档消息传输,我们可以通过Windows的message事件来监听发送跨文档消息传输内容。

4、proxy(代理)

原理:因为同源策略只是针对浏览器的安全策略,但是服务端并不受同源策略的限制,也就不存在跨域的问题。

这个显然是处理前端跨域最优的方法了,在此记录下来方便以后使用,附送scss 转 css

使用 vscode IDE作为编写工具

1搜索并加载 vscode 插件 live server
2要文件根目录创建 "vscode" 目录
3在 vscode 目录下创建settingsjson
4proxUri 为代理的目标地址
5baseUri 识别代理的符号 (如下例中 baseUri: '/api', 则以"/api"开头的网络请求都将被识别为需要代理转发的地址,并把 ‘/api’重写为空"")

1ajax请求会受到浏览器同源策略的限制(同源 = 域名 + 端口 都一致)
2ajax请求默认携带 同源下的所有cookie, 如果不做限制 a 去请求 b 的时候就等于把a所有的cookie 都告诉b。
3同源下: 张三的网站只能访问张三的内容如鞋子衣服吃饭等等,如果想访问李四的,浏览器就不让你干了。如果充许这么干的话,张三的cookie隐私将直接暴露给李四,李四有可能干一些不怀好意的事情。
4跨域情况:张三把钱都放在李四那里,现在张三想去李四那边取钱,这时候就需要跨域了。
5跨域怎么解决呢?接下来把解决问题的思路简单描绘一下。
51:李四告诉全世界说我对钱不感兴趣,只要我有,你们所有人都随便来取。因此,当浏览器看到张三要取钱的人是李四这种慈善家,就不再拦着你了。
52:李四不是慈善家怎么办?于是张三这个时候就很讨厌浏览器,想了个办法绕过浏览器,然后另外找了个代理去跟李四取钱
521: 问题是绕过浏览器?怎么绕呢? 于是张三自己建了个服务器,每次要跟李四取钱的时候就欺骗浏览器说我要跟自己的服务器取钱,浏览器这个时候也就不再拦着你了
522:当张三自己的服务器接收到跟李四取钱任务后,就以proxy代理的身份向李四取钱,取完钱之后再通过浏览器给了张三
523:vscode 中的live server 插件里面就这个代理向李四取钱的代理服务器功能,本文settingsjson 中包含了配置信息
6当然还有一些很多牛叉的解决跨域的方法。若有兴趣的同学可以一起研究探讨。

项目背景
用户登录成功后,服务端生成token,并保存在cookie里。>(1)无法读取非同源网页的Cookie、LocalStorage等

(2)无法接触非同源网页的DOM

(3)不能向非同源地址发送Ajax请求

(1)浏览器对跨域请求进行拦截

跨域请求可以正常发起 —— 浏览器能正常接收到跨域响应的数据 —— 数据被浏览器同源策略拦截,因此Ajax获取不到数据

(2)如何实现跨域数据请求:

(1)借助 script标签的src属性,将请求服务器当作请求JS进行

(2)请求JS时将回调函数作为查询字符串发送给服务器

(3)服务器返回的数据作为回调函数的参数返回给浏览器,回调函数被执行,这样就可以进行跨域请求了

缺点: JSONP只能是get请求,请求资源都是get请求

(1)防抖策略:当事件触发后,延迟n秒后再执行回调,如果在这n秒内事件又被触发,则重新计时。

(2)应用场景:文本框确认输入完再去发送请求(可借助定时器实现)(缓存搜索建议列表)

(1)节流策略:减少一段时间内事件的触发频率

(2)应用场景:

(3)节流阀:节流阀为空,可以执行下一次 *** 作;不为空,不能执行下次 *** 作(当前 *** 作执行完,必须将节流阀置空,表示可以继续执行,执行之前都要判断一下节流阀是否为空)

主流的 前后端分离模式 下,当前端调用后台接口时,由于是在非同一个域下的请求,从而会引发 浏览器 的自我安全保护机制,最终结果是 接口成功请求并响应 ,但 前端不能正常处理该返回数据

因此,当 同时满足 以下三个条件的情况下,就会出现跨域问题:

想要彻底解决跨域问题,只需要破坏以上三个条件的任一即可:

添加浏览器启动参数: chrome --disable-web-security ,但是极不推荐这种解决方式。

Jsonp,全称 JSON with Padding ,一种非官方的协议,而是一种约定;前端通过向后台发送 script 类型请求解决跨域,此时接口响应的 application/javascript 类型的数据会作为 callback 函数的参数进行处理。

所以,后台也需要做相应的处理。以 Java 为例,添加如下配置即可:

综上, jsonp 请求存在以下几个弊端:

用 Nginx 或 Apache 来代理调用方的请求( 客户端变更为相对路径请求,而非绝对路径 ),此时对于浏览器来说,由于请求是同源的,因此就不存在跨域问题。

以 Java 应用为例,添加如下全局配置:

如果只想针对某个类下的接口,或者是某个具体的接口配置允许跨域,只需要在相应的地方添加注解 @CrossOrigin 即可。

如果配置了 nginx 作为代理服务器,那么只需要为 nginx 添加支持跨域请求即可:

Q1:浏览器在执行跨域请求时,是先执行后判断,还是先判断后执行?
A1:都有可能,这需要根据所发送的请求是 简单请求 还是 非简单请求 来判断;如果是非简单请求,浏览器每次在执行真正的请求之前,还会先发送一个 options 请求方式的预检命令 可设定缓存时长,取消每次请求都要预检,提高效率,参考上面的服务端配置 。关于两种请求的区分及定义,参考下图说明:

Q2:如果是允许带( 被调用方 ) cookie 的跨域请求,此时服务端同样配置为 Access-Control-Allow-Origin 等于 ,前端是否还可以请求成功?
A2:不可以,此时要将 Access-Control-Allow-Origin 指定为 调用方 具体的域 可以先取得调用方的域再动态配置,这样就不存在多个域请求的限制问题 ,并且添加配置 Access-Control-Allow-Credentials 为 true 。


欢迎分享,转载请注明来源:内存溢出

原文地址: https://outofmemory.cn/yw/13391401.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-07-27
下一篇 2023-07-27

发表评论

登录后才能评论

评论列表(0条)

保存