关于跨域的总结

关于跨域,我的总结了如下几种方法

  • JSONP
  • CORS
  • WebSocket
  • document.domain
  • window.name
  • location.hash
  • postMessage

其中:CORS、jsonp等方法经常使用,window.name的方法既不复杂,也能兼容到几乎全部浏览器,这真是极好的一种跨域方法。html


webSocket

WebSocket是一种在单个TCP链接上进行全双工通信的协议。WebSocket与HTTP协议其实二者的关系像是两兄弟,各自有着各自擅长的领域,并且时不时还一同协做解决难题。
WebSocket要解决的问题:当服务器资源到位时,可以主动通知浏览器并返回相应资源。HTML5标准推出了WebSocket协议。
自己就不受浏览器“同源策略”的限制,WebSocket协议下的通信机制,客户端和服务端一旦创建链接,就能够顺畅的互发数据,所以WebSocket协议自己就是“有状态的”,不须要Cookie的帮忙,既然没有Cookie,天然也不须要“同源策略”去保护。
下面来讲说webSocket的具体实现:
像发起AJAX请求同样,发起WebSocket请求须要借助浏览器提供的WebSocket对象,该对象提供了用于建立和管理WebSocket链接,以及经过该链接收发数据的API。全部的浏览器都默认提供了WebSocket对象。让咱们看看该对象的用法:web

和使用XHRHttpRequest对象同样,咱们首先要实例化一个WebSocket对象:json

clipboard.png

传入的参数为响应WebSocket请求的地址。跨域

一样相似AJAX的是,WebSocket对象也有一个readyState属性,用来表示对象实例当前所处的连接状态,有四个值:浏览器

0:表示正在链接中(CONNECTING);
1:表示链接成功,能够通讯(OPEN);
2:表示链接正在关闭(CLOSING);
3:表示链接已经关闭或打开链接失败(CLOSED);
咱们能够经过判断这个值来执行咱们相应的代码。服务器

除此以外,WebSocket对象还提供给咱们一系列事件属性,使咱们控制链接过程当中的通讯行为:cookie

onopen:用于指定链接成功后的回调函数;
onclose:用于指定链接关闭后的回调函数;
onmessage:用于指定收到服务器数据后的回调函数;
onerror:用于指定报错时的回调函数;
经过.send()方法,咱们拥有了向服务器发送数据的能力(WebSocket还容许咱们发送二进制数据)。cors

clipboard.png

如何知道什么时候咱们的数据发送完毕呢?咱们须要使用WebSocket对象的bufferedAmount属性,该属性的返回值表示了还有多少字节的二进制数据没有发送出去,因此咱们能够经过判断该值是否为0而肯定数据是否发送结束。dom

clipboard.png


CORS

阮一峰博客http://www.ruanyifeng.com/blo...
在http header中写入容许访问的域名。
Access-Control-Allow-Origin,该字段是必须的。它的值要么是请求时Origin字段的值,要么是一个*,表示接受任意域名的请求。
须要注意的是:CORS请求默认状况下是不会发送cookie的,因此须要在服务器的响应中设置:
Access-Control-Allow-Credentials: true
除此以外,还须要在AJAX请求中设置:
var xhr = new XMLHttpRequest();
xhr.withCredentials = true;
CORS请求分为简单请求和非简单请求:
简单请求:须要AJAX里的onerrer回调函数进行捕获,由于也可能会返回200。
非简单请求:浏览器先询问服务器,当前网页所在的域名是否在服务器的许可名单之中,以及可使用哪些HTTP动词和头信息字段。只有获得确定答复,浏览器才会发出正式的XMLHttpRequest请求,不然就报错。
会首先发送一个预检请求,请求方法为:options,而且在请求头中会包含相应字段:
Access-Control-Request-Method
Access-Control-Request-Headers
若是响应头中有CORS相关字段:
Access-Control-Allow-Origin
Access-Control-Allow-Methods
Access-Control-Allow-Headers
浏览器检查响应头中包含这三个字段,则预检请求成功;不然,则会抛出错误。一旦服务器经过了"预检"请求,之后每次浏览器正常的CORS请求,就都跟简单请求同样,会有一个Origin头信息字段。服务器的回应,也都会有一个Access-Control-Allow-Origin头信息字段。socket


JSONP

  1. 咱们发现,Web页面上调用js文件时则不受是否跨域的影响(不只如此,咱们还发现凡是拥有”src”这个属性的标签都拥有跨域的能力,好比<script>、<img>、<iframe>);
  2. 因而能够判断,当前阶段若是想经过纯web端(ActiveX控件、服务端代理、属于将来的HTML5之Websocket等方式不算)跨域访问数据就只有一种可能,那就是在远程服务器上设法把数据装进js格式的文件里,供客户端调用和进一步处理;
  3. 恰巧咱们已经知道有一种叫作JSON的纯字符数据格式能够简洁的描述复杂数据,更妙的是JSON还被js原生支持,因此在客户端几乎能够为所欲为的处理这种格式的数据;
  4. 这样子解决方案就呼之欲出了,web客户端经过与调用脚本如出一辙的方式,来调用跨域服务器上动态生成的js格式文件(通常以JSON为后缀),显而易见,服务器之因此要动态生成JSON文件,目的就在于把客户端须要的数据装入进去。
  5. 、客户端在对JSON文件调用成功以后,也就得到了本身所需的数据,剩下的就是按照本身需求进行处理和展示了,这种获取远程数据的方式看起来很是像AJAX,但其实并不同。
  6. 为了便于客户端使用数据,逐渐造成了一种非正式传输协议,人们把它称做JSONP,该协议的一个要点就是容许用户传递一个callback参数给服务端,而后服务端返回数据时会将这个callback参数做为函数名来包裹住JSON数据,这样客户端就能够随意定制本身的函数来自动处理返回数据了。

document.domain

这个主要针对跨域访问cookie的状况
两个网页一级域名相同,只是二级域名不一样,浏览器容许经过设置document.domain共享 Cookie。
举例来讲,A网页是http://w1.example.com/a.html,B网页是http://w2.example.com/b.html,那么只要设置相同的document.domain,两个网页就能够共享Cookie。其实也能够在服务器端进行设置:指定Cookie的所属域名为一级域名,好比.example.com。Set-Cookie: key=value; domain=.example.com; path=/这样二级域名和三级域名不用作任何设置均可以共享这个cookie。未完待续。。。

相关文章
相关标签/搜索