springboot自定义拦截器的方法
拦截器应该分属于web框架的组件,每个框架提供的自己的支持,实现方式也就不同。例如Struts和Spring,以下是Spring 的拦截器总结,它是基于动态代理(反射)实现的。
Spring 中声明拦截器需要实现 HandlerInterceptor 接口,当然也可以通过继承HandlerInterceptorAdapter 抽象类,HandlerInterceptorAdapter也是实现了HandlerInterceptor 接口。
拦截器中有四个方法:
preHandle:在Controller中的方法之前执行,决定是否放行,return true表示放行。一旦放行其对应的afterCompletion就一定会执行。
postHandle:Controller中的方法处理完之后,DispatcherServlet进行视图的渲染之前,也就是说在这个方法中你可以对ModelAndView进行操作
afterCompletion:DispatcherServlet进行视图的渲染之后
afterConcurrentHandlingStarted:与异步相关
下面通过代码实践,备注了是否放行和异常对拦截器内方法执行的影响结论。其实只需对方法执行的时机进行分析,我们就可以得出相同的结论。
如果想深入了解每个方法的执行时机,可以阅读SpringMVC的 DispatcherServlet 源码
@Component
public class InterceptorTwo extends HandlerInterceptorAdapter {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
//这里我们是没办法拿到方法参数的,parameters是空的,但是可以拿到controller种注入的bean
//可以断点验证
HandlerMethod handlerMethod = (HandlerMethod)handler;
MethodParameter [] parameters = handlerMethod.getMethodParameters();
return true;//放行
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
//在拦截器链中,只要有一个不放行的,所有的postHandle都不会执行
//如果Controller方法抛异常了,所有的postHandle也不会执行
System.out.println("postHandle");
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
//只要对应的preHandle放行了就一定会执行,Controller方法抛异常也不会影响
System.out.println("afterCompletion");
}
@Override
public void afterConcurrentHandlingStarted(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
System.out.println("afterConcurrentHandlingStarted");
}
}
使拦截器生效
//Springboot 是1.x版本的项目中是extends WebMvcConfigurerAdapter ,代码也是一样的
@Configuration
public class InterceptorConfig implements WebMvcConfigurer {
@Autowired
private SourceAccessInterceptor interceptor;
@Autowired
private InterceptorOne interceptorOne;
@Override
public void addInterceptors(InterceptorRegistry interceptorRegistry) {
//1.加入的顺序就是拦截器执行的顺序,设置@Order也不会影响
//2.按顺序执行所有拦截器的preHandle
//3.所有的preHandle 执行完再反向执行全部postHandle 最后是反向执行afterCompletion,
//如果其中有一个未放行,或者抛异常了会影响执行顺序吗?怎样影响
interceptorRegistry.addInterceptor(interceptor).addPathPatterns("
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
HandlerMethod handlerMethod = (HandlerMethod) handler;
//WithoutToken是我自定义的注解,标注在方法上,表示不需要验证token
if (handlerMethod.getMethod().isAnnotationPresent(WithoutToken.class)) {
//不需要验证token
return true;
} else {
try {
//校验jwt
String access_token = request.getHeader("access_token");
jwtUtil.verifierToken(access_token);
//获取用户信息
final String account = jwtUtil.getAccount(access_token);
//TODO 可以在这里查询用户信息,然后将用户信息设置到线程变量
} catch (NullPointerException | JWTVerificationException e) {
//TODO 重定向到登陆页
response.sendRedirect(loginUrl);
return false;
}
return true;
}
}
}
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持编程网。
免责声明:
① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。
② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341