天天看點

Filter 對未登入使用者通路位址的控制

首先我們應該明白java過濾器的作用原理,他到底是幹什麼的?什麼原理?

顧名思義,過濾器即起到過濾的作用。大家可以把它根過濾網聯想一下。這是我畫的過濾器示意圖:

Filter 對未登入使用者通路位址的控制

1  過濾器對使用者的‘請求’和伺服器的‘響應’做了一層過濾,即進行了預處理。

(1)    當使用者在用戶端向伺服器送出請求時,首先在請求進入伺服器之前要經過過濾器Filter的處理(修改請求資訊—包括請求的頭資訊、資料、url位址等資訊);

(2)    當伺服器接收到使用者的請求之後,會響應用戶端回報資訊回去,同樣在伺服器發送響應資訊到用戶端之前,過濾器也會進行相應的過濾處理;

2  寫一個java過濾器,必須要實作javax.servlet.Filter接口。

過濾重新開機定義了3個必須實作的方法:

(1)      public void init(FilterConfig config) throwsServletException {}

(2)      public void doFilter(ServletRequest request,ServletResponse response, FilterChain chain) throws IOException,ServletException{}

(3)      public void destroy(){}

方法 (1) 用來初始化過濾器配置資訊;

方法 (2) 進行相應的過濾處理;

方法 (3) 在取消執行之前進行過濾資源釋放。

3        下面我們來實作一個使用者通過浏覽器通路資源的過濾器,要求:

(1)     如果使用者未登入則跳轉至登入頁面,登陸之後跳轉到原來輸入位址對應的頁面;

(2)     如果使用者已登入則直接進入輸入的位址對應的頁面;

(3)     實作原理:

主要是對于未登入使用者的處理,在跳轉至登入頁面之前将使用者原來的通路的位址截取項目名稱後面的部分,然後作為一個參數寫入session中儲存;

當使用者登入時,将session中儲存的位址取出進行跳轉。

4        代碼實作與配置:

(1)     過濾器代碼

package adam.bp.workflow.filter;

import java.io.IOException;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;


/**
 * @author hsy
 *
 */
public class LoginFilter implements Filter {
	private static final String SHOW_LOGIN_PATH = "SHOW_LOGIN_PATH";	//顯示登入頁面
	private static final String DO_LOGIN_PATH = "DO_LOGIN_PATH";		//登入操作不能過濾掉
	private static final String LOGIN_PERSONID = "LOGIN_PERSONID";		//登入使用者在session中的屬性key -- session.setAttribute(key,value)
	private String showloginPath;
	private String dologinPath;
	private String loginPersonId;
	
    public void init(FilterConfig config) throws ServletException {
    	showloginPath = config.getInitParameter(SHOW_LOGIN_PATH);
    	dologinPath = config.getInitParameter(DO_LOGIN_PATH);
    	loginPersonId = config.getInitParameter(LOGIN_PERSONID);
    	if(showloginPath==null || showloginPath.equals("") || showloginPath.equals("null") ){
    		throw new ServletException("登入頁面配置出錯...");
    	}
    }
    
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
    	 HttpServletRequest  httpReq  = (HttpServletRequest) request;
         HttpServletResponse httpResp = (HttpServletResponse) response;
         httpResp.setContentType("text/html");
         //判斷是否是登陸頁面
         String servletPath = httpReq.getServletPath();
         
         //flag:若為登陸頁面的action路徑 showloginPath/nologinPath,則指派true,否則指派false
         boolean flag = false;
         if(servletPath.equals(showloginPath) || servletPath.equals(dologinPath)){
        	 chain.doFilter(request, response);
        	 flag = true;
        	 return;
         }
         else
         {   //如果不是登入頁面,則需先判斷使用者是否已登入
        	 //String url = servletPath;
        	 Object loginId = httpReq.getSession().getAttribute(loginPersonId);
        	 if(loginId != null){//如果不為空,則進行已登入處理
        		 chain.doFilter(request, response);
        	 }else{//如果為空,則進行未登入處理
        		 if ( httpReq.getQueryString() != null )
            	 {
            		 servletPath += "?"+httpReq.getQueryString();
            	 }
            	 httpReq.getSession().setAttribute("returnUri", servletPath);
                 if ( flag == false )
                 {	
                	httpReq.getRequestDispatcher(showloginPath).forward(httpReq,httpResp);
                 } 
        	 }
         }
    }
    
    public void destroy(){
    	//do something
    }
    
}
           

(2)     web.xml中的配置

<!-- 使用者登入過濾 -->
	<filter>
	 <filter-name>loginFilter</filter-name>
	 <filter-class>adam.bp.workflow.filter.LoginFilter</filter-class>
	 <init-param>
	     <param-name>LOGIN_PERSONID</param-name>
	     <param-value>loginPersonId</param-value>
	 </init-param>
	 <init-param>
	     <param-name>SHOW_LOGIN_PATH</param-name>
	     <param-value>/showLogin.do</param-value>
	 </init-param>
	 <init-param>
	     <param-name>DO_LOGIN_PATH</param-name>
	     <param-value>/doLogin.do</param-value>
	 </init-param>
	</filter>
	<filter-mapping>
		<filter-name>loginFilter</filter-name>
		<url-pattern>*.do</url-pattern>
	</filter-mapping>
	<filter-mapping>
		<filter-name>loginFilter</filter-name>
		<url-pattern>*.jsp</url-pattern>
	</filter-mapping>
           

(3) 相應的頁面登入的servlet或者action代碼,就不寫了,相信對大家來說這個不難!