XMLHttpRequest对象
创建XHR对象(IE7+,其他浏览器)
var xhr = new XMLHttpRequest();
XHR用法
启动一个请求,使用open()
方法,接受3个参数,要发送的请求类型,请求URL(相对或绝对路径)和表示是否异步的布尔值
xhr.open("get","example.php",false);
发送请求,使用send()
方法,接受一个参数,即要作为请求主体发送的数据,不发送数据为null
xhr.send(null);
当浏览器接受到响应后,响应的数据会自动充填到XHR对象的属性中
- responseText:作为响应主体返回的文本
- responseXML:当响应类型为”text/xml”或”application/xml”时,此属性将包含XML DOM文档信息
- status:响应的HTTP状态
- statusText:HTTP状态的说明
XHR对象的readyState属性表示请求的/响应过程的活动阶段,当值为4时,表示响应已经接受完毕,每次状态变化,都会触发readystatechange事件,可以利用此事件来检测状态
xhr.onreadstatechange = function(){
if (xhr.readyState == 4){
if ((xhr.status >=200 && xhr.status <300) || xhr.status == 304){ //接受成功时
alert(xhr.responseText);
}else{
alert("接受失败:" + xhr.status);
}
}
};
收到响应之前,还可以使用xhr.abort()
方法取消异步请求
设置和获取HTTP头部消息
使用setRequestHeader()
方法可以设置自定义的请求头部信息,接受两个参数,头部字段的名称和值。该方法必须在调用open()
方法之后,且调用send()
方法之前调用。
var xhr = new XMLHttpRequest();
xhr.open("get","example.php",true);
xhr.setRequestHeader("Myheader","Myvalue");
xhr.send(null);
调用getResponseHeader()
方法,并传入头部字段名称,可以获取相应的响应头部信息。而调用getAllResponseHeaders()
可以获取包含所有头部信息的长字符串。
var myHeader = xhr.getResponseHeader("MyHeader");
var allHeaders = xhr.getAllResponseHeaders();
GET请求
可以在传入open()方法的URL末尾添加查询字符串,但名称和值必须经过encodeURIComponent()
方法正确的编码才可以
name = encodeURIComponent(name);
value = encodeURIComponet(value);
xhr.open("get", "example.php?"+name+"="+value, true);
POST请求
若为POST请求,则需将数据序列化后,传入send()
方法中,模仿表单提交,需将Content-Type头部信息设置为application/x-www-form-urllencoded
xhr.open("post","example.php",true);
xhr.setRequestHeader("Content-Type","application/x-www-form-urllencoded");
data="name1=value1&name2=value2&name3=value3";
xhr.send(data);
XMLHttpRequest 2级
FormData
FormData为序列化表单以及创建与表单格式相同的数据提供了便利。可以向FormData构造函数中传入表单元素,也可以用表单元素的数据预先向其中填入键值对。创建了实例后,可以直接将其传给send()
方法。
var data = new FormData(document.forms[0]); //直接传入表单元素
xhr.send(data);
var data = new FormData();
data.append("name","zjw"); //传入键值对
xhr.send(data);
超时设定
XHR对象的timeout属性,表示在等待响应多少毫秒之后就终止。当超时终止请求之后,再访问status属性,将会出现错误。
xhr.open("get","timeout.php",true);
xhr.timeout = 1000; //将超时设置为1秒钟
xhr.ontimeout = function(){
alert("error");
};
xhr.send(null);
重写XHR响应的MIME类型
调用overrideMimeType()
方法可以重写MIME类型,必须在调用send()
方法之前调用
xhr.open("get","text.php",true);
xhr.overrideMimeType("text/xml"); //将MIME类型重写为"text/xml"
xhr.send(null);
进度事件
- loadstart:在接受到响应数据的第一个字节时触发
- progress:接受期间不断触发,其中event对象具有lengthComputable(表示进度信息是否可用的布尔值)、position(已接受的字节数)、totalSize(总字节数)属性
- error:请求发生错误时触发
- abort:调用abort()方法,而终止连接时触发
- load:接受到完整的响应数据时触发,可以替代readystatechange事件,无需再检测readyState属性是否等于4
- loadend:通信完成或触发error、abort、load事件后触发
xhr.onload = function(){
if ((xhr.status >=200 && xhr.status <300) || xhr.status == 304){ //接受成功时
alert(xhr.responseText);
}else{
alert("接受失败:" + xhr.status);
}
};
xhr.onprogress = function(event){
var divstatus = document.getElementById("status");
if (event.lengthComputable){
divstatus.innerHTML = event.position / event.totalSize *100 + "%";
}
};
xhr.open("get","events.php",true);
xhr.send(null);
跨域源资源共享
CORS(Cross-Origin Resource Sharing)定义了在必须访问跨域资源时,浏览器与服务器应该如何沟通。其基本思想是使用自定义的HTTP头部让浏览器与服务器进行沟通,决定请求或响应是接受或拒绝。注意请求和响应都不包含Cookie信息。
浏览器请求附加头部
Origin:http://www.nczonline.net
如果服务器认为请求可接受,将会返回对应的头部信息
Access-Control-Allow-Origin:http://www.nczonline.net
浏览器接受到这个响应的头部信息,若信息匹配正确,将会处理。
IE对CORS的实现
IE引入了XDR对象,来实现CORS,该对象的大部分方法和属性与XHR类似
var xdr = new XDomainRequest(); //创建XDR对象
xdr.onload = function(){
alert(xdr.responseText);
};
xdr.open("get","https://www.zjw666.top/example"); //只接受两个参数,不支持同步执行
xdr.send(null);
- XDR对象也具有timeout属性以及contentType属性,用于在POST请求中表示数据格式
其他浏览器对CORS的实现
其他浏览器都通过XHR对象实现了CORS,访问其他域资源非常简单,直接在open()
方法中传入绝对URL即可,且支持异步和同步请求
xhr.open("get","http://www.zjw666.com/123",true);
- 当跨域请求资源时,不能使用
setRequestHeader()
方法设置头部信息 - 不能发送和接受Cookie
- 调用
getAllResponseHeaders()
方法,总会返回空字符串
其他跨域技术
图像Ping
最常用语跟踪用户点击页面或动态广告的曝光次数
img.onload = img.onerror = function(){
alert("done");
};
img.src = "http://www.zjw666.top";
JSONP
是JSON with padding的简写,JSONP由两部分组成:回调函数和数据。回调函数是当响应到来时应该在页面调用的函数
返回数据
callback({"name":"zjw"});
典型的请求
http://freegeoip.net/json/?callback=handleResponse // 此处回调函数名为handleResponse
使用<script>
元素使用JSONP的例子
function handleResponse(response){
alert(response.ip);
}
var script = document.createElement("script");
script.src = "http://freegeoip.net/json/?callback=handleResponse";
document.body.insertBefore(script,document.body.firstChild);