作者:tonytfjing + Java兔
DispatcherServlet
SpringMVC具有統一的入口DispatcherServlet,所有的請求都通過DispatcherServlet。DispatcherServlet是前置控制器,配置在web.xml文件中的。攔截匹配的請求,Servlet攔截匹配規則要自已定義,把攔截下來的請求,依據某某規則分發到目標Controller來處理。 所以我們現在web.xml中加入以下配置:
<servlet>
<servlet-name>demo</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:spring-mvc.xml</param-value>
</init-param>
<load-on-startup>2</load-on-startup>
<async-supported>true</async-supported>
</servlet>
<servlet-mapping>
<servlet-name>demo</servlet-name>
<!-- *.do的請求,會被DispatcherServlet處理 -->
<url-pattern>*.do</url-pattern>
</servlet-mapping>
靜態資源不攔截
一般實現攔截器主要是爲了權限管理,主要是攔截一些url請求,所以不對靜態資源進行攔截。要過濾掉靜態資源可以在spring-mvc.xml配置文件中這樣配置:
<!-- cache-period:配置緩存時間 -->
<mvc:resources mapping="/resources/**" location="/resources/" cache-period="300" />
自定義攔截器
SpringMVC的攔截器HandlerInterceptorAdapter對應提供了三個preHandle,postHandle,afterCompletion方法。
- preHandle在業務處理器處理請求之前被調用;
- postHandle在業務處理器處理請求執行完成後,生成視圖之前執行;
- afterCompletion在DispatcherServlet完全處理完請求後被調用,可用於清理資源等 。
所以要想實現自己的權限管理邏輯,需要繼承HandlerInterceptorAdapter並重寫其三個方法。
- springmvc.xml中加入自己定義的攔截器:
<!--配置攔截器, 多個攔截器,順序執行 -->
<mvc:interceptors>
<bean class="org.springframework.web.servlet.i18n.LocaleChangeInterceptor"/>
<mvc:interceptor>
<!-- 匹配的是url路徑, 如果不配置或/**,將攔截所有的Controller -->
<mvc:mapping path="/**"/>
<mvc:exclude-mapping path="/resources/**"/>
<bean class="com.wx.app.ygp.action.interceptor.LoginInterceptor"></bean>
</mvc:interceptor>
<!-- 當設置多個攔截器時,先按順序調用preHandle方法,然後逆序調用每個攔截器的postHandle和afterCompletion方法 -->
<mvc:interceptor>
<mvc:mapping path="/**"/>
<mvc:exclude-mapping path="/resources/**"/>
<!-- 自定義攔截器文件的路徑 -->
<bean class="**com.wx.app.ygp.action.interceptor.MessageInterceptor**"></bean>
</mvc:interceptor>
</mvc:interceptors>
- 自定義攔截器的具體代碼:
package com.wx.app.ygp.action.interceptor;
import java.io.IOException;
import javax.servlet.RequestDispatcher;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.log4j.Logger;
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter;
/**
*
* @author huangjp
* @Descripition : 短信驗證攔截器
* 2017年6月22日 下午1:11:11
*/
public class MessageInterceptor extends HandlerInterceptorAdapter{
/**
* 需要攔截的URL
*/
private static final String[] INTERCEPTOR_URL = {
"/icCard/workCard.do?menuId=97",
"/billManagement/counterPayment/show.do?menuId=2003",
"/icCard/dailyBusiness.do?menuId=95",
"/icCard/exceptionBusiness.do?menuId=96"
};
private static final String MESSAGE_URL = "/message/show.do";
private final Logger logger = Logger.getLogger(MessageInterceptor.class);
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
throws Exception {
//獲取當前請求url:http://localhost:8080/ygp/icCard/workCard.do
String url = request.getRequestURL().toString();
String message = request.getParameter("message");
//如果是需要短信驗證的頁面,則先跳轉到短信驗證頁面
for(String oneUrl : INTERCEPTOR_URL){
if(url.contains(oneUrl.split("[?]")[0]) && message == null){
logger.info("該頁面需要短信驗證");
fowardMessage(request, response, oneUrl);
return false;
}
}
logger.info("該頁面不需要短信驗證");
return true;
}
/**
* 跳轉到短信驗證頁面
* @param : menuUrl
* @throws IOException
* @throws ServletException
*/
private void fowardMessage(HttpServletRequest request,HttpServletResponse response, String menuUrl) throws ServletException, IOException{
RequestDispatcher rd = request.getRequestDispatcher(MESSAGE_URL+"?menuUrl="+menuUrl);
rd.forward(request, response);
}
}
這樣,就完成了一個簡單的自定義攔截器。
參考資料
http://blog.csdn.net/tonytfjing/article/details/39207551