spring 自定义拦截器
1.前言.
本文转自:http://blog.csdn.net/tjcyjd/article/details/7498236
2.内容。
经过一天的奋战,终于会使用了SpringMVC,下面讲下他的拦截器。使用SpringMVC拦截器和Struts2一样,SpringMVC也可以使用拦截器对请求进行拦截处理,用户可以自定义拦截器来实现特定的功能,自定义的拦截器必须实现HandlerInterceptor接口。完整的例子可以到我的资源下载:http://download.csdn.net/download/tjcyjd/4255319
HandlerInterceptor接口的代码如下:
[java]viewplaincopyprint?
01.packageorg.springframework.web.servlet;
02.importJavax.servlet.http.HttpServletRequest;
03.importJavax.servlet.http.HttpServletResponse;
04.publicinterfaceHandlerInterceptor{
05.//preHandle()方法在业务处理器处理请求之前被调用
06.booleanpreHandle(HttpServletRequestrequest,
07.HttpServletResponseresponse,
08.Objecthandler)
09.throwsException;
10.//postHandle()方法在业务处理器处理请求之后被调用
11.voidpostHandle(
12.HttpServletRequestrequest,HttpServletResponse
13.response,Object
14.handler,ModelAndViewmodelAndView)
15.throwsException;
16.//afterCompletion()方法在DispatcherServlet完全处理完请求后被调用
17.voidafterCompletion(
18.HttpServletRequestrequest,HttpServletResponse
19.response,Object
20.handler,Exceptionex)
21.throwsException;
22.
23.}
packageorg.springframework.web.servlet;
importJavax.servlet.http.HttpServletRequest;
importJavax.servlet.http.HttpServletResponse;
publicinterfaceHandlerInterceptor{
//preHandle()方法在业务处理器处理请求之前被调用
booleanpreHandle(HttpServletRequestrequest,
HttpServletResponseresponse,
Objecthandler)
throwsException;
//postHandle()方法在业务处理器处理请求之后被调用
voidpostHandle(
HttpServletRequestrequest,HttpServletResponse
response,Object
handler,ModelAndViewmodelAndView)
throwsException;
//afterCompletion()方法在DispatcherServlet完全处理完请求后被调用
voidafterCompletion(
HttpServletRequestrequest,HttpServletResponse
response,Object
handler,Exceptionex)
throwsException;
}
下面对代码中的三个方法进行解释。
preHandle():这个方法在业务处理器处理请求之前被调用,在该方法中对用户请求request进行处理。如果程序员决定该拦截器对请求进行拦截处理后还要调用其他的拦截器,或者是业务处理器去进行处理,则返回true;如果程序员决定不需要再调用其他的组件去处理请求,则返回false。
postHandle():这个方法在业务处理器处理完请求后,但是DispatcherServlet向客户端返回请求前被调用,在该方法中对用户请求request进行处理。
afterCompletion():这个方法在DispatcherServlet完全处理完请求后被调用,可以在该方法中进行一些资源清理的操作。
下面通过一个例子来说明如何使用SpringMVC框架的拦截器。
现在要编写一个拦截器,拦截所有不在工作时间的请求,把这些请求转发到一个特定的静态页面,而不对它们的请求进行处理。
首先编写TimeInterceptor.Java,代码如下:
[sql]viewplaincopyprint?
01.packagecom.yjde.web.interceptor;
02.
03.importjava.util.Calendar;
04.
05.importjavax.servlet.http.HttpServletRequest;
06.importjavax.servlet.http.HttpServletResponse;
07.
08.importorg.springframework.web.servlet.ModelAndView;
09.importorg.springframework.web.servlet.handler.HandlerInterceptorAdapter;
10.
11.publicclassTimeInterceptorextendsHandlerInterceptorAdapter{
12.//继承HandlerInterceptorAdapter类
13.
14.privateintopeningTime;//openingTime属性指定上班时间
15.privateintclosingTime;//closingTime属性指定下班时间
16.privateStringoutsideOfficeHoursPage;//outsideOfficeHoursPage属性指定错误提示页面的URL
17.
18.//重写preHandle()方法,在业务处理器处理请求之前对该请求进行拦截处理
19.publicbooleanpreHandle(HttpServletRequestrequest,
20.HttpServletResponseresponse,Objecthandler)throwsException{
21.Calendarcal=Calendar.getInstance();
22.inthour=cal.get(Calendar.HOUR_OF_DAY);//获取当前时间
23.if(openingTime<=hour&&hour<closingTime){//判断当前是否处于工作时间段内
24.returntrue;
25.}else{
26.response.sendRedirect(outsideOfficeHoursPage);//返回提示页面
27.returnfalse;
28.}
29.}
30.
31.publicvoidpostHandle(HttpServletRequestrequest,
32.HttpServletResponseresponse,Objecto,ModelAndViewmav)
33.throwsException{
34.System.out.println("postHandle");
35.}
36.
37.publicvoidafterCompletion(HttpServletRequestrequest,
38.HttpServletResponseresponse,Objecto,Exceptionexcptn)
39.throwsException{
40.System.out.println("afterCompletion");
41.}
42.
43.publicintgetOpeningTime(){
44.returnopeningTime;
45.}
46.
47.publicvoidsetOpeningTime(intopeningTime){
48.this.openingTime=openingTime;
49.}
50.
51.publicintgetClosingTime(){
52.returnclosingTime;
53.}
54.
55.publicvoidsetClosingTime(intclosingTime){
56.this.closingTime=closingTime;
57.}
58.
59.publicStringgetOutsideOfficeHoursPage(){
60.returnoutsideOfficeHoursPage;
61.}
62.
63.publicvoidsetOutsideOfficeHoursPage(StringoutsideOfficeHoursPage){
64.this.outsideOfficeHoursPage=outsideOfficeHoursPage;
65.}
66.
67.}
68.//可以看出,上面的代码重载了preHandle()方法,该方法在业务处理器处理请求之前被调用。在该方法中,首先获得当前的时间,判断其是否在
69.//openingTime和closingTime之间,如果在,返回true,这样才会调用业务控制器去处理该请求;否则直接转向一个页面,返回false,这样该请求就不会被处理。
packagecom.yjde.web.interceptor;
importjava.util.Calendar;
importjavax.servlet.http.HttpServletRequest;
importjavax.servlet.http.HttpServletResponse;
importorg.springframework.web.servlet.ModelAndView;
importorg.springframework.web.servlet.handler.HandlerInterceptorAdapter;
publicclassTimeInterceptorextendsHandlerInterceptorAdapter{
//继承HandlerInterceptorAdapter类
privateintopeningTime;//openingTime属性指定上班时间
privateintclosingTime;//closingTime属性指定下班时间
privateStringoutsideOfficeHoursPage;//outsideOfficeHoursPage属性指定错误提示页面的URL
//重写preHandle()方法,在业务处理器处理请求之前对该请求进行拦截处理
publicbooleanpreHandle(HttpServletRequestrequest,
HttpServletResponseresponse,Objecthandler)throwsException{
Calendarcal=Calendar.getInstance();
inthour=cal.get(Calendar.HOUR_OF_DAY);//获取当前时间
if(openingTime<=hour&&hour<closingTime){//判断当前是否处于工作时间段内
returntrue;
}else{
response.sendRedirect(outsideOfficeHoursPage);//返回提示页面
returnfalse;
}
}
publicvoidpostHandle(HttpServletRequestrequest,
HttpServletResponseresponse,Objecto,ModelAndViewmav)
throwsException{
System.out.println("postHandle");
}
publicvoidafterCompletion(HttpServletRequestrequest,
HttpServletResponseresponse,Objecto,Exceptionexcptn)
throwsException{
System.out.println("afterCompletion");
}
publicintgetOpeningTime(){
returnopeningTime;
}
publicvoidsetOpeningTime(intopeningTime){
this.openingTime=openingTime;
}
publicintgetClosingTime(){
returnclosingTime;
}
publicvoidsetClosingTime(intclosingTime){
this.closingTime=closingTime;
}
publicStringgetOutsideOfficeHoursPage(){
returnoutsideOfficeHoursPage;
}
publicvoidsetOutsideOfficeHoursPage(StringoutsideOfficeHoursPage){
this.outsideOfficeHoursPage=outsideOfficeHoursPage;
}
}
//可以看出,上面的代码重载了preHandle()方法,该方法在业务处理器处理请求之前被调用。在该方法中,首先获得当前的时间,判断其是否在
//openingTime和closingTime之间,如果在,返回true,这样才会调用业务控制器去处理该请求;否则直接转向一个页面,返回false,这样该请求就不会被处理。
可以看出,上面的代码重载了preHandle()方法,该方法在业务处理器处理请求之前被调用。在该方法中,首先获得当前的时间,判断其是否在openingTime和closingTime之间,如果在,返回true,这样才会调用业务控制器去处理该请求;否则直接转向一个页面,返回false,这样该请求就不会被处理。
下面是在dispatcher-servlet.xml中对拦截器进行的配置,代码如下:
[java]viewplaincopyprint?
01.<PREclass=htmlname="code"><?xmlversion="1.0"encoding="UTF-8"?>
02.<beansxmlns="http://www.springframework.org/schema/beans"
03.xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xmlns:mvc="http://www.springframework.org/schema/mvc"
04.xmlns:p="http://www.springframework.org/schema/p"xmlns:context="http://www.springframework.org/schema/context"
05.xmlns:aop="http://www.springframework.org/schema/aop"xmlns:tx="http://www.springframework.org/schema/tx"
06.xsi:schemaLocation="http://www.springframework.org/schema/beans
07.http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
08.http://www.springframework.org/schema/context
09.http://www.springframework.org/schema/context/spring-context-3.0.xsd
10.http://www.springframework.org/schema/aop
11.http://www.springframework.org/schema/aop/spring-aop-3.0.xsd
12.http://www.springframework.org/schema/tx
13.http://www.springframework.org/schema/tx/spring-tx-3.0.xsd
14.http://www.springframework.org/schema/mvc
15.http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd
16.http://www.springframework.org/schema/context
17.http://www.springframework.org/schema/context/spring-context-3.0.xsd">
18.<!--
19.使Spring支持自动检测组件,如注解的Controller
20.-->
21.<context:component-scanbase-package="com.yjde.web.controller"/>
22.
23.<beanid="viewResolver"
24.class="org.springframework.web.servlet.view.InternalResourceViewResolver"
25.p:prefix="/WEB-INF/jsp/"p:suffix=".jsp"/>
26.<mvc:interceptors>
27.<mvc:interceptor>
28.<!--设置拦截的路径-->
29.<mvc:mappingpath="/login1.htm"/>
30.<mvc:mappingpath="/login2.htm"/>
31.<beanclass="com.yjde.web.interceptor.TimeInterceptor">
32.<!--openingTime属性指定上班时间-->
33.<propertyname="openingTime">
34.<value>12</value>
35.</property>
36.<!--closingTime属性指定下班时间-->
37.<propertyname="closingTime">
38.<value>14</value>
39.</property>
40.<!--outsideOfficeHoursPage属性指定提示页面的URL-->
41.<propertyname="outsideOfficeHoursPage">
42.<value>http://localhost:8080/SpringMVCInterceptor/jsp/outsideOfficeHours.jsp
43.</value>
44.</property>
45.</bean>
46.</mvc:interceptor>
47.</mvc:interceptors>
48.<beanid="messageSource"
49.class="org.springframework.context.support.ResourceBundleMessageSource"
50.p:basename="message">
51.</bean>
52.</beans></PRE><BR>
53.<BR>
54.<PRE></PRE>
55.<P></P>
56.<PRE></PRE>
57.<P></P>
58.<Pstyle="BACKGROUND:white"align=left><SPANstyle="COLOR:#555555">可以看出,上面代码用bean</SPAN>标签去定义TimeInterceptor,令其id为officeHoursInterceptor,并给它的3个属性赋值。具体的大家可以运行一下项目看看。</P>
59.<Pstyle="BACKGROUND:white"align=left><SPANstyle="COLOR:#555555"></SPAN></P>
60.<Pstyle="BACKGROUND:white"align=left><SPANstyle="COLOR:#555555">说明:控制反转是Spring</SPAN>框架的核心思想,即用一个接口去定义一些操作,在接口的实现类中去重写这些操作,然后在Spring的配置文件中去把该接口的实现类注入到应有框架中,这样就可以通过调用接口去调用接口的实现类。此次讲的拦截器就体现了这种思想,即实现HandlerInterceptorAdapter接口,重写preHandle()方法并在配置文件中实现TimeInterceptor的注入。这
61.样当框架调用HandlerInterceptorAdapter时,就可以调用到TimeInterceptor类的preHandle()方法。</P>
62.<Pstyle="BACKGROUND:white"align=left></P>
63.<H4><Aname=t1></A><SPANstyle="FONT-FAMILY:KaiTi_GB2312;FONT-SIZE:16px"><SPANstyle="BACKGROUND-COLOR:white">完整的例子可以到我的资源下载:<Ahref="http://download.csdn.net/download/tjcyjd/4255319">http://download.csdn.net/download/tjcyjd/4255319</A></SPAN></SPAN></H4>
64.<P></P>
65.<Pstyle="BACKGROUND:white"align=left><BR>
66.</P>
67.<P></P>