Ajax和XMLHttpRequest
我們通常將Ajax等同于XMLHttpRequest,但細究起來它們兩個是屬于不同維度的2個概念。
以下是我認為對Ajax較為準確的解釋:(摘自what is Ajax)
AJAX stands for Asynchronous JavaScript and XML. AJAX is a new technique for creating better, faster, and more interactive web applications with the help of XML, HTML, CSS, and Java Script.
AJAX is based on the following open standards:
Browser-based presentation using HTML and Cascading Style Sheets (CSS).
Data is stored in XML format and fetched from the server.
Behind-the-scenes data fetches using XMLHttpRequest objects in the browser.
JavaScript to make everything happen.
從上面的解釋中可以知道:ajax是一種技術(shù)方案,但并不是一種新技術(shù)。它依賴的是現(xiàn)有的CSS/HTML/Javascript,而其中最核心的依賴是瀏覽器提供的XMLHttpRequest對象,是這個對象使得瀏覽器可以發(fā)出HTTP請求與接收HTTP響應(yīng)。
所以我用一句話來總結(jié)兩者的關(guān)系:我們使用XMLHttpRequest對象來發(fā)送一個Ajax請求。
XMLHttpRequest的發(fā)展歷程
XMLHttpRequest一開始只是微軟瀏覽器提供的一個接口,后來各大瀏覽器紛紛效仿也提供了這個接口,再后來W3C對它進行了標準化,提出了XMLHttpRequest標準。XMLHttpRequest標準又分為Level 1和Level 2。
XMLHttpRequest Level 1主要存在以下缺點:
受同源策略的限制,不能發(fā)送跨域請求;
不能發(fā)送二進制文件(如圖片、視頻、音頻等),只能發(fā)送純文本數(shù)據(jù);
在發(fā)送和獲取數(shù)據(jù)的過程中,無法實時獲取進度信息,只能判斷是否完成;
那么Level 2對Level 1 進行了改進,XMLHttpRequest Level 2中新增了以下功能:
可以發(fā)送跨域請求,在服務(wù)端允許的情況下;
支持發(fā)送和接收二進制數(shù)據(jù);
新增formData對象,支持發(fā)送表單數(shù)據(jù);
發(fā)送和獲取數(shù)據(jù)時,可以獲取進度信息;
可以設(shè)置請求的超時時間;
當然更詳細的對比介紹,可以參考阮老師的這篇文章,文章中對新增的功能都有具體代碼示例。
XMLHttpRequest兼容性
關(guān)于xhr的瀏覽器兼容性,大家可以直接查看“Can I use”這個網(wǎng)站提供的結(jié)果,下面提供一個截圖。
從圖中可以看到:
IE8/IE9、Opera Mini 完全不支持xhr對象
IE10/IE11部分支持,不支持 xhr.responseType為json
部分瀏覽器不支持設(shè)置請求超時,即無法使用xhr.timeout
部分瀏覽器不支持xhr.responseType為blob
細說XMLHttpRequest如何使用
先來看一段使用XMLHttpRequest發(fā)送Ajax請求的簡單示例代碼。
上面是一個使用xhr發(fā)送表單數(shù)據(jù)的示例,整個流程可以參考注釋。
接下來我將站在使用者的角度,以問題的形式介紹xhr的基本使用。
我對每一個問題涉及到的知識點都會進行比較細致地介紹,有些知識點可能是你平時忽略關(guān)注的。
如何設(shè)置request header
在發(fā)送Ajax請求(實質(zhì)是一個HTTP請求)時,我們可能需要設(shè)置一些請求頭部信息,比如content-type、connection、cookie、accept-xxx等。xhr提供了setRequestHeader來允許我們修改請求 header。
void setRequestHeader(DOMString header, DOMString value);
注意點:
方法的第一個參數(shù) header 大小寫不敏感,即可以寫成content-type,也可以寫成Content-Type,甚至寫成content-Type;
Content-Type的默認值與具體發(fā)送的數(shù)據(jù)類型有關(guān),請參考本文【可以發(fā)送什么類型的數(shù)據(jù)】一節(jié);
setRequestHeader必須在open()方法之后,send()方法之前調(diào)用,否則會拋錯;
setRequestHeader可以調(diào)用多次,最終的值不會采用覆蓋override的方式,而是采用追加append的方式。下面是一個示例代碼:
varclient=newXMLHttpRequest();client.open('GET','demo.cgi');client.setRequestHeader('X-Test','one');client.setRequestHeader('X-Test','two');// 最終request header中"X-Test"為: one, twoclient.send(); 如何獲取response header
評論
查看更多