1. 什么是同源策略及限制
同源策略限制从一个源加载的文档或脚本如何与来自另一个源的资源进行交互。这是一个用于隔离潜在恶意文件的关键的安全机制。
源:协议+域名+端口,例如:
1 | 协议:HTTP |
不同源之间的访问限制:
- 无法获取 Cookie、LocalStorage 和 IndexDB 无法读取
- 无法获取 DOM 节点
- 不能发送 Ajax 请求
2. 前后端如何通信
- Ajax:
受到同源策略的限制 - WebSocket:
不受同源策略的限制 - CORS:
既支持同源通信,也支持不同源通信
3. 如何创建 Ajax
考察点:
- XMLHttpRequest 对象的工作流程
- 兼容性处理(IE和其他浏览器)
- 事件的触发条件
- 事件的触发顺序
1 | util.json = function(options){ |
4. 跨域通信的几种方式
- JSONP
- Hash
- postMessage
- WebSocket
- CORS
4.1 JSONP
原理:利用 <script>
标签是可以异步加载的
举个栗子,我的个人主页地址是:www.xinxiaoyang.com,但是我在页面中引用了 GA 的统计代码,引入的 JavaScript 地址是:https://www.google-analytics.com/analytics.js。很明显,请求的 JS 文件是跨域的,但是是被允许的。
i. 请求的 <script>
标签中写明回调函数名(callback),例如:
1 | <script src="http://www.abc.com/?callback=jsonp></script> |
ii. 在服务器端的 JS 文件中定义一个以 callback
为名称的函数,请求的数据以参数形式保存。例如:
1 | <script> |
iii. 使用时,客户端本地需要定义一个相同 callback
名的函数,用来处理返回的数据。
以下代码实现了 jsonp 的处理过程:
1 | // 动态创建 script 标签 |
缺点:
- JSONP 只支持 GET 请求
4.2 Hash
原理:
注:Hash(#) 不会重新刷新页面,而Search(?) 会重新刷新页面
举个例子,假设以下场景:当前页面 A 通过 iframe 或 frame 嵌入跨域的页面 B
1 | // 在 A 中伪代码如下: |
4.3 postMessage
H5 新属性
1 | // 窗口 A(http:A.com) 向跨域的窗口 B(http://B.com) 发送信息 |
4.4 WebSocket
1 | // wss(加密)/ws(非加密):服务器地址 |
4.5 CORS(Cross-Origin Resource Sharing)
原理:浏览器拦截 Ajax 请求,添加 <Access-Control-Allow-*>
请求头
新的通信标准,可以理解为支持跨域通信的 Ajax,需要浏览器和服务器同时支持。
这里引入了一个新的 API:fetch
。原生写法下,Ajax 只能通过 XMLHttpRequest
对象来实现,在新标准中,可以通过 fetch
来实现。
同源情况下,fetch
就是 Ajax,不同源情况下,需要添加配置。
具体配置项参见:http://www.ruanyifeng.com/blog/2016/04/cors.html
1 | // CORS: url(必须),options(可选) |