使用者嘗試在 AJAX 回呼中直接使用 JSP EL 表達式 ${fileNameMap},期望後端 request.setAttribute("fileNameMap", map) 能自動渲染。這在傳統同步請求 (Forward/Include) 才有效,AJAX 完全不同機制。
| 特性 | 同步請求 (Forward) | AJAX 非同步請求 |
|---|---|---|
| 流程 | Servlet → setAttribute → forward → JSP 渲染 → 回傳完整 HTML | JS 發請求 → Servlet 回傳 JSON → JS 解析 → DOM 操作更新局部 |
| 資料載體 | Request 域物件 (伺服器端) | HTTP Response Body (JSON/XML/文字) |
| JSP EL 生效 | 是 (JSP 編譯時期解析) | 否 (瀏覽器端無 JSP 引擎) |
@WebServlet("/api/files")
public class FileListServlet extends HttpServlet {
protected void doGet(HttpServletRequest req, HttpServletResponse resp) {
Map<String, Object> data = getFileMap(); // 業務邏輯
resp.setContentType("application/json;charset=UTF-8");
new ObjectMapper().writeValue(resp.getWriter(), data); // Jackson 序列化
}
}
// jQuery 版
$.getJSON('/api/files', function(data) {
// data 即為後端 Map 對應的 JS 物件
let html = '';
for (let key in data) {
html += `<option value="${key}">${data[key]}</option>`;
}
$('#fileSelect').html(html); // 動態更新下拉選單
});
// Fetch 版 (現代瀏覽器)
fetch('/api/files')
.then(r => r.json())
.then(data => { /* 同上 DOM 操作 */ });
request.setAttribute 僅在伺服器端轉發鏈路生效。AJAX 是「前端主動索取資料、自行渲染」的範式,切勿混淆兩種模式。採用「後端輸出 JSON、前端消費 JSON」的統一協議,前後端分離才能徹底落地。