Spring MVC中的拦截器(很详细)

前言

在学习SSM的时候遇到了拦截器问题,Spring MVC的处理器拦截器类似于Servlet 开发中的过滤器Filter,本文主要总结一下Spring MVC中拦截器是如何定义的,以及测试拦截器的执行情况和使用方法。供大家参考

拦截器(Interceptor)

拦截器的前世今生

HandlerInterceptor接口中,定义了 3 个方法,分别为preHandle()postHandle()afterCompletion(),我们就是通过复写这 3 个方法来对用户的请求进行拦截处理的。因此,我们可以通过直接实现HandlerInterceptor接口来实现拦截器的功能。不过在 Spring 框架之中,其还提供了另外一个接口和一个抽象类,实现了对HandlerInterceptor接口的功能扩展,分别为:AsyncHandlerInterceptorHandlerInterceptorAdapter.

对于AsyncHandlerInterceptor接口,其在继承HandlerInterceptor接口的同时,又声明了一个新的方法afterConcurrentHandlingStarted();而HandlerInterceptorAdapter抽象类,则是更进一步,在其继承AsyncHandlerInterceptor接口的同时,又复写了preHandle方法。因此,AsyncHandlerInterceptor更像是一个过渡的接口。

在实际应用中,我们一般都是通过实现HandlerInterceptor接口或者继承HandlerInterceptorAdapter抽象类,复写preHandle()、postHandle()和afterCompletion()这 3 个方法来对用户的请求进行拦截处理的。

什么是拦截器

  • Spring MVC中的拦截器(Interceptor)类似于Servlet中的过滤器(Filter),它主要用于拦截用户请求并作相应的处理。例如通过拦截器可以进行权限验证、记录请求信息的日志、判断用户是否登录等。要使用Spring MVC中的拦截器,就需要对拦截器类进行定义和配置。通常拦截器类可以通过两种方式来定义:
  1. 通过实现HandlerInterceptor接口,或继承HandlerInterceptor接口的实现类(如HandlerInterceptorAdapter)来定义。

  2. 通过实现WebRequestInterceptor接口,或继承WebRequestInterceptor接口的实现类来定义。

首先讲解实现HandlerInterceptor接口定义拦截器

/**
 * 定义拦截器,实现 HandlerInterceptor 接口,实现接口的三个方法
 */
public class SysInterceptor implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o) throws Exception {
    	//false表示拦截,不向下执行;true表示放行
        return false;
    }

    @Override
    public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) throws Exception {

    }

    @Override
    public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception {

    }
}

详解三个方法

  1. preHandle方法:该方法会在控制器方法前执行,其返回值表示是否中断后续操作。当其返回值为true时,表示继续向下执行;可以用于身份认证、身份授权。比如如果认证没有通过表示用户没有登陆,需要此方法拦截不再往下执行(return false),否则就放行(return true)。
  2. postHandle方法:该方法会在控制器方法调用之后,且解析视图之前执行。可以看到该方法中有个modelAndView的形参。应用场景:从modelAndView出发:将公用的模型数据(比如菜单导航之类的)在这里传到视图,也可以在这里同一指定视图。
  3. afterCompletion方法:该方法会在整个请求完成,即视图渲染结束之后执行。应用场景:统一异常处理,统一日志处理等。

拦截器的xml配置

	<!--拦截器-->
	<mvc:interceptors>
		<!--可以配置多个拦截器-->
		<mvc:interceptor>
		 <!--配置拦截器的作用路径-->
			<mvc:mapping path="/*/sys/*"/>
			<!--定义在<mvc:interceptor>下面的表示匹配指定路径的请求才进行拦截-->
			<bean class="cn.smbms.inteceptor.AdminInteceptor"></bean>
		</mvc:interceptor>
	</mvc:interceptors>

上面的代码中,<mvc:interceptors>元素用于 配置一组拦截器 ,基子元素<bean>中定义的是全局拦截器,它会拦截所有的请求;而<mvc:interceptor>元素中定义的是指定路径的拦截器,它会对指定路径下的请求生效。<mvc:interceptor>元素的子元素<mvc:mapping>用于配置拦截器作用的路径,该路径在其属性path 中定义。如上述代码中 path 的属性值“/**” 表示拦截所有路径,“/hello” 表示拦截所有以 “/hello” 结尾的路径。如果在请求路径中包含不需要拦截的内容,还可以通过<mvc:exclude-mapping>元素进行配置。

注意<mvc:interceptor>中的子元素必须按照上述代码中的配置顺序进行编写,即<mvc:mapping> <mvc:exclude-mapping> <bean>,否则文件会报错。

执行流程

  1. 程序先执行preHandle()方法,如果该方法的返回值为true,则程序会继续向下执行处理器中的方法,否则将不再向下执行。

  2. 在业务处理器(即控制器Controller类)处理完请求后,会执行postHandle()方法,然后会通过DispatcherServlet向客户端返回响应。

  3. 在DispatcherServlet处理完请求后,才会执行afterCompletion()方法。

继承抽象类 HandlerInterceptorAdapter

里面的方法根据自己的需求实现即可。

public class SysInterceptor1 extends HandlerInterceptorAdapter {
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
            throws Exception {
        System.out.println("WrongCodeInterceptor, preHandle......");
        return true;
    }

    @Override
    public void postHandle(
            HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView)
            throws Exception {
        System.out.println("WrongCodeInterceptor, postHandle......");
    }

    @Override
    public void afterCompletion(
            HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
            throws Exception {
        System.out.println("WrongCodeInterceptor, afterCompletion......");
    }

    @Override
    public void afterConcurrentHandlingStarted(
            HttpServletRequest request, HttpServletResponse response, Object handler)
            throws Exception {
        System.out.println("WrongCodeInterceptor, afterConcurrentHandlingStarted......");
    }
}

总结

本篇博文带大家了解Spring MVC拦截器的流程,常用的接口和抽象类。

  • 0
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值