通過
HttpSession案例一和
HttpSession案例二的學習,大家對HttpSession的用途有了一定的了解。今天我們來深入了解HttpSession的原理。學習HttpSession的原理對大家運用HttpSession有很大幫助。
1.HttpSession原理分析
首先,我們知道session對象是由服務器創(chuàng)建,并保存在服務器端。那么服務器在什么情況下創(chuàng)建session對象?瀏覽器在訪問服務器時,服務器又是通過什么來找到對應的session對象呢?帶著這些問題,我們來深入了解HttpSession。
1.1服務器如何識別session對象
session是依賴于Cookie的。瀏覽器訪問服務器后,在瀏覽器端查看cookie時可以發(fā)現(xiàn)一個名為JSESSIONID的cookie。如圖1-1所示:
圖1-1 cookie信息
從圖1-1可以看出,這個名字為JSESSIONID的cookie的值是A147B274C704729BA01624490C898757,并且過期時間為瀏覽會話結束時,即表示當瀏覽器關閉,該cookie就死亡。其實這個cookie的值就是當前會話session的id值。
服務器每次創(chuàng)建的session對象,都具有一個id屬性,也是唯一標識的屬性。服務器創(chuàng)建session后,將它的id值保存在cookie中,然后發(fā)送給瀏覽器。瀏覽器在一次會話中無論訪問服務器的那個資源都會帶著這個cookie,服務器會根據cookie的值找到對應的session,然后從session中取出數(shù)據。下面通過一張圖形象理解這個過程們,如圖1-2所示:
圖1-2 瀏覽器與服務器之間傳遞session過程
調用request.getSession()方法是從名為JSESSIONID的cookie中獲取session的id值,然后拿到這個id值去服務器的session緩存中查找對應session并返回。
1.2服務器在什么情況下創(chuàng)建session對象
調用request.getSession()方法可以獲得session對象,但并不是代表調用該方法服務器就會創(chuàng)建一個HttpSession對象,只有在一次會話中,第一次調用該方法時服務器才會創(chuàng)建一個session對象。
request.getSession()方法會查找請求信息中是否存在一個名為JSESSIONID的cookie,這個cookie是否存在會導致出現(xiàn)以下三種情況:
Cookie不存在,說明服務器還沒有為本次會話創(chuàng)建session對象,這時服務器會創(chuàng)建一個session對象,并把這個session對象保存在session緩存中,然后將session的id值保存在一個cookie中,再把這個cookie發(fā)送給瀏覽器。
- Cookie存在,session的id值有對應的session對象:
拿到該cookie的值,即session的id值,然后根據id值去session緩存中查找到了對應的session對象,這時服務器不會重新創(chuàng)建session,而是將找到的session返回。
- Cookie存在,session的id值沒有對應的session對象:
根據session的id值在session緩存中沒有找到對應的session對象,這時服務器創(chuàng)建新的session,并將新session的id值保存在一個cookie中,然后響應給瀏覽器。
以上就是服務器創(chuàng)建session的對象的三種情況。另外,request對象還有其他兩個方法可以獲取session對象,分別是:
- request.getSession(false):這個方法的作用是:從cookie中取出session的id值,但是該id值沒有對應的session,服務器不再創(chuàng)建新的session對象,返回null;
- request.getSession(true):該方法的作用和request.getSession()方法的作用一樣。
HttpSession對象有最大不活動時間,默認的最大不活動時間是30分鐘,也就是說,如果session對象長時間不被使用,30分鐘后這個session對象就會失效。
2.驗證HttpSession對象創(chuàng)建時機
(1)創(chuàng)建一個web應用,Example23,在該應用下新建一個Servlet類,SessionServlet,該Servlet類的訪問路徑為:“/SessionServlet“,主要代碼如例1-1所示:
例1-1 SessionServlet.java
public class SessionServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=utf-8");
response.getWriter().write("請查看是否有jsessionid這個cookie");
}
}
例1-1中,因為要向瀏覽器端響應中文,因此要設置響應信息編碼以防亂碼。
(2)將Example23發(fā)布到Tomcat服務器中,然后啟動服務器,在瀏覽器地址欄上輸入:http://localhost:8080/Example23/SessionServlet,瀏覽器顯示結果如圖1-3所示:
圖1-3 瀏覽器顯示結果
(3)查看瀏覽器中保存的cookie信息,如圖1-4所示:
圖1-4 cookie信息
由圖1-4可知,該瀏覽器中并沒有一個叫JSESSIONID的cookie,也就是說瀏覽器訪問服務器端的SessionServlet,服務器并沒有創(chuàng)建session對象。因為在SessionServlet中并沒有調用request.getSession()方法。
(4)現(xiàn)在在瀏覽器端訪問Example23應用的index.jsp頁面,然后查看瀏覽器中的cookie信息,如圖1-5所示:
圖1-5 cookie信息
由圖1-5可知,訪問index.jsp頁面后,瀏覽器中存在一個名為JSESSIONID的cookie,說明服務器創(chuàng)建了一個session對象。我們并沒有在index.jsp頁面調用request.getSession()方法,服務器為什么就創(chuàng)建session對象了?因為session是jsp頁面的內置對象,服務器將jsp翻譯成Java文件后,在該Java文件中存在一句代碼,調用了getSession()方法。
(5)將瀏覽器中的cookie刪除,然后修改SessionServlet,如下所示:
public class SessionServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=utf-8");
request.getSession();
response.getWriter().write("請查看是否有jsessionid這個cookie");
}
}
(6)重新啟動服務器,在瀏覽器端訪問SessionServlet ,然后查看瀏覽器的cookie信息,如圖1-6所示:
圖1-6 cookie信息
當在SessionServlet中添加request.getSession()代碼,服務器就創(chuàng)建了session對象。
本文版權歸傳智播客Java培訓學院所有,歡迎轉載,轉載請注明作者出處。謝謝!
作者:傳智播客Java培訓學院
首發(fā):http://8y3kgpwe.cn/javaee