详解Spring流程及多个的执⾏顺序
⽬录
的定义
测试
多个的执⾏顺序
让 preHandle 进⾏拦截
总结
是 Spring MVC 中的组件,它可以在进⼊请求⽅法前做⼀些操作,也可以在请求⽅法后和渲染视图后做⼀些事情。
的定义
SpringMVC 的只需要实现 HandlerInterceptor 接⼝,并进⾏配置即可。HandlerInterceptor 接⼝的定义如下:
public interface HandlerInterceptor {
default boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
return true;
}
default void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable ModelAndView modelAndView) throws Exception { }
default void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable Exception ex) throws Exception {
}
}
在 HandlerInterceptor 中共有三个⽅法,每个⽅法的含义如下:
preHandler:进⼊请求⽅法之前执⾏;
postHandler:请求⽅法执⾏完成之后执⾏;
afterCompletion:视图渲染后执⾏。
的执⾏流程
在 preHandle ⽅法中,它的返回值是 boolean 类型的,它的返回值影响着请求⽅法,以及 postHandle 和 afterCompletion 的执
⾏。具体如下。
也就是说,在 preHandle 中如果返回 false,那么后续的流程将不被执⾏,这可能也是命名的由来。
测试
写⼀个简单,代码如下:
@Slf4j
public class TestInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
log.info("preHandler");
return true;
cacheable}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
log.info("postHandler");
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
log.info("afterCompletion");
}
}
创建了⼀个 TestInterceptor 的类,它实现了 HandlerInterceptor 的所有接⼝。写完 TestInterceptor 还需要进⾏注册。代码如下:
@Configuration
public class InterceptorConfig implements WebMvcConfigurer {
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(testInterceptor());
}
再来写⼀个简单的请求⽅法,代码如下:
@GetMapping("test")
public String test()
{
return "test";
}
来启动我们的项⽬,并进⾏访问,控制台的输出如下:
2021-05-05 16:02:08.110 INFO 88509 --- [nio-8081-exec-6] ample.demo.TestInterceptor : preHandler
2021-05-05 16:02:08.111 INFO 88509 --- [nio-8081-exec-6] ample.demo.TestInterceptor : postHandler
2021-05-05 16:02:08.111 INFO 88509 --- [nio-8081-exec-6] ample.demo.TestInterceptor : afterCompletion
多个的执⾏顺序
我们来写多个相同的,分别是 TestInterceptor、TestInterceptor2 和 TestInterceptor3。然后我们进⾏注册,注册代码如下:@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(testInterceptor());
registry.addInterceptor(testInterceptor2());
registry.addInterceptor(testInterceptor3());
}
请求我们的⽅法,输出如下:
2021-05-05 16:09:57.735 INFO 88572 --- [nio-8081-exec-1] ample.demo.TestInterceptor : preHandler
2021-05-05 16:09:57.736 INFO 88572 --- [nio-8081-exec-1] ample.demo.TestInterceptor2 : preHandler2
2021-05-05 16:09:57.736 INFO 88572 --- [nio-8081-exec-1] ample.demo.TestInterceptor3 : preHandler3
2021-05-05 16:09:57.755 INFO 88572 --- [nio-8081-exec-1] ample.demo.TestInterceptor3 : postHandler3
2021-05-05 16:09:57.755 INFO 88572 --- [nio-8081-exec-1] ample.demo.TestInterceptor2 : postHandler2
2021-05-05 16:09:57.755 INFO 88572 --- [nio-8081-exec-1] ample.demo.TestInterceptor : postHandler
2021-05-05 16:09:57.755 INFO 88572 --- [nio-8081-exec-1] ample.demo.TestInterceptor3 : afterCompletion3
2021-05-05 16:09:57.755 INFO 88572 --- [nio-8081-exec-1] ample.demo.TestInterceptor2 : afterCompletion2
2021-05-05 16:09:57.755 INFO 88572 --- [nio-8081-exec-1] ample.demo.TestInterceptor : afterCompletion
注意观察输出的顺序,preHandle ⽅法是按注册顺序进⾏执⾏的,⽽ postHandle 和 afterCompletion 跟注册顺序是相反的。
让 preHandle 进⾏拦截
我们让 TestInterceptor2 的 preHandle 返回值为 false,然后查看⼀下输出内容。
2021-05-05 16:14:00.997 INFO 88582 --- [nio-8081-exec-1] ample.demo.TestInterceptor : preHandler
2021-05-05 16:14:00.998 INFO 88582 --- [nio-8081-exec-1] ample.demo.TestInterceptor2 : preHandler2
2021-05-05 16:14:00.998 INFO 88582 --- [nio-8081-exec-1] ample.demo.TestInterceptor : afterCompletion
可以看到,TestInterceptor2 的 preHandle 的返回值为 false 以后,相当于在 TestInterceptor2 的 preHandle 后续流程则不再继续执⾏了。
我们调整⼀下注册的顺序,代码如下:
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(testInterceptor2());
registry.addInterceptor(testInterceptor());
registry.addInterceptor(testInterceptor3());
}
修改顺序后的输出如下:
2021-05-05 16:17:23.956 INFO 88589 --- [nio-8081-exec-1] ample.demo.TestInterceptor2 : preHandler2
可以看到它后⾯的流程都被拦截了,没有机会执⾏了。
总结
是使⽤⼀个 List 进⾏保存,我们可以在项⽬中添加多个来完成不同的功能,⽐如可以进⾏ Token 的验证,权限的获取等。我们可以放到不同的中来进⾏相关的操作。
以上就是详解Spring 流程及多个的执⾏顺序的详细内容,更多关于Spring 的资料请关注其它相关⽂章!
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论