AJAX (Asynchronous JavaScript and XML) 並非新技術,而是瀏覽器提供的 XMLHttpRequest 對象,允許網頁在不重新加載整頁的情況下,與服務器進行異步數據交換並局部更新頁面。現代開發多用 JSON 替代 XML,但術語沿用至今。
用戶輸入 → JS 事件觸發 → 創建 XMLHttpRequest → 發送異步請求
↓
服務器處理 (PHP/Java/Node...) → 返回數據 (JSON/HTML/文本)
↓
JS 回調函數接收響應 → DOM 更新頁面局部內容
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>AJAX 即時搜索建議演示</title>
<style>
#txtHint { color: #2c3e50; font-weight: bold; min-height: 1.5em; }
.loading::after { content: " 載入中..."; color: #3498db; }
</style>
</head>
<body>
<h3>請在下方輸入框鍵入字母 (A-Z):</h3>
<form>
姓氏:<input type="text" id="txt1" placeholder="輸入首字母..."
onkeyup="showHint(this.value)" autocomplete="off" />
</form>
<p>建議:<span id="txtHint"></span></p>
<script>
function showHint(str) {
const hintEl = document.getElementById("txtHint");
// 1. 空輸入清空提示
if (!str.trim()) {
hintEl.innerHTML = "";
return;
}
// 2. 創建 XHR 對象 (兼容 IE6+)
const xhr = window.XMLHttpRequest
? new XMLHttpRequest()
: new ActiveXObject("Microsoft.XMLHTTP");
// 3. 註冊回調
xhr.onreadystatechange = function() {
if (xhr.readyState === 4) {
if (xhr.status === 200) {
hintEl.innerHTML = xhr.responseText;
} else {
hintEl.innerHTML = "請求失敗: " + xhr.status + "";
}
}
};
// 4. 發送 GET 請求 (攜帶查詢參數)
xhr.open("GET", "ajax.php?q=" + encodeURIComponent(str), true);
xhr.send();
}
</script>
</body>
</html>
<?php
// 1. 模擬姓名數據源 (實際項目從資料庫查詢)
$names = [
"Anna", "Brittany", "Cinderella", "Diana", "Eva", "Fiona", "Gunda", "Hege",
"Inga", "Johanna", "Kitty", "Linda", "Nina", "Ophelia", "Petunia", "Amanda",
"Raquel", "Cindy", "Doris", "Eve", "Evita", "Sunniva", "Tove", "Unni",
"Violet", "Liza", "Elizabeth", "Ellen", "Wenche", "Vicky"
];
// 2. 獲取前端傳來的查詢參數 q
$q = isset($_GET['q']) ? trim($_GET['q']) : '';
// 3. 模糊匹配邏輯 (不區分大小寫,匹配開頭)
$hint = "";
if (strlen($q) > 0) {
$qLower = strtolower($q);
foreach ($names as $name) {
if (strtolower(substr($name, 0, strlen($q))) === $qLower) {
$hint .= ($hint ? " , " : "") . $name;
}
}
}
// 4. 輸出響應
echo $hint ? $hint : "no suggestion";
?>
| readyState | 階段 | 說明 |
|---|---|---|
| 0 | UNSENT | open() 未調用 |
| 1 | OPENED | open() 已調用 |
| 2 | HEADERS_RECEIVED | 響應頭已接收 |
| 3 | LOADING | 響應體下載中 |
| 4 | DONE | 請求完成 (成功或失敗) |
只在 readyState === 4 時處理響應,並檢查 status === 200 確保 HTTP 成功。
htmlspecialchars() 防 XSSasync function showHintModern(str) {
if (!str.trim()) return;
try {
const resp = await fetch(`ajax.php?q=${encodeURIComponent(str)}`);
const text = await resp.text();
document.getElementById("txtHint").textContent = text;
} catch (e) {
document.getElementById("txtHint").textContent = "網絡錯誤";
}
}
fetch 基於 Promise,語法更簡潔,但 IE 不支援,需 Polyfill。
AJAX 核心在於 異步請求 + DOM 更新。原生 XMLHttpRequest 雖繁瑣但無依賴、兼容性佳,理解其底層機制有助於排查網絡問題。實際項目中,建議封裝通用請求函數或使用 Axios/Fetch,並配合防抖、緩存、錯誤重試等工程化手段,構建健壯的交互體驗。