jsp(5):會話Session的使用,跟蹤使用者
應用場景:使用者登陸我們的網址後,下次登陸時會自動顯示使用者的登陸名稱。這就是“跟蹤使用者”技術,目前使用最多的是利用session實現跟蹤使用者資訊。
Session是什麼?
jsp的內建物件之一。JSP通過request物件控制使用者瀏覽器的請求,通過response對客戶瀏覽器進行響應;
session就是維持這個反反覆覆的會話期間需要傳遞的資料資訊。
起止時間
開啟瀏覽器訪問伺服器後開始建立session物件,關閉瀏覽器後本專案的session才消失。
(注:與瀏覽器頁面開關無關,與整個瀏覽器有關)
簡單demo:使用session儲存我們對該頁面的訪問次數
(jsp中直接使用內建物件session)
... <body> <% int num=1; //初始化次數為1 if(session.getAttribute("count")!=null){ //若已經session已經建立,則num+1 String n=(String)session.getAttribute("count"); num=Integer.parseInt(n)+1; } session.setAttribute("count",num+""); //在session儲存num %> 當前點選了<%=num %>次頁面 </body> ...
效果:每次重新整理一次eclipse的內建瀏覽器就能觀察到num在增加。
· num不是區域性變數麼?(詳見教程1)為什麼重新整理的時候區域性變數沒有重新賦值?
因為session啊,只要我們沒關閉瀏覽器,session中的值就一直不會釋放掉,重新整理是沒有用的。強調,是關閉瀏覽器,我們本專案的session才會消失,如果我們關閉了瀏覽器的當前頁面,session仍然存在,不信可以自己去QQ瀏覽器、火狐瀏覽器等瀏覽器自行訪問專案地址測試下。(例如:http://localhost:8080/Test/hhhh.jsp。不推薦使用eclipse的內建瀏覽器測試,雞肋)
· 為什麼session.setAttribute()中的num要num+"",從int變成string型別?
因為該函式接受一個object(String或者Integer),這裡我們把int這樣轉型為string(也可嘗試轉Integer或其他方法)。
存值的時候用的是String,取值取得也是String,這就是為什麼我們getAttribute後要強轉的原因了。
實用場景Demo
防止“非正規登陸”:demo大部分程式碼借鑑前幾節部落格的內容。部分改動。login.jsp:不變
check.jsp : 判斷使用者名稱密碼是否匹配,是否登陸成功
....
<body>
<%
String username = request.getParameter("user");
String password = request.getParameter("psw");
if(username.equals("admin")&&password.equals("123"))
{
//密碼正確,登陸成功,建立會話session,跳轉到歡迎介面
session.setAttribute("user", username);
response.sendRedirect("welcom.jsp");
}
else{
//密碼不對,跳轉回登入頁面
response.sendRedirect("login.jsp");
}
%>
</body>
....
welcome.jsp: 如果使用者登陸成功,就轉入“歡迎”介面,並且可以點選超連結更改我們自己的部落格內容。
...
<body>
welcome
<%
out.print(session.getAttribute("user"));
%>
<br>
<a href="rewrite.jsp">重寫我的部落格</a>
</body>
...
rewrite.jsp: 假設在這裡實現更改我們部落格的操作。
....
<body>
正在重寫部落格...
</body>
...
執行:從login.jsp執行,輸入admin,123,發現一切正常~
但是!現在我們關閉並再次開啟我們的瀏覽器,訪問rewrite.jsp的地址(例如我的:http://localhost:8080/Test/rewrite.jsp),
你會發現就算你沒登陸,你也可以執行使用者登入後才有的“重寫部落格”操作。
這時候我們可以通過判斷使用者是否通過了正規的登陸檢驗check.jsp,是否建立了session來阻止非法訪問遊客部落格空間的行為。
即可以更改rewrite.jsp程式碼:
.....
<body>
<%-- <jsp:include page="checkvalid.jsp" flush="true"></jsp:include> --%>
<%-- <%@include file="checkvalid.jsp" %> --%>
<%
if(session.getAttribute("user")==null){
%>
<jsp:forward page="login.jsp" ></jsp:forward>
<%
}
%>
正在重寫部落格...
</body>
...
這時候我們再關閉,重新開啟我們的瀏覽器訪問rewrite介面,就會發現我們因為沒有通過正常登陸渠道建立與伺服器的session,無法執行“重寫部落格”操作,我們被強制返回登陸頁面操作了~
關於註釋中的checkvaild.jsp,如果對前文中提到的坑感興趣的,可以自己試試。
<%
if(session.getAttribute("user")==null){
%>
<jsp:forward page="login.jsp" ></jsp:forward>
<%
}
%>
雖然到這裡看起來就完美了,但是仔細一思考:
使用者登陸後的操作一般都有好多個的,除了“重寫部落格”外,還有“檢視訪問量”、“刪除部落格”....等操作,難道我們每次寫這些操作的介面時,都要判斷一次session.getAttribute()是否為空?為空就返回到login.jsp?這不是程式碼冗餘了嘛!還好我們有重寫、過濾器可以解決這個問題。(後面章節再提)
上面那個demo是在jsp中直接使用,但是後面我們會講到servlet之類的純java程式碼,在Java中是不能使用jsp的內建物件的,所以如果在java程式碼中怎麼使用session呢?這就需要建立物件來使用,這裡以HttpSession 為例子。
HttpSession session=request.getSession();
session.setAttribute("username", username);