SpringMvc—拦截器「建议收藏」

SpringMvc—拦截器「建议收藏」SpringMvc拦截器作用拦截器是用来拦截经过dispatcherServlet【请求控制器】的请求。它用来拦截控制器方法的执行。拦截器通过实现接口HandlerInterceptor并在S

大家好,又见面了,我是你们的朋友全栈君。

SpringMvc—拦截器

作用

拦截器是用来拦截经过dispatcherServlet【请求控制器】的请求。它用来拦截控制器方法的执行。

拦截器通过实现接口HandlerInterceptor并在SpringMvc配置文件中添加配置实现拦截功能。记得为拦截器类加注解把它加到IOC容器中

使用

在拦截器中

首先添加注解,@Component【既不是bean、也不是service、也不是controller,是一个基本java类,所以用它声明,用别的也行】,然后实现接口HandlerInterceptor,实现三个方法

@Component
public class FirstInterceptor implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        System.out.println("FirstInterceptor--preHandle--控制器方法执行之前执行");
        return true;
    }
​
    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        System.out.println("FirstInterceptor--postHandle---控制器方法执行之后执行");
    }
​
    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        System.out.println("FirstInterceptor---afterCompletion----视图渲染完毕执行");
    }
}

 

 

在SpringMvc配置文件中

首先添加命名空间mvc、context,开启组件扫描、添加视图解析器thymeleaf、开启mvc注解扫描。

配置文件中的标签的作用注释里都有

    <mvc:interceptors>
<!--使用bean标签注册的拦截器会对经过dispatcherServlet的所有请求进行处理,使用ref也是一样的-->
<!--        <bean class="xlw.com.SpringMvc03.Interceptor.FirstInterceptor"></bean>-->
<!--        <ref bean="firstInterceptor"></ref>-->
<!--        <mvc:interceptor>-->
<!--使用标签mvc:interceptor可以规定那些请求被拦截哪些不被拦截,可以设置多个,最后要对拦截器注册-->
<!--            <mvc:mapping path="/test?"/>-->
<!--            <mvc:exclude-mapping path="/"/>-->
<!--            <mvc:exclude-mapping path="/test1"/>-->
<!--            <ref bean="firstInterceptor"></ref>-->
<!--        </mvc:interceptor>-->
​
        <ref bean="firstInterceptor"></ref>
        <ref bean="secondInterceptor"></ref>
​
    </mvc:interceptors>
 

 

多个拦截器(preHandle返回true)

在上面的配置文件中配置两个拦截器,在对请求进行拦截时可以发现方法的执行顺序 有些不同

第二个拦截器

@Component
public class SecondInterceptor implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        System.out.println("SecondInterceptor--preHandle--控制器方法执行之前执行");
        return true;
    }
​
    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        System.out.println("SecondInterceptor--postHandle---控制器方法执行之后执行");
    }
​
    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        System.out.println("SecondInterceptor---afterCompletion----视图渲染完毕执行");
    }
}

 

 

拦截器处理请求后结果

可以发现,preHandle执行顺序是跟在配置文件的先后注册顺序执行的,postHandle和AfterCompletion是反过来执行的

FirstInterceptor--preHandle--控制器方法执行之前执行
SecondInterceptor--preHandle--控制器方法执行之前执行
SecondInterceptor--postHandle---控制器方法执行之后执行
FirstInterceptor--postHandle---控制器方法执行之后执行
SecondInterceptor---afterCompletion----视图渲染完毕执行
FirstInterceptor---afterCompletion----视图渲染完毕执行

 

在源码中

首先为控制器方法打上断点。debug启动服务器,进入断点模式,然后再debug底下的控制台执行方法找到DispatchServlet的1061,点进去,做好以下断点。

再对断点放行,再次请求资源。开始观察。

第一个断电对应的正是preHandle方法,在if的判断条件中,发现需要一个true的返回值,与感叹号一起使判断条件变成false,才能使程序继续往下执行,否则就会终结当前循环

SpringMvc---拦截器「建议收藏」

 

 

 

点击下一行进入applyPreHandle方法具体执行中,发现有一个++的for循环,里面循环执行一个Interceptor的list数组,可以看见list里面正是SpringMvc自己的interceptor和我自己注册的interceptor,++执行就确保了PreHandle方法按照在配置文件中的顺序执行。

 

