XHR 2.0Z中新增了CORS跨域解决方案
何为跨域的情况?
1.不同域名: 如---> a域名请求b域名中的数据
2.不同端口: 如---> 3000端口下请求8000端口下的数据
3.不同协议: 如---> http协议下请求https协议下的数据
CORS解决方案?
1. 需要服务器配合设置响应头: 如----> header('Access-Control-Allow-Origin: * ');
2. 可选择是否带上cookie;
简单请求和复杂请求的区别?
1. 复杂请求会先发送一次 options 方法的预检请求,简单请求不会
2. 简单请求需要同时满足的条件:
1)请求方式必须为head、get、post中的一个;
2)请求头中的字段不超过Accept ,Accept-Language ,Content-Language ,Last-Event-ID ,Content-Type;
3)Content-Type只限于三个值,application/x-www-form-urlencoded、multipart/form-data、text/plain;
以上三个条件,在请求时,只要有一个不被满足,就会被认为是复杂请求;
例如自定义一个请求头字段去发送请求:
function ajax(){ //兼容IE写法 考虑兼容性
//实例化请求对象
var xhr = window.XMLHttpRequest ? (new XMLHttpRequest()) : (new ActiveXObject('Mircosoft.XMLHTTP'));
var src = 'http://sub.local.com/cors-data.php';
//确定请求方式,路径,同步或者异步
//第三个参数默认为true,默认为异步
xhr.open('GET',src);
//自定义请求头 此时会出现跨域问题,需要服务端设置对应的响应头才可解决
xhr.setRequestHeader('abc','123');
//设置响应数据类型
xhr.responseType = 'json';
//发送请求
xhr.send();
//监听请求状态
xhr.onreadystatechange = function(){
if(xhr.readyState === 4 && xhr.status === 200){
//设置responseType之后,响应数据为对象形式
//需用stringify方法转化为json格式数据
console.log(JSON.stringify(xhr.response,null,2));
}
}
}
服务器端响应头字段设置?
1.Access-Control-Allow-Origin
1)表示允许访问的域名
2)必须在响应头中设置该字段
3)可使用 * 号表示允许任意域名
2.Access-Control-Allow-Credentials
1)值只能设为true,表示允许前端向服务器发送cookie;
2)客户端也需要设置XHR对象的widthCredentials为true,配合服务器端;
3)Access-Control-Allow-Origin必须设置为指定域名,不能为 * 号;
例如(在跨域的情况下,客户端与服务器端沟通cookie):
document.cookie = 'name=client;' //设置cookie的值
function ajax(){
//兼容IE写法 考虑兼容性
//实例化请求对象
var xhr = window.XMLHttpRequest ? (new XMLHttpRequest()) : (new ActiveXObject('Mircosoft.XMLHTTP'));
var src = 'http://sub.local.com/cors-data.php';
//确定请求方式,路径,同步或者异步
//第三个参数默认为true,默认为异步
xhr.open('GET',src);
//自定义请求头 此时会出现跨域问题,需要服务端设置对应的响应头才可解决
xhr.setRequestHeader('abc','123');
//设置响应数据类型
xhr.responseType = 'json';
//设置widthCredentials属性
xhr.withCredentials = true;
//发送请求
xhr.send();
//监听请求状态
xhr.onreadystatechange = function(){
if(xhr.readyState === 4 && xhr.status === 200){
//设置responseType之后,响应数据为对象形式
//需用stringify方法转化为json格式数据
console.log(JSON.stringify(xhr.response,null,2));
}
}
}
此时服务端需要设置: 1)Access-Control-Allow-Credentials 为true;
2)Access-Control-Allow-Origin 只能指定一个域名
3)还需要设置相应cookie的值
注意,此时的ajax请求,前端所接收到的cookie值并不是自己设置的那个,而是服务器给响应的值;
3.Access-Control-Expose-Headers
1)表示允许客户通过getResponseHeader方法获取的字段;
2)CORS方式下该方法默认只能获取6个基础字段;分别是: Cache-Control / Content-Language / Content-Type / Expires / Last-Modified / Pragma