Web高级 Ajax和跨域CORS
Asynchronous JavaScript and XML
1. XMLHttpRequest
前端开发都知道,不多说。
var xhr = new XMLHttpRequest();
xhr.onreadystatechange = function () {
if (xhr.readyState !== 4) return;
if (xhr.status >= 200 && xhr.status < 300) {
console.log(JSON.parse(xhr.responseText));
}
else {
// What to do when the request has failed
console.log('error', xhr);
}
};
xhr.open('GET', 'https://mysite.com/index');
xhr.setRequestHeader('X-Token', '123456');
xhr.send();
1.1 open方法
定义:open( Method, URL, Asynchronous, UserName, Password )
- Method:GET/POST/HEAD/PUT/DELETE/OPTIONS
- Asynchronous(defualt true)
1.2 setRequestHeader方法
定义:setRequestHeader( Name, Value )
注意,以X开头的为header为自定义头部
1.3 send方法
定义:send(body)
- body可以是:document,Blob, BufferSource, FormData, URLSearchParams, ReadableStream等
2. Fetch
新一代旨在替换XHR的API方法。
fetch("https://mysite.com/index", {
method: "POST",
headers: {
"Content-Type": "application/x-www-form-urlencoded",
'X-Token': '123456'
},
body: "id=123"
}).then(function (response) {
if (response.ok) {
return response.json();
} else {
return Promise.reject({
status: response.status,
statusText: response.statusText
});
}
})
.then(function (data) {
console.log('success', data);
})
.catch(function (error) {
console.log('error', error);
});
2.1 fetch方法
定义:fetch(input, init)
- input:URL或者Request对象
- init:一个配置项对象,包括所有对请求的设置。可选的参数有:
- method: 请求使用的方法,如 GET、POST。
- headers: 请求的头信息,形式为 Headers 对象或 ByteString。
- body: 请求的 body 信息:可能是一个 Blob、BufferSource、FormData、URLSearchParams 或者 USVString 对象。注意 GET 或 HEAD 方法的请求不能包含 body 信息。
- mode: 请求的模式,如 cors、 no-cors 或者 same-origin。
- credentials: 请求的 credentials,如 omit、same-origin 或者 include。
- cache: 请求的 cache 模式: default, no-store, reload, no-cache, force-cache, or only-if-cached.
2.2 回调
fetch返回一个promise,采用then的链式调用避免回调地狱问题。
2.3 返回值
参考这里:https://developer.mozilla.org/zh-CN/docs/Web/API/Response
3. XHR vs Fetch
- Fetch返回值不是可读的形式,需要使用response.json()转换为可读形式
- XHR的请求失败通过判断状态码,Fetch请求失败通过catch处理
- Fetch默认不带cookie,XHR默认带cookie
- Fetch在服务器返回 400,500 错误码时并不会reject而被当做成功处理进then,只有网络错误这些导致请求不能完成才会触发catch
- Fetch没有abort和onTimeout,不能中途中断,XHR可以。
Cross-Origin Resource Sharing
CORS是一种机制,用来保护跨域数据传输的安全性和降低风险。
1. 常见的可以跨域请求的资源
- XHR或Fetch发起的跨域HTTP请求
- Web字体
- CSS文件
- Scripts文件
2. 跨域相关的Http首部
Access-Control-Request-Headers
(Preflight使用)客户端告诉服务器实际请求时使用的头部。Access-Control-Request-Method
(Preflight使用)客户端告诉服务器实际请求时使用的方法。Access-Control-Allow-Origin
服务端允许请求的源域Access-Control-Allow-Credentials
服务端是否允许请求带cookie,设置为true时allow-origin不能为*Access-Control-Allow-Headers
服务端允许的客户端请求的头部Access-Control-Allow-Methods
服务端允许客户端请求的方法Access-Control-Max-Age
preflight可以被缓存的时间Cross-Origin-Resource-Policy
(fetch使用)具体查看https://fetch.spec.whatwg.org/#cross-origin-resource-policy-headerOrigin
客户端请求从哪个域来
1. OPTIONS /resources/post-here/
2. HTTP/1.1
3. Host: bar.other
4. User-Agent: Mozilla/5.0 (Macintosh; U; 5.Intel Mac OS X 10.5; en-US; rv:1.9.1b3pre) Gecko/20081130 Minefield/3.1b3pre
6. Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
7. Accept-Language: en-us,en;q=0.5
8. Accept-Encoding: gzip,deflate
9. Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
10. Connection: keep-alive
11. Origin: http://foo.example
12. Access-Control-Request-Method: POST
13. Access-Control-Request-Headers: X-PINGOTHER, Content-Type
//响应
14. HTTP/1.1 200 OK
15. Date: Mon, 01 Dec 2008 01:15:39 GMT
16. Server: Apache/2.0.61 (Unix)
17. Access-Control-Allow-Origin: http://foo.example
18. Access-Control-Allow-Methods: POST, GET, OPTIONS
19. Access-Control-Allow-Headers: X-PINGOTHER, Content-Type
20. Access-Control-Max-Age: 86400
21. Vary: Accept-Encoding, Origin
22. Content-Encoding: gzip
23. Content-Length: 0
24. Keep-Alive: timeout=2, max=100
25. Connection: Keep-Alive
26. Content-Type: text/plain
3. 简单请求
跨域请求分为简单请求和预检请求,全部符合下列条件时为简单请求:
- 使用的方法为:GET/HEAD/POST
- 不得设置安全首页之外的首页:Accept,Accept-Language,Content-Language,Content-Type,DPR,Downlink,Save-Data,Viewport-Width,Width
- Content-Type只能是以下值: text/plain, multipart/form-data, application/x-www-form-urlencoded
- 请求中的任意XMLHttpRequestUpload 对象均没有注册任何事件监听器
- 请求中没有使用 ReadableStream 对象
当使用普通请求时,如果服务器允许该源域跨域请求资源,则直接返回响应。如果服务器不允许跨域请求,则返回不正确的响应首部,则请求方不会收到任何数据。
4. 预检请求(preflight request)
除了简单请求的情况,其他的CORS请求都会有预检请求。
预检请求会先使用OPTIONS方法发起一个预检请求到服务器,以获知服务器是否允许该实际请求,所以会进行2个回合的通信。
典型的会触发预检请求的跨域情景:请求JSON数据 或 带有自定义头部
如:
- content-type:application/json
- X-Audit-Token:X123456
JSONP
跨域请求的一种常见实现方式.
1. 优缺点
- 优点:
不受同源策略限制,可以向没有启用CORS的跨域服务端请求数据。
兼容性较强,所有浏览器都支持该技术。 - 缺点
只支持GET,不支持POST
请求失败时不会有HTTP状态码返回
安全性也是一个值得考虑的问题
2. 实现原理
- Client端用JS动态生成一个script标签并添加到文档流中,如
<script type="text/javascript">
function jsonpCallBack(data){
console.log(data.msg);
}
$(document).ready(function(){
$("body").append('<script src="http://www.ASite.com/ServerJSONP.js?callback=jsonpCallBack"></script>');
});
</script>
- 浏览器会使用GET方法请求ASite上的ServerJSONP.js并携带参数
- 服务端接收到该请求,并根据参数中的回调函数名动态生成返回的内容,如
jsonpCallBack({msg:"this is jsonp request!"});
- 浏览器获取到script标签请求的内容后会执行其中的代码
- 最终我们定义的jsonpCallBack函数会被调用,输出: "this is jsonp request!"
refs:
https://xhr.spec.whatwg.org/
https://developer.mozilla.org/en-US/docs/Web/API/XMLHttpRequest
https://gomakethings.com/why-i-still-use-xhr-instead-of-the-fetch-api/
https://hacks.mozilla.org/2015/03/this-api-is-so-fetching/
https://developer.mozilla.org/zh-CN/docs/Web/HTTP/Access_control_CORS
Web高级 Ajax和跨域CORS的更多相关文章
- .NET MVC & Web API Cors让AJAX 实现跨域
什么是Cors? CORS是一个W3C标准,全称是"跨域资源共享"(Cross-origin resource sharing).它允许浏览器向跨源服务器,发出XMLHttpReq ...
- ASP.NET MVC & WebApi 中实现Cors来让Ajax可以跨域访问 (转载)
什么是Cors? CORS是一个W3C标准,全称是"跨域资源共享"(Cross-origin resource sharing).它允许浏览器向跨源服务器,发出XMLHttpReq ...
- ajax跨域-CORS
CORS:跨域资源共享,是一种跨域访问的W3C标准,它允许浏览器可以跨源服务器进行请求,可以让ajax实现跨域访问.出现跨域问题的原因是浏览器同源策略导致的,协议+域名+端口三者一致被认为是同源.网站 ...
- AJAX POST&跨域 解决方案 - CORS
一晃又到新年了,于是开始着手好好整理下自己的文档,顺便把一些自认为有意义的放在博客上,记录成点的点滴. 跨域是我在日常面试中经常会问到的问题,这词在前端界出现的频率不低,主要原因还是 ...
- AJAX POST&跨域 解决方案 - CORS(转载)
跨域是我在日常面试中经常会问到的问题,这词在前端界出现的频率不低,主要原因还是由于安全限制(同源策略, 即JavaScript或Cookie只能访问同域下的内容),因为我们在日常的项目开发时会不可避免 ...
- (转) AJAX POST&跨域 解决方案 - CORS
跨域是我在日常面试中经常会问到的问题,这词在前端界出现的频率不低,主要原因还是由于安全限制(同源策略, 即JavaScript或Cookie只能访问同域下的内容),因为我们在日常的项目开发时会不可避免 ...
- JavaScript(10)——Ajax以及跨域处理
Ajax以及跨域处理 哈哈哈,终于写到最后一章了.不过也还没有结束,说,不要为了学习而学习,恩.我是为了好好学习而学习呀.哈哈哈.正在尝试爱上代码,虽然有一丢丢的难,不过,我相信我会的! [Ajax] ...
- MVC跨域CORS扩展
一般的基于浏览器跨域的主要解决方法有这么几种:1.JSONP 2.IFrame方式 3.通过flash实现 4.CORS跨域资源共享 ,这里我们主要关注的是在MVC里面的CORS ...
- 跨域CORS
一.跨域CORS是什么 当一个资源从与该资源本身所在的服务器的域或端口不同的域或不同的端口请求一个资源时,浏览器会发起一个跨域 HTTP 请求.出于安全考虑,浏览器会限制从脚本内发起的跨域HTTP请求 ...
随机推荐
- Tensorflow描述张量的维度:阶,形状以及维数
张量 TensorFlow用张量这种数据结构来表示所有的数据.你可以把一个张量想象成一个n维的数组或列表.一个张量有一个静态类型和动态类型的维数.张量可以在图中的节点之间流通. 阶 在TensorFl ...
- TCP长连接与短连接、心跳机制
1. TCP连接 当网络通信时采用TCP协议时,在真正的读写操作之前,server与client之间必须建立一个连接,当读写操作完成后,双方不再需要这个连接时它们可以释放这个连接,连接的建立是需要三次 ...
- VUE处理 组件赋值 watch 监听不到赋值问题
开发中,遇到了一个BUG,做的页面类似于 导航切换效果.两个组件传值. 上方导航组件 (主动) 左侧导航组件 (被动) 点击上方导航,左侧导航实现变换对应的栏目. 实现过程中,遇到了点问题.左 ...
- 深度学习(PYTORCH)-2.python调用dlib提取人脸68个特征点
在看官方教程时,无意中发现别人写的一个脚本,非常简洁. 官方教程地址:http://pytorch.org/tutorials/beginner/data_loading_tutorial.html# ...
- element UI 下拉菜单滚动监听(vue指令)
直接看代码吧,可以直接粘贴此代码到你的编辑器中看效果. <template> <div class="page-component"> <div cl ...
- Linux中访问Apache报403错误处理方法
1.先说本地环境,脱离基础环境的解决策略都是耍流氓 (1)Linux:CentOS7.5 (2)Apache: Apache/2.4.6 (CentOS) (3)Apache的安装路径在 /usr/l ...
- Heap Sort - recursion
Heap Sort Build a max heap using exsiting array, which is called Heapify Swap root with the last el ...
- yii2 rules 验证规则
yii2 框架定义的约束 public $builtInValidators = [ 'boolean' => 'yii\validators\BooleanValidator', 'capt ...
- 关于ubuntu远程访问服务器的知识点
为了可以打开图形界面,用ssh -X 用户名@地址 如何远程打开文件夹可视化界面 nautilus /文件夹
- maven各个属性参数详解
<project xmlns="http://maven.apache.org/POM/4.0.0 " xmlns:xsi="http://www.w3.org/2 ...