XMLHttpRequest

XMLHttpRequest (XHR) 是一個 JavaScript類efn|儘管一些文獻 XMLHttpRequest 稱為API， 從技術上講，它是一個使用 new語句實例化到對象變量的類聲明.，包含將HTTP請求從網絡瀏覽器異步傳輸到網絡服務器的方法。這些方法允許基於瀏覽器的應用程序進行細粒度的服務器調用並把存儲結果存儲在XMLHttpRequest的responseText特性中。 XMLHttpRequest類是Ajax編程的一個組件。在Ajax出現之前，需要將網頁表單完全發送到服務器，然後刷新整個瀏覽器頁面。

**歷史**
“XMLHttpRequest”類背後的概念是由Microsoft Outlook 的開發人員於2000年提出的——可在Windows 2000操作系統上使用。然後這個概念在Internet Explorer 5 (2001) 瀏覽器的 解釋器 中實現。efn|現代瀏覽器使用即時編譯器調用了JavaScript引擎。但是，原始的語法沒有使用XMLHttpRequest標識符。相反，開發人員使用了標識符ActiveXObject("Msxml2.XMLHTTP")和ActiveXObject("Microsoft.XMLHTTP")。 到Internet Explorer 7 (2006)，所有的瀏覽器都支持XMLHttpRequest標識符。
XMLHttpRequest標識符現在是所有現代瀏覽器的事實標準，包括Mozilla的Gecko layout engine (2002), Konqueror (2002), Safari 1.2 (2004), Opera 8.0 (2005),, and iCab (2005).
隨著跨瀏覽器 JavaScript 庫（例如 jQuery）的出現，開發人員可以間接調用 XMLHttpRequest 功能。

**標準**
萬維網聯盟 (W3C)於2006年4月5日發佈了XMLHttpRequest對象的工作草案規範。 efn|該標準是Opera Software的Anne van Kesteren和W3C的Dean Jackson審稿。2008年2月25日，W3C發佈了Working Draft Level 2規範。Level 2規範添加了監視事件進度、允許跨站點請求和處理字節流的方法。2011年底，Level 2規範被吸收到原始規範中。
2012年底，WHATWG接管開發並使用Web IDL維護動態文檔。

**XMLHttpRequest用法**

**構造器**
生成發給Web服務器的異步請求首先要實例化分配內存）“XMLHttpRequest”對象。分配的內存（的地址）被賦值給變量。 JavaScript中實例化新對象的編程 語句 為new。new語句後跟對象的構造函數。面嚮對象語言的開發人員的習慣是使用與類名相同的名稱來調用構造函數本例中，類名是XMLHttpRequest。實例化一個新的XMLHttpRequest並賦值給變量request:
var request = new XMLHttpRequest();

**open方法**
open方法準備XMLHttpRequest。它最多可接受五個參數，但只有前兩個是必須的。
var request = new XMLHttpRequest();
request.open( RequestMethod, SubmitURL, AsynchronousBoolean, UserName, Password );- RequestMethod: 對於典型的數據量，HTTP請求方法可以是GET。在其他可用的請求方法中，POST將處理大量數據。收到返回字符串後，將DELETE請求方法發送到.open()以釋放 XMLHttpRequest 內存。如果發送DELETE，則 SubmitURL 參數可為null。
 * request.open( "DELETE", null );- SubmitURL: SubmitURL是包含執行文件名和提交到Web服務器的任何參數的URL。如果URL包含主機名，則它一定是發送HTML文檔的Web服務器。Ajax支持同源策略。- AsynchronousBoolean: 如果提供該參數，則應將其設置為true。如果設置為false，則瀏覽器將等待，直到收到返回字符串。不鼓勵程序員將AsynchronousBoolean設置為false，瀏覽器可能會遇到異常錯誤。- UserName:如果提供，它將有助於驗證用戶身份。- Password: 如果提供，它將有助於驗證用戶身份。

