跨域问题及解决方案
前言
跨域请求的响应一般会被浏览器所拦截,注意,是被浏览器拦截,响应其实是成功到达客户端了。
问题引入
你打开了一个银行站点,然后又一不小心打开了一个恶意站点,如果没有安全措施,恶意站点就可以做很多事情:
- 修改银行站点的 DOM、CSSOM 等信息;
- 在银行站点内部插入 JavaScript 脚本;
- 劫持用户登录的用户名和密码;
- 读取银行站点的 Cookie、IndexDB 等数据;
- 甚至还可以将这些信息上传至自己的服务器,这样就可以在你不知情的情况下伪造一些转账请求等信息。
所以说,在没有安全保障的 Web 世界中,我们是没有隐私的,因此需要安全策略来保障我们的隐私和数据的安全。
同源策略
- 概念:如果两个 URL 的
协议、域名和端口都相同
,我们就称这两个 URL 同源。浏览器默认两个相同的源之间是可以相互访问资源和操作 DOM 的。两个不同的源之间若想要相互访问资源或者操作 DOM,那么会有一套基础的安全策略的制约,我们把这称为同源策略。 - 同源策略主要表现在 DOM、Web 数据和网络这三个层面:
- DOM 层面:同源策略限制了来自不同源的 JavaScript 脚本对当前 DOM 对象读和写的操作
- 数据层面:同源策略限制了不同源的站点读取当前站点的 Cookie、IndexDB、LocalStorage 等数据
- 网络层面:同源策略限制了通过 XMLHttpRequest 等方式将站点的数据发送给不同源的站点
跨域解决方案
JSONP
- 原理:
利用script标签的src属性没有跨域限制的特性
,网页可以得到从其他来源动态产生的JSON数据。JSONP请求一定需要对方的服务器支持才可以。 - JSONP与AJAX对比:都是客户端向服务器端发送请求,从服务器获取数据的方式。但AJAX属于同源策略,而JSONP属于跨域请求
- 优缺点:优点是简单兼容性好,可用于解决主流浏览器的跨域数据访问问题。缺点是仅支持get方法具有局限性,不安全可能遭到XXS攻击
- 实现代码
const jsonp = ({
url,
params,
callback
}) => {
//得到完整的url
const generate = () => {
let str = ''
for (let key in params) {
str += `${
key}=${
params[key]}&`
}
str += `callback=${
callback}`
return `${
url}?</