总结前端跨域解决方案

什么是同源策略

同源策略/SOP(Same origin policy)是一种约定,由Netscape公司1995年引入浏览器,它是浏览器最核心也最基本的安全功能,如果缺少了同源策略,浏览器很容易受到XSS、CSFR等攻击。所谓同源是指"协议+域名+端口"三者相同,即便两个不同的域名指向同一个ip地址,也非同源。

同源策略限制以下几种行为:

  1. IndexDB、LocalStorage 和 Cookie无法读取
  2. Js对象 和DOM无法获得
  3. AJAX 请求不能发送

同源需要:(<img><link><script>三种标签不受限制)

我们可以根据同源策略的定义,总结出常见的6种跨域场景:
image

遇到上述这些情况,根据我们应用的技术,我们可以总结出来9种跨域解决方案:

实现跨域的常用方式

通过jsonp跨域

利用<script>标签没有跨域限制的漏洞,网页可以得到从其他来源动态产生的 JSON 数据。JSONP请求一定需要对方的服务器做支持才可以。优点是兼容老式浏览器,但是只支持get而且不太安全,一般不用。基于此原理,我们可以通过动态去创建script,再请求一个带参网址实现跨域通信。

jsonp缺点:只能实现get一种请求。

var script = document.createElement("script");
script.type = "text/javascript";

//传参一个回调函数名给后端,方便后端返回时执行这个在前端定义的回调函数
script.src =
  "http://www.baidu.com:8080/login?user=admin&callback=handleCallback";
document.head.appendChild(script);

//回调执行函数
function handleCallback(res) {
  console.log("res =", res);
}

CORS跨域

跨域的请求其实是发出去了的,只不过被浏览器给拦截了,因为不安全,说直白点儿就是,你想要从服务器哪儿拿个东西,但是没有经过人家允许啊。所以怎么样才安全 ?服务器允许了不就安全了,这就是 CORS 实现的原理:使用额外的 HTTP 头来告诉浏览器,让运行在某一个 origin 上的 Web 应用允许访问来自不同源服务器上的指定的资源

目前,所有的主流浏览器都支持 CORS,其中,IE 浏览器的版本不能低于 10,IE 8 和 9 需要通过 XDomainRequest 来实现。

简单请求

若请求满足所有下述条件,则该请求可视为“简单请求”:

允许的方法之一:

Fetch 规范定义了对 CORS 安全的首部字段集合

不得人为设置该集合之外的其他首部字段。该集合为:

Content-Typ 的值仅限于下列三者之一:

  • text/plain
  • multipart/form-data
  • application/x-www-form-urlencoded

预检请求

与前述简单请求不同,“需预检的请求”要求必须首先使用 OPTIONS 方法发起一个预检请求到服务器,以获知服务器是否允许该实际请求。

Websocket

WebSocket 规范定义了一种 API,可在网络浏览器和服务器之间建立“套接字”连接。简单地说:客户端和服务器之间存在持久的连接,而且双方都可以随时开始发送数据。

这种方式本质没有使用了 HTTP 的响应头, 因此也没有跨域的限制

前端部分

let socket = new WebSocket("ws://localhost:8080");
socket.onopen = function() {
    socket.send("秋风的笔记");
  };
socket.onmessage = function(e) {
    console.log(e.data);
  };  

window.postMessage

window.postMessage() 方法可以安全地实现跨源通信。通常,对于两个不同页面的脚本,只有当执行它们的页面位于具有相同的协议(通常为 https),端口号(443 为 https 的默认值),以及主机 (两个页面的模数 Document.domain设置为相同的值) 时,这两个脚本才能相互通信。window.postMessage() 方法提供了一种受控机制来规避此限制,只要正确的使用,这种方法就很安全。

用途

1.页面和其打开的新窗口的数据传递

2.多窗口之间消息传递

3.页面与嵌套的 iframe 消息传递

node中间件代理

实现原理: 同源策略是浏览器需要遵循的标准,而如果是服务器向服务器请求就无需遵循同源策略。代理服务器,需要做以下几个步骤:

  1. 接受客户端请求
  2. 将请求转发给服务器
  3. 拿到服务器响应数据
  4. 将响应转发给客户端
posted @ 2020-04-15 12:30  仲吕  阅读(210)  评论(0编辑  收藏  举报