AJAX的學習筆記(二)

在上篇筆記中,咱們主要談了一些概述和跨域的問題,這一次咱們聊聊請求和響應的具體內容。

向服務器發起請求

咱們在建立了XHR對象後,接着須要用兩個方法來發送請求:open()和send(),這兩個方法有點像賽跑前的兩個步驟:預備、跑。在open()中,並無實際發送請求,只是一個「預備」動做,真正的發送要到send()中了。php

open和send

open()能夠傳遞三個參數:html

  1. method:請求的類型,GET或POST之類;
  2. url:文件在服務器的位置;
  3. async:同步或是異步,默認異步,當選擇默認時,咱們能夠選擇不填這個參數。

send()的參數只有一個,是運用在post方式的請求中,以string的形式。前端

如下是一個例子:segmentfault

xhr.open("GET","example.php",true);
xhr.send();
//post不須要傳遞參數;
xhr.open("POST","example.php",true);
xhr.send();
//post須要傳遞參數;
xhr.open("POST","example.php",true);
xhr.setRequestHeader("Content-type","application/x-www-form-urlcoded");
xhr.send("fname=henry&lname=ford")

get和post

get經常使用於查詢數據,有時候,須要咱們用某種指定的格式把參數追加到url的末尾。若是格式不正確的話,會出現錯誤。跨域

舉一個例子:瀏覽器

xhr.open("get","example.php?name1=value1&name2=value2",true");
xhr.send();

post多用於向服務器提交應該被保存的數據。與get不一樣的是,post應該以發送的數據做爲請求的主體。參數則不須要寫在url裏了,而是寫在send裏,在這裏,能夠傳遞XML DOM文檔也能夠傳遞字符串。固然,要注意的是,若是隻是簡單的,沒有數據傳遞的POST請求,那麼和GET請求同樣,在send()中不須要添加什麼。若是須要POST數據,我麼要用setRequestHeader()來添加HTTP頭,而後在send()中用參數的形式添加數據傳遞。服務器

HTTP頭部信息

每一個HTTP請求都帶有頭信息,因此咱們發送一個AJAX請求時,實際上也會發送相關的頭信息。默認狀況下,下列的頭信息會被髮送出去:app

  • Accept;
  • Accept-Charset;
  • Accept-Ending;
  • Accept-Language;
  • Connection;
  • Cookie;
  • Host;
  • Refer;
  • User-Agent;

使用setRequestHeader()能夠設置自定義的頭信息。這個方法接收兩個參數:頭部字段的名稱和值。例如:異步

xhr.setRequestHeader("Content-type","application/x-www-form-urlcoded");

xhr.setRequestHeader("MyHeader","MyValue");

要注意的是setRequestHeader方法須要在open()和send()中間設置,這樣才能成功發送請求的頭部信息。async

服務器響應

當咱們發送請求後,一切順利,服務器也順利發回了響應,那麼咱們要怎麼來獲取這些響應呢?

responseText和responseXML

這是獲取兩種不一樣格式的響應,esponseText是字符串形式,responseXML則是XML形式。

舉一個例子:

var xhr;
if(window.XMLHttpRequest){
  xhr=new XMLHttpRequest();
}else{
  xhr=new ActiveXObject("Microsoft.XMLHTTP");
}
xhr.onreadystatechange=function(){
  if(xhr.readyState==4 && xhr.status==200){
    document.getElementById("myDiv").innerHTML=xhr.responseText;
  }
}
xhr.open("get","example.php",true);
xhr.send();

就是這樣。

XHR 2級

XHR的發展也促使W3C着手製定更爲完善的2級規範。在這套規範裏,有一些內容須要瞭解。

FormData

爲了實現表單數據的序列化,在Web應用中更方便地傳輸數據,2級規範定義了FormData類型。

下面是一個建立FormData實例的例子:

<form id="myForm" action="" method="post">
    <input type="text" name="name">名字
    <input type="password" name="psw">密碼
    <input type="submit" value="提交">
</form>
var data=new FormData();
//直接添加鍵值對
data.append("nama","Mike");
//經過向構造函數中傳入表單元素也可
  //這是一個表單元素
var form=document.getElementById("myForm");
  //傳入
var data=new FormData(form);
xhr.send(data);
  //獲取
var name=data.get("name");
var psw=data.get("psw");

建立了FormData的實例後,能夠直接傳到send中。

關於更詳細的FormData知識,請參考這篇文章:
系統學習前端之FormData詳解 - 前端與生活 - SegmentFault

超時設置

最先是IE8爲XHR添加了timeout屬性,後來被XHR 2級規範收入。

當給timeout設置了數值後,規定時間內沒有響應,就會觸發timoeout事件,進而調用ontimeout。

這是一個例子:

var xhr;
...
xhr.open("get","example.php",true);
xhr.timeout=1000;
xhr.ontimeout=function(){
  alert("Request is not return in a second"
};
xhr.send();

進度事件

XHR 2的進度事件定義了XHR在請求的不一樣階段觸發不一樣的事件,具體的有6個事件:

  • loadstart;
  • progress;
  • error;
  • abort;
  • load;
  • loadend;

每一個瀏覽器所支持的事件不徹底相同,好比IE8就支持load事件。有了這些不一樣的事件支持,開發者能夠免去檢查readyState之類的工做,更加的方便。

其中load事件和progress事件比較重要。load事件會在接收到完整的響應數據時觸發,所以咱們就不須要再檢查readyState屬性了,只要確保XHR的status爲200就能夠了。

progress事件則會爲XHR在瀏覽器接收數據期間週期性地觸發。在觸發時,它會額外地提供三個屬性:

  1. lengthComputable;表示進度信息是否可用
  2. position;表示已經接收的字節數
  3. totalSize;表示響應頭肯定的預期字節數

有了這些信息,咱們能夠創造一個進度指示器:

var xhr=createXHR();
xhr.onload=function(event){
...
}
xhr.onprogress=function(event){
  var divStatus=document.getElementById("status");
if(event.lengthCoputable){
  divStatus.innerHTML="Reiceived"+event.position+"of"+event.totalSize+"bytes";
}
};

這裏要注意的是:必須在調用open()方法以前添加progress事件處理程序。

相關文章
相關標籤/搜索