在 JavaScript 中,一般將格式設定為 XML、HTML、JSON 或其他純文字格式。具體使用哪種響應格式,可以參考下面幾條原則。
-
如果向頁面中新增大塊資料,選擇 HTML 格式會比較方便。
-
如果需要共同作業開發,且專案龐雜,選擇 XML 格式會更通用。
-
如果要檢索複雜的資料,且結構複雜,那麼選擇 JSON 格式更加輕便。
獲取 XML 資料
XMLHttpRequest 物件通過 responseText、responseBody、responseStream 或 responseXML 屬性獲取響應資訊,說明如下表所示,它們都是唯讀屬性。
XMLHttpRequest 物件響應資訊屬性
響應資訊 |
說明 |
responseBody |
將響應資訊正文以 Unsigned Byte 陣列形式返回 |
responseStream |
以 ADO Stream 物件的形式返回響應資訊 |
responseText |
將響應資訊作為字串返回 |
responseXML |
將響應資訊格式化為 XML 文件格式返回 |
範例1
在伺服器端建立一個簡單的 XML 文件。
<?xml version="1.0" encoding="utf-8"?>
<the>XML 資料</the>
然後,在用戶端進行如下請求。createXHR() 方法在建立 XMLHttpRequest 物件中講解過。
<input name="submit" type="button" id="submit" value="向伺服器發出請求" />
<script>
window.onload = function () { //頁面初始化
var b = document.getElementsByTagName("input")[0];
b.onclick = function () {
var xhr = createXHR(); //範例化XMLHttpRequest物件
xhr.open("GET", "server.xml", true); //建立連線,要求非同步響應
xhr.onreadystatechange = function () { //係結響應狀態事件監聽函數
if (xhr.readyState == 4) { //監聽readyState狀態
if (xhr.state == 200 || xhr.status == 0) { //監聽HTTP狀態碼
var info = xhr.responseXML;
console.log(info.getElementsByTagName("the")[0].firstChild.data); //返回元資訊字串“XML 資料”
}
}
}
xhr.send(); //傳送請求
}
}
</script>
在上面程式碼中,使用 XML DOM 的 getElementsByTagName() 方法獲取 the 節點,然後再定位第一個 the 節點的子節點內容。此時如果繼續使用 responseText 屬性來讀取資料,則會返回 XML 原始碼字串。
範例2
以範例 1 為例,使用伺服器端指令碼生成 XML 結構資料。
<?php
header('Content-Type: text/html;');
echo '<?xml version="1.0" encoding="utf-8"?><the>XML 資料</the>'; //輸出XML
?>
獲取 HTML 字串
設計響應資訊為 HTML 字串,然後使用 innerHTML 把獲取的字串插入到網頁中。
範例
在伺服器端設計響應資訊為 HTML 結構程式碼。
<table border="1" width="100%">
<tr><td>RegExp.exec()</td><td>通用的匹配模式</td></tr>
<tr><td>RegExp.test()</td><td>檢測一個字串是否匹配某個模式</td></tr>
</table>
然後在用戶端可以這樣接收響應資訊。
<input name="submit" type="button" id="submit" value="向伺服器發出請求" />
<script>
window.onload = function () { //頁面初始化
var b = document.getElementsByTagName("input")[0];
b.onclick = function () {
var xhr = createXHR(); //範例化XMLHttpRequest物件
xhr.open("GET", "server.xml", true); //建立連線,要求非同步響應
xhr.onreadystatechange = function () { //係結響應狀態事件監聽函數
if (xhr.readyState == 4) { //監聽readyState狀態
if (xhr.state == 200 || xhr.status == 0) { //監聽HTTP狀態碼
var o = document.getElementById("grid");
o.innerHTML = xhr.responseText; //直接插入到頁面中
}
}
}
xhr.send(); //傳送請求
}
}
</script>
在某些情況下,HTML 字串可能為用戶端解析響應資訊節省了一些 JavaScript 指令碼,但是也帶來了一些問題。
-
響應資訊中包含大量無用的字元,響應資料會變得很臃腫。因為 HTML 標記不含有資訊,完全可以把它們放置在用戶端,由 JavaScript 指令碼負責生成。
-
響應資訊中包含的 HTML 結構無法有效利用,對於 JavaScript 指令碼來說,它們僅僅是一堆字串。同時結構和資訊混合在一起,也不符合標準化設計原則。
獲取 JavaScript 指令碼
設計相應為 JavaScript 程式碼,與 JSON 資料不同,它是可執行的命令或指令碼。
範例
在伺服器端請求檔案中包含下面一個函數。
function () {
var d = new Date();
return d.toString();
}
然後在用戶端執行下面的請求。
<input name="submit" type="button" id="submit" value="向伺服器發出請求" />
<script>
window.onload = function () { //頁面初始化
var b = document.getElementsByTagName("input")[0];
b.onclick = function () {
var xhr = createXHR(); //範例化XMLHttpRequest物件
xhr.open("GET", "server.xml", true); //建立連線,要求非同步響應
xhr.onreadystatechange = function () { //係結響應狀態事件監聽函數
if (xhr.readyState == 4) { //監聽readyState狀態
if (xhr.state == 200 || xhr.status == 0) { //監聽HTTP狀態碼
var info = xhr.responseText;
var o = eval("(" + info + ")" + "()"); //用eval()把字串轉換為指令碼
console.log(o); //返回用戶端當前資訊
}
}
}
xhr.send(); //傳送請求
}
}
</script>
使用 eval() 方法時,在字串前後附加兩個小括號:一個是包含函數結構體的,一個是表示呼叫函數的。不建議直接使用 JavaScript 程式碼作為響應格式,因為它不能傳遞更豐富的資訊,同時 JavaScript 指令碼極易引發安全隱患。
獲取 JSON 資料
使用 responseText 可以獲取 JSON 格式的字串,然後使用 eval() 方法將其解析為本地 JavaScript 指令碼,再從該資料物件中讀取資訊。
範例
在伺服器端請求檔案中包含下面 JSON 資料。
{ user : "css8", pass : "123456", email : "[email protected]" }
然後在用戶端執行下面的請求。把返回 JSON 字串轉換為物件,然後讀取屬性值。
<input name="submit" type="button" id="submit" value="向伺服器發出請求" />
<script>
window.onload = function () { //頁面初始化
var b = document.getElementsByTagName("input")[0];
b.onclick = function () {
var xhr = createXHR(); //範例化XMLHttpRequest物件
xhr.open("GET", "server.xml", true); //建立連線,要求非同步響應
xhr.onreadystatechange = function () { //係結響應狀態事件監聽函數
if (xhr.readyState == 4) { //監聽readyState狀態
if (xhr.state == 200 || xhr.status == 0) { //監聽HTTP狀態碼
var info = xhr.responseText;
var o = eval("(" + info + ")"); //呼叫eval()把字串轉換為本地指令碼
console.log(info); //顯示JSON物件字串
console.log(o.user); //讀取物件屬性值,返回字串“css8”
}
}
}
xhr.send(); //傳送請求
}
}
</script>
eval() 方法在解析 JSON 字串時存在安全隱患。如果 JSON 字串中包含惡意程式碼,在呼叫回撥函數時可能會被執行。解決方法:先對 JSON 字串進行過濾,遮蔽掉敏感或惡意程式碼。不過,確信所響應的 JSON 字串是安全的,沒有被人惡意攻擊,那麼可以使用 eval() 方法解析 JSON 字串。
獲取純文字
對於簡短的資訊,可以使用純文字格式進行響應。但是純文字資訊在傳遞過程中容易丟失,且沒有辦法檢測資訊的完整性。
範例
伺服器端響應資訊為字串“true”,則可以在用戶端這樣設計。
var xhr = createXHR(); //範例化XMLHttpRequest物件
xhr.open("GET", "server.txt", true); //建立連線,要求非同步響應
xhr.nreadystatechange = function () { //係結響應狀態事件監聽函數
if (xhr.readyState == 4) { //監聽readyState函數
if (xhr.status == 200 || xhr.status == 0) { //監聽HTTP狀態碼
var info = xhr.responseText;
if (info == "true") console.log("文字資訊傳輸完整"); //檢測資訊是否完整
else console.log("文字資訊可能存在丟失");
}
}
}
xhr.send(); //傳送請求