HTTP 無狀態特性導致伺服器無法識別同一用戶的多次請求。會話跟蹤技術透過 SessionId 建立客戶端與伺服器的 1 對 1 關聯。本文通過完整 Servlet 實例,演示 Session 生命週期、Cookie 依賴、URL 重寫降級方案及常見陷阱。
JSESSIONID 中jsessionid 附加在 URL 路徑參數中| Servlet | 職責 | 關鍵 API |
|---|---|---|
LoginServlet | 登入頁 + Session 信息展示 | getSession()、isNew()、getId()、getCreationTime() |
LoginChkServlet | 驗證用戶名密碼,寫入 Session | setAttribute("username", name) |
WelcomeServlet | 登入成功頁,讀取 Session、分頁查詢 | getAttribute()、Session 失效跳轉邏輯 |
LogOutServlet | 銷毀 Session,返回登入頁 | invalidate() |
// LoginServlet - 獲取/建立 Session 並打印狀態
HttpSession session = request.getSession();
out.println("會話狀態: " + (session.isNew() ? "新會話" : "舊會話"));
out.println("SessionId: " + session.getId());
out.println("創建時間: " + new Date(session.getCreationTime()));
// LoginChkServlet - 登入驗證成功寫入 Session
if (validUser) {
HttpSession session = request.getSession();
session.setAttribute("username", userName);
response.sendRedirect("welcome");
}
// URL 重寫適配(禁用 Cookie 時必須)
response.sendRedirect(response.encodeRedirectURL("login"));
// 表單 action 也需重寫
out.println("<form action='" + response.encodeURL("loginchk") + "' method=post>");
<session-config>
<session-timeout>10</session-timeout> <!-- 分鐘 -->
</session-config>
MaxInactiveInterval=600 秒(10 分鐘);jsessionid=xxx,恢復正常會話跟蹤request.changeSessionId()(Servlet 3.1+)HttpOnly、Secure 屬性invalidate() 銷毀伺服器端 Session