在for循环中的if判断,就是判断返回值是不是false,如果是就会执行当前的afterCompletion方法【就是最后执行的那个方法】,并且返回false终结掉DispatcherServlet中的程序执行。如果返回的是true,就会按照在list中的顺序执行

 

 

preHandel执行完后会跳到下一个断点,就是那个mv那一行,进行获取视图名称。再跳到下一个断点就会回到控制器方法,在跳到下一个断点就是那个postHandel方法。

 

来到postHandel的哪一行断点,点击下一行,进入postHandel,发现是一个–的for循环,循环的依旧是那个interceptor的list集合,所以就能知道为什么postHandel的执行顺序和配置文件中的相反。afterCompletion方法的执行也和这个postHandel一样–for循环

 

SpringMvc---拦截器「建议收藏」

 

 

 

 

SpringMvc---拦截器「建议收藏」

 

 

 

多个拦截器(preHandel返回false)

依旧是断点模式,但是是将preHandel返回值变成false。就会发现,在进入applyPreHandel方法中后,先执行第一个注册的interceptor的preHandel方法,执行后再执行第二个拦截器,但是第二个拦截器的返回值被修改为false,就会通过applyPreHandel的for循环中的if判断,中执行第一个interceptor的triggerAfterCompletion并返回false。

再回到Dispatch Servlet中就会通过if判断,执行return,后面的就不执行了。请求被拦截。

 

所以在有多个interceptor被注册后,其中有一个interceptor的preHandel方法的返回值为false,那么在这个拦截器之前注册的拦截器的preHandel方法和afterCompletion方法都会执行,这个拦截器的preHandel方法也会执行。post Handel方法都不执行

 

SpringMvc---拦截器「建议收藏」

 

 

 

 

 

 SpringMvc---拦截器「建议收藏」

 

 

 

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/154784.html原文链接:https://javaforall.net

赞 (0)
全栈程序员-站长的头像全栈程序员-站长

相关推荐

  • Java代码求水仙花数

    Java代码求水仙花数这里写自定义目录标题Java代码求水仙花数Java代码求水仙花数//求水仙花数.//1.什么是水仙花数//2.水仙花数是一个三位数,且水仙花的个位,十位,百位的数字立法和等于原数。publicclassdemo_18{publicstaticvoidmain(String[]args){intnumber=0,x=0,y=0,z=0;//x表示3位数的百位上的数字,y表示三位百位上的数字,z表示三位数上个位的数字intcount

    2022年7月9日
  • 一文说清楚pytorch和tensorFlow的区别究竟在哪里

    最近用了一点pytorch,想着稍稍理一下,这样一个和TensorFlow抗衡的一个框架,究竟是何方神圣?首先我们要搞清楚pytorch和TensorFlow的一点区别,那就是pytorch是一个动态的框架,而TensorFlow是一个静态的框架。何为静态的框架呢?我们知道,TensorFlow的尿性是,我们需要先构建一个TensorFlow的计算图,构建好了之后,这样一个计算图是不能够变的了…

    2022年4月5日
  • windows server 禁用智能卡服务的步骤

    windows server 禁用智能卡服务的步骤许多用户对于系统中的很多功能都不太了解,其中智能卡服务更是少有人知。智能卡服务就是对插入的智能卡进行管理和访问控制,大多数用户都无需使用此项功能。那么在Win7系统中要怎么取消智能卡服务呢?1.首先

    2022年7月1日
  • webbench源码分析_webpack原理和机制

    webbench源码分析_webpack原理和机制webbench是一种网站的压力测试工具,它是由Lionbridge公司开发,wenbench的标准测试可以向我们展示两项内容:每秒钟相应的请求数和每秒钟传输的数据量;。webbench不但能具有便准静态页面的测试能力,还能对动态页面(ASP,PHP,Java,CGI)进行测试的能力。还有就是他支持对含有SSL的安全网站例如电子商务网站进行静态或动态的性能测试。Webbench最多可以模拟3

    2022年11月3日
  • Laravel5性能优化技巧

    Laravel5性能优化技巧

    2022年3月8日
  • LC5–ftp服务器密码检测

    LC5–ftp服务器密码检测目录实验目的:实验任务:实验原理:实验环境:实验步骤:实验目的:1.掌握FTP服务器的搭建方法2.理解FTP的使用。3.学习LC5激活成功教程密码工具的配置和使用方法。实验任务:1、架设一个简单的FTP服务器,分配用户,并…

    2022年7月24日

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号