如 果您在Controller執行的前後,或者是在View繪製之後打算作一些記錄或欄截請求等動作,您可以實作 org.springframework.web.servlet.HandlerInterceptor介面,在這個介面中規範了三個必須實作的方法, 其定義如下所示:
package org.springframework.web.servlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public interface HandlerInterceptor {
boolean preHandle(HttpServletRequest request,
HttpServletResponse response,
Object handler) throws Exception;
void postHandle(HttpServletRequest request,
HttpServletResponse response,
Object handler,
ModelAndView modelAndView) throws Exception;
void afterCompletion(HttpServletRequest request,
HttpServletResponse response,
Object handler,
Exception ex) throws Exception;
}
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public interface HandlerInterceptor {
boolean preHandle(HttpServletRequest request,
HttpServletResponse response,
Object handler) throws Exception;
void postHandle(HttpServletRequest request,
HttpServletResponse response,
Object handler,
ModelAndView modelAndView) throws Exception;
void afterCompletion(HttpServletRequest request,
HttpServletResponse response,
Object handler,
Exception ex) throws Exception;
}
preHandler()會在Controller處理請求之前被呼叫,傳回的boolean快定是否呼叫接下來的Handler Interceptor或是Controller來處理請求,如果傳回false,則接下來的Interceptor或Controller就不處理請 求,postHandler()則會在Controller處理完請求之後被呼叫,afterCompletion()方法會在View繪製完成之後被呼 叫。
您可以直接繼承org.springframework.web.servlet.handler.HandlerInterceptorAdapter,它實作了HandlerInterceptor介面,您只要針對您有興趣的方法進行重新定義就可以了,例如可以修改 第一個 Spring MVC 程式,在當中實作一個LoggingInterceptor,在請求被控制物件處理的前、後來作記錄:
- LoggingInterceptor.java
package onlyfun.caterpillar;
import java.util.logging.Logger;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.
handler.HandlerInterceptorAdapter;
public class LoggingInterceptor
extends HandlerInterceptorAdapter {
private Logger logger =
Logger.getLogger(this.getClass().getName());
public boolean preHandle(HttpServletRequest request,
HttpServletResponse response,
Object handler) throws Exception {
logger.info(
handler.getClass().getName() + " 開始執行...");
return true;
}
public void postHandle(HttpServletRequest request,
HttpServletResponse response,
Object handler,
ModelAndView modelAndView) throws Exception {
logger.info(
handler.getClass().getName() + " 執行完畢...");
}
public void afterCompletion(HttpServletRequest request,
HttpServletResponse response,
Object handler,
Exception ex) throws Exception {
logger.info("請求處理完畢...");
}
}
要使用定義好的HandlerInterceptor,必須在Bean定義檔中進行定義,例如:
- mvc-config.xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC
"-//SPRING/DTD BEAN/EN"
"http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
<bean id="loggingInterceptor"
class="onlyfun.caterpillar.LoggingInterceptor"/>
<bean id="viewResolver"
class="org.springframework.web.servlet.
→ view.InternalResourceViewResolver">
<property name="prefix">
<value>/WEB-INF/jsp/</value>
</property>
<property name="suffix">
<value>.jsp</value>
</property>
</bean>
<bean id="urlHandlerMapping"
class="org.springframework.web.servlet.
→ handler.SimpleUrlHandlerMapping">
<property name="interceptors">
<list>
<ref bean="loggingInterceptor"/>
</list>
</property>
<property name="mappings">
<props>
<prop key="/hello.do">helloController</prop>
</props>
</property>
</bean>
<bean id="helloController"
class="onlyfun.caterpillar.HelloController">
<property name="viewPage">
<value>hello</value>
</property>
</bean>
</beans>
注意到這邊所使用的UrlHandlerMapping是SimpleUrlHandlerMapping;當您透過DispatcherServlet請求時,則在請求被處理的前後都會被記錄下動作及所處理請求的控制物件,在控制台所看到的資訊如下所示:
2005/12/30 上午 12:03:24 onlyfun.caterpillar.LoggingInterceptor preHandle
資訊: onlyfun.caterpillar.HelloController 開始執行...
2005/12/30 上午 12:03:24 onlyfun.caterpillar.LoggingInterceptor postHandle
資訊: onlyfun.caterpillar.HelloController 執行完畢...
2005/12/30 上午 12:03:24 onlyfun.caterpillar.LoggingInterceptor afterCompletion
資訊: 請求處理完畢...
資訊: onlyfun.caterpillar.HelloController 開始執行...
2005/12/30 上午 12:03:24 onlyfun.caterpillar.LoggingInterceptor postHandle
資訊: onlyfun.caterpillar.HelloController 執行完畢...
2005/12/30 上午 12:03:24 onlyfun.caterpillar.LoggingInterceptor afterCompletion
資訊: 請求處理完畢...