Ajax 跨域 异步 CORS
对于一个简单的请求,没有定制header并且body是text/plain的话,该请求发送的时候会带上一个header叫origin,包含了发送请求的(prototype,domin,和port),服务器就可以根据这个来决定是否响应:
Origin: http://www.haha.com
当服务器响应的时候,会返回一个Access-Control-Allow-Origin头,里面的信息要么和发送的的origin一样,要么为*如果那是一个公共资源,浏览器匹配以后才会进行处理:
Access-Control-Allow-Origin: http://www.haha.com
IE跨域:
通过XDomainRequest对象实现,和XHR比有一些不同之处:
1、Cookies are neither sent with requests nor received with responses.
2、There is no access to set request headers other than Content-Type.
3、There is no access to response headers.
4、Only GET and POST requests are supported.
上面这些限制缓解了跨网站伪造请求(csrf)和跨网站脚本攻击(xss),被请求的资源可以根据恰当的数据(user-agent,referrer等等),动态地决定是否设置返回的 Access-Control-Allow-Origin头信息。作为请求的一部分,origin头信息携带着请求发起源域名信息也会被同时发送,这样被请求的资源服务方就可以识别出这是一个XDR跨域请求了。
get请求例子:
var xdr = new XDomainRequest();
xdr.onload = function(){
alert(xdr.responseText);
};
xdr.onerror = function(){
alert(“An error occurred.”);
};
xdr.timeout = 1000;
xdr.ontimeout = function(){
alert(“Request took too long.”);
};
xdr.open(“get”, “http://www.somewhere-else.com/page/”); 这里只接受两个参数,只能使用异步方式请求
xdr.send(null);
xdr.abort(); //stop the request
当收到响应的时候,只能拿到未经处理的text。也不能判断status的值。如果没有 Access-Control-Allow-Origin也会失败,并且无法得到错误信息,所以必须监听error事件,不然失败了都没人知道啊。
post请求方式:
var xdr = new XDomainRequest();
xdr.onload = function(){
alert(xdr.responseText);
};
xdr.onerror = function(){
alert(“An error occurred.”);
};
xdr.open(“post”, “http://www.somewhere-else.com/page/”);
xdr.contentType = “application/x-www-form-urlencoded”; 这是XDR里唯一允许接入的头信息了
xdr.send(“name1=value1&name2=value2”);
其他浏览器实现跨域:
同样使用xhr就可以了,把请求的地址改为绝对地址
var xhr = createXHR();
xhr.onreadystatechange = function(){
if (xhr.readyState == 4){
if ((xhr.status >= 200 && xhr.status < 300) || xhr.status == 304){
alert(xhr.responseText);
} else {
alert(“Request was unsuccessful: “ + xhr.status);
}
}
};
xhr.open(“get”, “http://www.somewhere-else.com/page/”, true);
xhr.send(null);
有三个限制:
1、Custom headers cannot be set using setRequestHeader().
2、Cookies are neither sent nor received.
3、The getAllResponseHeaders() method always returns an empty string
为了区分的话请求本地资源用相对地址,外面资源用绝对地址
兼容两者的函数:
function createCORSRequest(method, url){
var xhr = new XMLHttpRequest();
if (“withCredentials” in xhr){ 通过检测是否含有 withCredentials可以判断当前xhr对象是否支持跨域请求
xhr.open(method, url, true);
} else if (typeof XDomainRequest != “undefined”){
xhr = new XDomainRequest();
xhr.open(method, url);
} else {
xhr = null;
}
return xhr;
}
Preflighted Requests(先导请求)(当使用GET, HEAD, POST以外的方法。而且當用POST方法時,如果請求連帶的資料其Content-Type不為application/x-www-form-urlencoded, multipart/form-data, 或text/plain,例如POST請求連帶的資料是application/xml或text/xml的XML類型資料,那麼先導請求就會先送出。或者請求中有自訂義標頭,例如自定义一個X-PINGOTHER header。)
Origin — Same as in simple requests.
Access-Control-Request-Method — The method that the request wants to use.
Access-Control-Request-Headers — (Optional) A comma-separated list of the custom headers being used.
Access-Control-Allow-Origin — Same as in simple requests.
Access-Control-Allow-Methods — A comma-separated list of allowed methods.
Access-Control-Allow-Headers — A comma-separated list of headers that the server will allow.
Access-Control-Max-Age — The amount of time in seconds that this prefl ight request should be cached for.
响应结果会按照 Access-Control-Max-Age的时间缓存起来,只会在第一次请求时才会额外增加一个HTTP请求。
Credentialed Requests(附带验证信息请求)
跨域请求默认是不提供验证信息的,但是可以通过把 withCredentials设置为true来开启该功能,如果服务器允许就会在相应中返回:
Access-Control-Allow-Credentials: true
浏览器就可以获取求响应中的验证信息,如果没有在相应中返回的话,浏览器会拒绝任何响应,不会把响应传给JavaScript处理( responseText is an empty string, status is 0, and onerror() is invoked)
上面两种请求ie10及以下都不支持
Ajax 跨域 异步 CORS的更多相关文章
- WCF SOA --- AJAX 跨域请求处理 CORS for WCF
一.问题 跨域请求无法处理的问题,由于为了阻止恶意的网站通过JS脚本来窃取正常网站受保护的资源.所由所有的浏览器的默认策略是阻止XmlHttpRequest的跨域的异步请求. 但是对于一 ...
- AJAX跨域资源共享 CORS 详解
CORS是一个W3C标准,全称是"跨域资源共享"(Cross-origin resource sharing). 它允许浏览器向跨源服务器,发出XMLHttpRequest请求,从 ...
- ajax跨域通过 Cors跨域资源共享 进行GetPost请求
using System; using System.Collections.Generic; using System.Linq; using System.Net; using System.Ne ...
- ajax 跨域了 cors
<?php /** * Author: humanhuang * Date: 13-12-17 */ header('Access-Control-Allow-Origin:*'); heade ...
- Ajax跨域问题及解决方案 asp.net core 系列之允许跨越访问(Enable Cross-Origin Requests:CORS) c#中的Cache缓存技术 C#中的Cookie C#串口扫描枪的简单实现 c#Socket服务器与客户端的开发(2)
Ajax跨域问题及解决方案 目录 复现Ajax跨域问题 Ajax跨域介绍 Ajax跨域解决方案 一. 在服务端添加响应头Access-Control-Allow-Origin 二. 使用JSONP ...
- AJAX POST&跨域 解决方案 - CORS
一晃又到新年了,于是开始着手好好整理下自己的文档,顺便把一些自认为有意义的放在博客上,记录成点的点滴. 跨域是我在日常面试中经常会问到的问题,这词在前端界出现的频率不低,主要原因还是 ...
- Ajax操作如何实现跨域请求 (JSONP和CORS实现Ajax跨域的原理)
由于浏览器存在同源策略机制,同源策略阻止ajax (XMLHttpRequest) 从一个源加载的文档或脚本获取或设置另一个源加载的文档的属性. 特别的:由于同源策略是浏览器的限制,所以请求的发送和响 ...
- WeX5 - AJAX跨域调用相关知识-CORS和JSONP
http://docs.wex5.com/ajax-cross-domain/ 1.什么是跨域 跨域问题产生的原因,是由于浏览器的安全机制,JS只能访问与所在页面同一个域(相同协议.域名.端口)的内容 ...
- AJAX跨域调用相关知识-CORS和JSONP(引)
AJAX跨域调用相关知识-CORS和JSONP 1.什么是跨域 跨域问题产生的原因,是由于浏览器的安全机制,JS只能访问与所在页面同一个域(相同协议.域名.端口)的内容. 但是我们项目开发过程中,经常 ...
随机推荐
- iOS Storyboard约束详解
链接:http://www.jianshu.com/p/b88c65ffc3eb 约束,就是指--此处略去1万字--都懂的,就不说了.直接进入实战环节. 本文的控件约束都是围绕着UITableView ...
- Linux学习——Shell基础
1 shell概述 Shell 是一个命令行解释器,它为用户提供了一个向Linux内核发送请求以便运行程序的界面系统级程序,用户可以用shell来启动,挂起,停止甚至编写一些程序. Shell 还是一 ...
- 风趣的JavaScript面向对象入门课程一
在我们程序猿界一直流传这这么一个joke,没女票我们可以new一个.没房子没票子没车子我们同样new一个!当然这听着更像是一种自嘲,毕竟我们程序猿都爱自嘲,哈哈,废话不多说,今天就由我带着你们来入Ja ...
- Just Finish it up UVA - 11093
Just Finish it up Time Limit: 3000MS Memory Limit: Unknown 64bit IO Format: %lld & %llu [Sub ...
- An Introduction to Variational Methods (5.1)
在这篇文章中,我引用Bishop书中的一个例子,来简单介绍一下Variational Methods的应用.想要更详细地理解这个例子,可以参考Bishop的书Pattern Recongnition ...
- 插入排序的性能测试对比(C与C++实现)
一.概述: [标题]学生成绩管理的设计与实现 [开发语言]C.C++ [主要技术]结构体.STL [基本功能]实现对学生成绩类的基本操作:增加.删除.查询.排序 [测试数据]功能测试:按提示输入5组正 ...
- JDFS:一款分布式文件管理系统,第五篇(整体架构描述)
一 前言 截止到目前为止,虽然并不完美,但是JDFS已经初步具备了完整的分布式文件管理功能了,包括:文件的冗余存储.文件元信息的查询.文件的下载.文件的删除等.本文将对JDFS做一个总体的介绍,主要是 ...
- PIC32MZ 通过USB在线升级 -- USB HID bootloader
了解 bootloader 的实现, 请加QQ: 1273623966(验证填bootloader); 欢迎咨询或定制bootloader; 我的博客主页 www.cnblogs.com/geekyg ...
- 用python爬虫爬取去哪儿4500个热门景点,看看国庆不能去哪儿
前言:本文建议有一定Python基础和前端(html,js)基础的盆友阅读. 金秋九月,丹桂飘香,在这秋高气爽,阳光灿烂的收获季节里,我们送走了一个个暑假余额耗尽哭着走向校园的孩籽们,又即将迎来一年一 ...
- php Socket通信
<?php error_reporting(0); $host = "0.0.0.0"; $port = 1082; $maxUser = 10; set_time_limi ...