1

XMLHttpRequest可解释为可扩展超文本传输请求。它是一个浏览器Api,为客户端提供了在客户端和服务器之间传输数据的功能。使得Javascript可以进行HTTP(S)通信。特点是能在不更新页面的情况下获取数据,这使得网页只更新一部分页面而不会打扰到用户。我们常接触的Ajax的核心就是XMLHttpRequest。

一次完整的XMLHttpRequest请求

图片描述

对于很多js对象来说,都会有状态事件方法。其中的状态和事件其实就是对象的属性。状态大多是一个值为function的属性。同样的,XMLHttpRequest也有这三样东西。

XMLHttpRequest状态readyState

XMLHttpRequest有一下5种状态:

0——unsent未打开————————————open()方法还未被调用
1——opened为发送————————————send()方法还未被调用
2——HEADERS_RECEIVED已获取响应头——send()方法已经被调用, 响应头和响应状态已经返回
3——LOADING正在下载响应体———————响应体下载中; responseText中已经获取了部分数据
4——DONE请求完成————————————整个请求过程已经完毕

XMLHttpRequest的事件

onreadystatechange()

XMLHttpRequest提供了一个onreadystatechange事件用于监听XMLHttpRequest状态的改变。当状态改变时会触发此方法,用于对不同状态下进行处理,包括完成后的数据处理、发生错误时关闭请求的处理、请求超时的处理等。
一个简单的例子:

objXMLHttp.onreadystatechange =  processResponse(){
    if(objXMLHttp.readyState == 1){
        alert("XMLHttpRequest对象开始发送请求");
    }else if(objXMLHttp.readyState == 2){
        alert("XMLHttpRequest对象的请求发送完成");
    }else if(objXMLHttp.readyState == 3){
        alert("XMLHttpRequest对象开始读取服务器的响应");
    }else if(objXMLHttp.readyState == 4){
        alert("XMLHttpRequest对象读取服务器响应结束");
        if(objXMLHttp.status == 200){
            //信息已经成功返回,开始处理信息
            //先捕获下所有的请求头
            var headers = objXMLHttp.getAllResponseHeaders();
            alert("所有的请求头= "+headers);
            //得到服务器返回的信息
            var infor = objXMLHttp.responseText;
            alert("服务器端的响应 = "+infor);
        }else{
            alert("所请求的服务器端出了问题");
        }
    }
}

ontimeout
让请求时长超过设定的时间时触发此方法,可在此方法中关闭此次请求;

objXMLHttp.timeout = 5000;// 设定请求最大时长
objXMLHttp.ontimeout = function() {
    alert('请求超时!')
    objXMLHttp.abort();//关闭此次请求
}

onprogress
新版本的XMLHttpRequest(XMLHttpRequest2)对象,传送数据的时候,有一个progress事件,用来返回进度信息。
它分成上传和下载两种情况。下载的progress事件属于XMLHttpRequest对象,上传的progress事件属于XMLHttpRequest.upload对象

// 定义一个共用方法
function updateProgress(event) {
    if (event.lengthComputable) {
      var percentComplete = event.loaded / event.total;
    }
  }
// 在两个事件上都引用此方法
xhr.onprogress = updateProgress;
xhr.upload.onprogress = updateProgress;

其中:
event.lengthComputable 长度可计算(true或false)
event.loaded 接收的字节数
event.total 总字节数

除了以上事件,XMLHttpRequest还有以下事件,可根据个人需要去实现对应的方法。

  * load事件:传输成功完成。
  * abort事件:传输被用户取消。
  * error事件:传输中出现错误。
  * loadstart事件:传输开始。
  * loadEnd事件:传输结束,但是不知道成功还是失败。

XMLHttpRequest的其他属性

除了上面的状态和事件,XMLHttpRequest还有一些其他的属性,用于配置或储存数据。常用的有responseText、responseType、status等


responseType: 设置响应类型,告诉服务器你期望的响应格式(即返回的数据格式),默认为""代表字符串。可选参数:"arraybuffer"、"blob"、"document"、"json"、"text"
response: 响应实体的类型由 responseType 来指定, 可以是 ArrayBuffer, Blob, Document, JavaScript 对象 (即 "json"), 或者是字符串。如果请求未完成或失败,则该值为 null
responseXML: 本次请求的响应是一个 Document 对象,如果是以下情况则值为 null:请求未成功,请求未发送,或响应无法被解析成 XML 或 HTML。当响应为text/xml 流时会被解析。当 responseType 设置为"document",并且请求为异步的,则响应会被当做 text/html 流来解析
responseText:此次请求的响应为文本,或是当请求未成功或还未发送时为 null


