jsp安全性問題,當別人知道某個jsp文件的網址后就可以跳過登陸頁面直接訪問該jsp文件了,這樣無法禁止外部無權限用戶的訪問。本文討論內容是通過權限驗證的用戶,才可以訪問特定的頁面。
JSP 頁面驗證,涉及到的知識有Session, 網頁權限, 用戶驗證等。
session對象
session對象用來存儲有關用戶會話的所有信息,一個會話就是瀏覽器與服務器之間的一次通話,它包含瀏覽器與服務器之間的多次請求、響應過程。session是JSP內置對象,與瀏覽器一一對應,允許用戶存儲和提取會話狀態的信息,信息保存在服務器端。
session信息獲取
1) JSP
session.setAttribute("userinfo", USERNAME);// session保存登錄信息和用戶名
2) Java(Servlet)
request.getSession().setAttribute("userinfo", USERNAME); // session保存登錄信息和用戶名 其中,request為HttpServletRequest對象,在doPost(HttpServletRequest request, HttpServletResponse response){...}引用
session超時設置
1) web.xml
<?xml version="1.0" encoding="UTF-8"?> <web-app> ... <session-config> <session-timeout>30</session-timeout> <!-- 單位為分鍾,例如30分鍾 --> </session-config>
</web-app>
2) Java
request.getSession().setMaxInactiveInterval(30*60);// 設置session失效時間(timeout),單位為秒
注: setMaxInactiveInterval() 比 web.xml 優先級高,如果兩者同時設置則采用 setMaxInactiveInterval()
JSP 網頁權限
JSP 網頁權限,有兩種配置方式:
1) include 文件
如: 驗證文件 logincheck.jsp
- <%
- if(session.getAttribute("userinfo") == null) {
- %>
- <script type="text/javascript" language="javascript">
- alert("您還沒有登錄,請登錄...");
- window.document.location.href="userlogin.html";
- </script>
- <%
- }
- %>
<% if(session.getAttribute("userinfo") == null) { %> <script type="text/javascript" language="javascript"> alert("您還沒有登錄,請登錄..."); window.document.location.href="userlogin.html"; </script> <% } %>
在需要驗證的jsp網頁起始位置,包含logincheck.jsp , 例如在需要驗證的jsp網頁 page111.jsp 中添加
<%@ include file="logincheck.jsp" %>
2) filter 過濾
首先,在web.xml配置文件中設置過濾頁
- <filter>
- <filter-name>LoginFilter</filter-name>
- <filter-class>com.homer.LoginFilter</filter-class>
- </filter>
- <filter-mapping>
- <filter-name>LoginFilter</filter-name>
- <url-pattern>/page222.jsp</url-pattern>
- </filter-mapping>
<filter> <filter-name>LoginFilter</filter-name> <filter-class>com.homer.LoginFilter</filter-class> </filter> <filter-mapping> <filter-name>LoginFilter</filter-name> <url-pattern>/page222.jsp</url-pattern> </filter-mapping>
注: 目前配置方式僅僅是在用戶訪問page222.jsp的時候才走過濾器,也可以配置/*, /user/*等目錄進行批量網頁過濾
然后,在 LoginFilter.java(web.xml配置文件中的com.homer.LoginFilter)文件中, 進行過濾驗證:
- public class LoginFilter implements Filter {
- @Override
- public void init(FilterConfig arg0) throws ServletException {
- }
- @Override
- public void doFilter(ServletRequest arg0, ServletResponse arg1, FilterChain arg2) throws IOException, ServletException {
- HttpServletRequest request = (HttpServletRequest)arg0;
- HttpServletResponse response = (HttpServletResponse)arg1;
- HttpSession session = request.getSession();
- if(session.getAttribute("userinfo") == null) {
- response.setCharacterEncoding("utf-8");
- PrintWriter out = response.getWriter();
- out.print("<script>alert('您還沒有登錄,請登錄...'); window.location='userlogin.html' </script>");
- out.flush();
- out.close();
- // request.setAttribute("loginError", "您還沒有登錄,請登錄...");
- // request.getRequestDispatcher("userlogin.html").forward(request, response);
- } else {
- arg2.doFilter(request, response);
- }
- }
- @Override
- public void destroy() {
- }
- }
public class LoginFilter implements Filter { @Override public void init(FilterConfig arg0) throws ServletException { } @Override public void doFilter(ServletRequest arg0, ServletResponse arg1, FilterChain arg2) throws IOException, ServletException { HttpServletRequest request = (HttpServletRequest)arg0; HttpServletResponse response = (HttpServletResponse)arg1; HttpSession session = request.getSession(); if(session.getAttribute("userinfo") == null) { response.setCharacterEncoding("utf-8"); PrintWriter out = response.getWriter(); out.print("<script>alert('您還沒有登錄,請登錄...'); window.location='userlogin.html' </script>"); out.flush(); out.close(); // request.setAttribute("loginError", "您還沒有登錄,請登錄..."); // request.getRequestDispatcher("userlogin.html").forward(request, response); } else { arg2.doFilter(request, response); } } @Override public void destroy() { } }
用戶登錄驗證
用戶登錄驗證,有兩種方式:JSP網頁前端和Java(Serlvet)后台
1) JSP網頁前端驗證(login.jsp)
- <%
- String USERNAME = "admin";
- String USERPWD = "123456";
- request.setCharacterEncoding("utf8");
- String userName = request.getParameter("username").trim();
- String userPwd = request.getParameter("userpwd").trim();
- if(userName == null || userPwd == null){
- response.sendRedirect("userlogin.html");
- return;
- }
- if(userName.equals(USERNAME) && userPwd.equals(USERPWD)) {
- session.setMaxInactiveInterval(30*60); // 設置session失效時間(timeout),單位為秒
- session.setAttribute("userinfo", USERNAME); // 用戶名和密碼正確,保存登錄信息
- response.sendRedirect("page111.jsp");
- } else {
- response.sendRedirect("userlogin.html"); // 用戶名和密碼錯誤,跳轉到登錄界面
- }
- %>
<% String USERNAME = "admin"; String USERPWD = "123456"; request.setCharacterEncoding("utf8"); String userName = request.getParameter("username").trim(); String userPwd = request.getParameter("userpwd").trim(); if(userName == null || userPwd == null){ response.sendRedirect("userlogin.html"); return; } if(userName.equals(USERNAME) && userPwd.equals(USERPWD)) { session.setMaxInactiveInterval(30*60); // 設置session失效時間(timeout),單位為秒 session.setAttribute("userinfo", USERNAME); // 用戶名和密碼正確,保存登錄信息 response.sendRedirect("page111.jsp"); } else { response.sendRedirect("userlogin.html"); // 用戶名和密碼錯誤,跳轉到登錄界面 } %>
2) Java(Serlvet)后台驗證(Login.java)
- public class Login extends HttpServlet {
- private static final long serialVersionUID = 1L;
- private final static String USERNAME = "admin";
- private final static String USERPWD = "123456";
- @Override
- protected void doGet(HttpServletRequest request, HttpServletResponse response) {
- }
- @Override
- protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
- request.setCharacterEncoding("utf-8");
- String userName = request.getParameter("username").trim();
- String userPwd = request.getParameter("userpwd").trim();
- if(userName == null || userPwd == null) {
- response.sendRedirect("userlogin.html");
- }
- if(userName.equals(USERNAME) && userPwd.equals(USERPWD)) {
- request.getSession().setMaxInactiveInterval(30*60); // 設置session失效時間(timeout),單位為秒
- request.getSession().setAttribute("userinfo", USERNAME); // 用戶名和密碼正確,保存登錄信息(獲得session與jsp網頁稍有不同)
- response.sendRedirect("page111.jsp");
- } else {
- response.sendRedirect("userlogin.html"); // 用戶名和密碼錯誤,跳轉到登錄界面
- }
- }
- }
public class Login extends HttpServlet { private static final long serialVersionUID = 1L; private final static String USERNAME = "admin"; private final static String USERPWD = "123456"; @Override protected void doGet(HttpServletRequest request, HttpServletResponse response) { } @Override protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { request.setCharacterEncoding("utf-8"); String userName = request.getParameter("username").trim(); String userPwd = request.getParameter("userpwd").trim(); if(userName == null || userPwd == null) { response.sendRedirect("userlogin.html"); } if(userName.equals(USERNAME) && userPwd.equals(USERPWD)) { request.getSession().setMaxInactiveInterval(30*60); // 設置session失效時間(timeout),單位為秒 request.getSession().setAttribute("userinfo", USERNAME); // 用戶名和密碼正確,保存登錄信息(獲得session與jsp網頁稍有不同) response.sendRedirect("page111.jsp"); } else { response.sendRedirect("userlogin.html"); // 用戶名和密碼錯誤,跳轉到登錄界面 } } }
其中,需要在web.xml配置Servlet映射關系:
- <servlet>
- <description>Login</description>
- <display-name>Login</display-name>
- <servlet-name>Login</servlet-name>
- <servlet-class>com.homer.Login</servlet-class>
- </servlet>
- <servlet-mapping>
- <servlet-name>Login</servlet-name>
- <url-pattern>/login</url-pattern>
- </servlet-mapping>
<servlet> <description>Login</description> <display-name>Login</display-name> <servlet-name>Login</servlet-name> <servlet-class>com.homer.Login</servlet-class> </servlet> <servlet-mapping> <servlet-name>Login</servlet-name> <url-pattern>/login</url-pattern> </servlet-mapping>
注: Login.java映射成對樣網頁為/login,login可以在網頁(html和jsp)form中指定,如 action="login"
用戶登錄界面
用戶登錄界面,是用戶在訪問整個網站之前需要訪問的,因此最好制作成靜態頁面HTML,本例如:userlogin.html
- <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
- <html>
- <head>
- <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
- <title>userlogin.html</title>
- </head>
- <body>
- <center>
- <form method="POST" name="form1" action="login">
- <table>
- <tr>
- <td>UserName : </td>
- <td><input type="text" name="username" /></td>
- </tr>
- <tr>
- <td>UserPwd : </td>
- <td><input type="text" name="userpwd" /></td>
- </tr>
- <tr>
- <td colspan="2" align="center">
- <input type="submit" name="btnSubmit" value="login"/>
- </td>
- </tr>
- </table>
- </form>
- </center>
- </body>
- </html>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> <title>userlogin.html</title> </head> <body> <center> <form method="POST" name="form1" action="login"> <table> <tr> <td>UserName : </td> <td><input type="text" name="username" /></td> </tr> <tr> <td>UserPwd : </td> <td><input type="text" name="userpwd" /></td> </tr> <tr> <td colspan="2" align="center"> <input type="submit" name="btnSubmit" value="login"/> </td> </tr> </table> </form> </center> </body> </html>
注: 此時 action="login" 默認對應Java(Servlet)中對應的 Login.java 進行驗證解析
userlogin.html 針對上述兩種 用戶登錄驗證 方式,分別提供了兩種POST方式:
1) 針對JSP方式
<form method="POST" name="form1" action="login.jsp">
2) 針對Java(Servlet)方式
<form method="POST" name="form1" action="login">
本示例代碼說明
本示例主要代碼結構圖如下:
1) head.jsp 和 foot.jsp
統一控制jsp頁面的上,下部內容,類似ASP.NET的模板
2) index.jsp
網站默認的登錄頁面,本示例主要用作跳轉到登錄頁面 userlogin.html :
<script type="text/javascript" language="javascript"> window.location="userlogin.html";</script>
3)userlogin.html
靜態登錄頁面,見上面 用戶登錄界面 的所示
4) login.jsp 和 Login.java
login.jsp 網頁驗證用戶登錄信息(用戶名和密碼),見上面的 用戶登錄驗證 方式1
Login.java 后台驗證用戶登錄信息(用戶名和密碼),見上面的 用戶登錄驗證 方式2
5) logincheck.jsp 和 LoginFilter.java
logincheck.jsp 網頁驗證用戶是否已登錄,見上面的 JSP 網頁權限方式1
LoginFilter.java 后台驗證用戶是否已登錄,見上面的 JSP 網頁權限方式2
6) page111.jsp, page222.jsp, page333.jsp
(1) page111.jsp
采用 logincheck.jsp 網頁權限驗證,其代碼內容為:
<%@ include file="logincheck.jsp" %> <%@ include file="head.jsp" %> I am page111.jsp <%@ include file="foot.jsp" %>
(2) page222.jsp
采用 logincheck.jsp 網頁權限驗證,其代碼內容為:
<%@ include file="head.jsp" %> I am page222.jsp <%@ include file="foot.jsp" %>
注:采用filter過濾方式,在web.xml配置文件中設置了哪些jsp網頁需要過濾,見上面JSP 網頁權限 ---》2) filter 過濾
(3) page333.jsp
采用 logincheck.jsp 網頁權限驗證,其代碼內容為:
<%@ include file="head.jsp" %> I am page333.jsp <%@ include file="foot.jsp" %>
注: 沒有任何驗證,用戶可以直接輸入網址進行訪問
7) logout.jsp
用戶退出時,注銷session中的登錄信息
<% session.invalidate();response.sendRedirect("http://blog.csdn.net/sunboy_2050/article/details/8032693"); %>
本示例運行界面:
1) 登錄界面
userlogin.html
2) JSP 頁面驗證
logincheck.jsp (或LoginFilter.java)頁面訪問前進行登錄驗證
3) 驗證通過訪問JSP頁面
login.jsp(或Login.java)用戶登錄后才可以正常訪問JSP頁面