**setRequestHeader方法**
如果調用POST請求方法，則需要額外發送媒體類型Content-Type: application/x-www-form-urlencoded。setRequestHeader方法允許程序將此或其他HTTP標頭髮送到Web服務器。其用法是setRequestHeader( HeaderField, HeaderValue )。啟用POST請求方法:
request.setRequestHeader( "Content-Type", "application/x-www-form-urlencoded" );

**send方法**
如果調用POST請求方法，則Web服務器期望從標準輸入流讀取表單數據。要將表單數據發送到Web服務器，請執行request.send( FormData )，其中FormData是文本字符串。如果調用GET請求方法，則Web服務器只需要默認標頭。要發送默認標頭，請執行request.send( null ).The null placeholder is currently in retirement but recommended. 

**onreadystatechange事件監聽器**
onreadystatechange是一個回調方法，在整個Ajax生命週期中定期執行。要設置名為 ReadyStateMethod()的回調方法，語法為request.onreadystatechange = ReadyStateMethod。For safety, this assignment should follow the execution of request.open().為了方便起見，該語法允許定義匿名方法。定義匿名回調方法:
var request = new XMLHttpRequest();
request.onreadystatechange = function()
{
// code omitted
}
XMLHttpRequest生命週期經歷幾個階段 - 從0到4。階段0是調用open()方法之前，階段4是文本字符串到達時。為了監視生命週期，XMLHttpRequest具有可用的readyState屬性。 第1-3階段不明確，不同瀏覽器的解釋也不同。儘管如此，一種解釋是：- 階段 0：未初始化- 第一階段：加載中- 第二階段：加載完成- 第三階段：交互- 第四階段：已完成
當readyState達到4時，文本字符串已經到達並被設置在responseText屬性中。
var request = new XMLHttpRequest();
request.onreadystatechange = function()
{
if ( request.readyState == 4 )
{
// request.responseText is set
}
}

**例子**
下例首先創建Javascript函數:- cd /var/www/html- 編輯文件ajax_submit.js:
function ajax_submit( element_id, submit_url )
{
var request = new XMLHttpRequest();
var completed_state = 4;
request.onreadystatechange = function()
{
if ( request.readyState == completed_state )
{
document.
getElementById( element_id ).
innerHTML =
request.responseText;
request.open( "DELETE", null );
}
}
request.open( "GET", submit_url );
request.send( null );
}- 同一個目錄下編輯文件ajax.phtml:
Hello World!';
?>- 同一個目錄下編輯文件ajax.html:
Hello World



Submit
- 在瀏覽器中打開http://localhost/ajax.html- 點擊Submit

**CGI例子**
通用網關接口 (CGI) 進程允許瀏覽器請求Web服務器執行已編譯的計算機程序。
CGI XMLHttpRequest的服務器組件是位於服務器上的可執行文件。操作系統將打開該文件並讀取其機器指令。 XMLHttpRequest協議要求可執行文件輸出文本字符串。
編譯後的程序有兩個文件：源代碼和相應的可執行文件。- cd /usr/lib/cgi-bin- 編輯文件ajax.c:
#include 
void main( void )
{
/* CGI requires the first line to output: */
printf( "Content-type: text/html\n" );
/* CGI requires the second line to output: */
printf( "\n" );
printf( "Hello World!\n" );
}- 編輯源文件產生可執行文件:
cc ajax.c -o ajax
或
sudo cc ajax.c -o ajax
CGI瀏覽器組件與PHP瀏覽器組件相同，只是submit_url略有變化。 告訴Web服務器執行可執行文件的語法是/cgi-bin/後跟文件名。為了安全起見，可執行文件必須駐留在chroot 監獄中。在本例中，監獄是目錄/usr/lib/cgi-bin/.The web server may be configured to add other executable directories.-  cd /var/www/html- 編輯文件ajax.html:
Hello World



Submit
- 用瀏覽器打開http://localhost/ajax.html- 點擊Submit

**參見**
 WebSocket- 表現層狀態轉換 (REST)

**參考文獻**

**註釋**

**外部鏈接**
  XMLHttpRequest Living Standard date=20231108152833  by the WHATWG-  XMLHttpRequest Level 1 date=20231113153254  draft by the W3C