status:该请求的响应状态(200、404、500等,更多值可参考http://tools.jb51.net/table/h...

statusText:该请求的响应状态信息,包含一个状态码和原因短语 (例如 "200 OK")

timeout:超时毫秒数,同步请求不可用。默认是0,永不超时。在 open() 和 send() 之间设置,超时会触发 xhr 的 timeout 事件

upload:只读,ajax 上传对象

withCredentials: Boolean,是否允许跨域响应设置cookie,默认是 false

XMLHttpRequest的方法

open()

初始化一个请求.此方法可以对需要请求的url进行初始化才操作,包括设置请求类型、请求连接、是否异步等

open()接收的参数

XMLHttpRequest.open(method,url,async,user,password);

method: 请求所使用的HTTP方法; 例如 "GET", "POST", "PUT", "DELETE"等. 如果下个参数是非HTTP(S)的URL,则忽略该参数.
url:该请求所要访问的URL
async: 一个可选的布尔值参数,默认为true,意味着是否执行异步操作
user:用户名,可选参数,为授权使用;默认参数为空string
password:密码,可选参数,为授权使用;默认参数为空string

setRequestHeader()

给指定的HTTP请求头赋值.在这之前,你必须确认已经调用 open() 方法打开了一个url.

该方法接收两个参数,一个是头名称一个是对应的值

//两个参数均为字符串
XMLHttpRequest.setRequestHeader("Content-Type","application/x-www-form-urlencoded; charset=gb2312")

对应的headers有哪些可以查阅:

http://tools.jb51.net/table/h...

send()

发送请求. 如果该请求是异步模式(默认),该方法会立刻返回. 相反,如果请求是同步模式,则直到请求的响应完全接受以后,该方法才会返回.

send()方法接收一个参数,表示请求发出时的请求体

XMLHttpRequest.send(data);

该参数也可以是一下几种形式:ArrayBuffer、Blob 、Document 、DOMString、FormData。

abort()

如果请求已经被发送,则立刻中止请求,此方法多用于超时的请求情况,在请求已发送但还未完成的这段过程中都可以调用此方法

XMLHttpRequest.abort();

getResponseHeader()

获取XMLHttpRequest的对应传入的响应头,如果传入的响应头不存在或响应头还没被接受,则返回null。

XMLHttpRequest.getResponseHeader(ResponseHeaderKay);

getAllResponseHeader()

返回所有响应头信息(响应头名和值), 如果响应头还没接受,则返回null

overrideMimeType()

重写由服务器返回的MIME type。这个可用于, 例如,强制把一个响应流当作“text/xml”来处理和解析,即使服务器没有指明数据是这个类型。注意,这个方法必须在send()之前被调用。

XMLHttpRequest.overrideMimeType(DOMString mimetype);

一个标准的XMLHttpRequest请求

step 1: 创建一个XMLHttpRequest对象

var objXMLHttp;
// 创建XMLHttpRequest对象
function createXMLHttpRequest(){
    //对于Firefox,Opera等遵守DOM 2规范的浏览器
    if(window.XMLHttpRequest){
        objXMLHttp = new XMLHttpRequest();
    }
    //对于IE浏览器
    else{
        //将IE浏览器不同的XMLHttp实现声明为数组
        var MSXML = ['MSXML2.XMLHTTP.5.0', 'MSXML2.XMLHTTP.4.0', 'MSXML2.XMLHTTP.3.0', 'MSXML2.XMLHTTP', 'Microsoft.XMLHTTP'];
        //依次对每个XMLHttp创建XMLHttpRequest对象
        for(var i = 0; n< MSXML.length; i++){
            try{
                //微软发布的是ActiveX控件
                objXMLHttp = new ActiveXObject(MSXML[i]);
                //如果正常创建XMLHttpRequest对象就使用break跳出循环
                break;
            }catch(e){
                alert("创建XMLHttpRequest对象失败");
            }
        }
    }    
}

step 2: 封装一个POST请求方法

/**
 * 通过post方式提交
 * 接收三个参数,分别是请求路径,请求体,是否异步
 * */
function postSend(url,data,async){
     // 默认async为true
     if(typeof async === 'undefined') {
         async = true;
     }
    //调用刚才定义的方法,初始化XMLHttpRequest对象
    createXMLHttpRequest();
    //打开与服务器的连接,使用post方式
    objXMLHttp.open('POST', url, async);
    //post方式需要设置请求消息头
    objXMLHttp.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");
    //设置处理响应的回调函数
    objXMLHttp.onreadystatechange = onChange;
    //发送请求并设置参数,参数的设置为param=value的形式
    objXMLHttp.send(data);
}

step 3: 封装一个监听请求状态的方法

/**
 * 设定的回调函数
 * */
function onChange(){
    //响应完成且响应正常
    if(objXMLHttp.readyState == 1){
        alert("XMLHttpRequest对象开始发送请求");
    }else if(objXMLHttp.readyState == 2){
        alert("XMLHttpRequest对象的请求发送完成");
    }else if(objXMLHttp.readyState == 3){
        alert("XMLHttpRequest对象开始读取服务器的响应");
    }else if(objXMLHttp.readyState == 4){
        alert("XMLHttpRequest对象读取服务器响应结束");
        if(objXMLHttp.status == 200){
            //信息已经成功返回,开始处理信息
            //先捕获下所有的请求头
            var headers = objXMLHttp.getAllResponseHeaders();
            alert("所有的请求头= "+headers);
            //得到服务器返回的信息
            var infor = objXMLHttp.responseText;
            alert("服务器端的响应 = "+infor);
        }else{
            alert("所请求的服务器端出了问题");
        }
    }
}

step 4: 调用Post请求

    var data = {
        id: '123456',
        name: '拉普拉斯的魔女'
    }
    Postsend('https://baidu.com/book/IT',data,true);

参考:

http://www.cnblogs.com/shenli...
http://www.ruanyifeng.com/blo...
https://developer.mozilla.org...


ermu
500 声望117 粉丝

不行啊,要上班