五
本篇是本人记录对于Spring的拦截器简单的使用记录,以及通过自定义注解的方式实现其拦截目的
首先看一下简单的实现
第一步:定义一个测试类,用于向后台发送请求
@RestController
public class Hello {
@RequestMapping("/sayHello")
public String sayHello(){
return "Hello,World!";
}
@RequestMapping("/helloInterceptor")
public String helloInterceptor(){
return "访问helloInterceptor";
}
}
第二步:定义一个自己的拦截器,需要实现Spring提供的HandlerInterceptor接口
public class MyInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response,
Object handler) throws Exception {
response.setContentType("application/json; charset=utf-8");
String a = request.getParameter("a");
if(null != a && a.equals("a"){
return true;
}else {
response.getWriter().print("你访问的资源需要登录");
return false;
}
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response,
Object handler, ModelAndView modelAndView) throws Exception {
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response,
Object handler, Exception ex) throws Exception {
}
}
这一步中,我们要求所有请求都需要带上指定的参数a,参数的值也是a,如果向后台发送到请求没有加上这个参数值的话,那么就会被拦截,反之则不会;
第三步:将上面的拦截器添加到拦截器链中,这里需要定义一个实现了WebMvcConfigurer接口的配置类
@Configuration
public class MyInterceptorConfigurer implements WebMvcConfigurer {
@Override
public void addInterceptors(InterceptorRegistry registry) {
//这种方式会拦截所有请求
//registry.addInterceptor(new MyInterceptor());
//这种方式会拦截指定的请求
registry.addInterceptor(new MyInterceptor()).addPathPatterns("/helloInterceptor");
}
}
好了,以上三部完成后,一个简单的web请求拦截器就已经可以使用了
接下来,启动项目,并在浏览器中进行访问
第一次请求
:sayHello
OK我们看到,这次请求未被拦截,顺利执行了
这是因为我们在拦截器链中指定了只对**helloInterceptor()**的访问进行拦截
第二次请求
:helloInterceptor
OK我们看到,这次的请求被拦截了,因为我们没有按要求带上指定的参数
第三次请求:
helloInterceptor?a=a
好的我们可以看到,当我们按照要求带上指定的参数后,那么请求是可以正确到达我们的目标方法的
通过上面的测试,可以看到,上面的方法虽然可以对访问请求进行拦截,但是当我们项目中的接口很多的时候,往往需要我们对大量的访问请求的进行拦截指定
那么接下来,再来看一下,如何通过注解,来实现对访问请求的拦截
首先,我们定义一个自定义的注解
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface LoginIntercept {
}
自定义注解的各个参数这里就不进行过多的描述了,这并不是本篇的重点;
自定义注解定义好了之后,我们首先想修改一下我们的测试类
@RestController
public class Hello {
@RequestMapping("/sayHello")
public String sayHello(){
return "Hello,World!";
}
@LoginIntercept
@RequestMapping("/helloInterceptor")
public String helloInterceptor(){
return "访问helloInterceptor";
}
}
注意,我们在 /helloInterceptor方法的上面,加上了我们自定义的注解,而**/sayHello**方法上面并没有加
然后对原先的拦截器方法进行修改
public class MyInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response,
Object handler) throws Exception {
//获取方法处理器
HandlerMethod handlerMethod = (HandlerMethod) handler;
LoginIntercept loginIntercept =
handlerMethod.getMethod()//这一步是获取到我们要访问的方法
//然后根据我们制定的自定义注解的Class对象来获取到对应的注解
.getAnnotation(LoginIntercept.class);
//如果要访问的方法上没有加这个注解,那么就说明这个方法不需要拦截,否则就需要进行拦截
if(null == loginIntercept){
System.out.println("访问的方法无需拦截");
return true;
}else {
response.setContentType("application/json; charset=utf-8");
String a = request.getParameter("a");
if(null != a && a.equals("a")){
return true;
}else {
response.getWriter().print("请求被拦截");
return false;
}
}
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response,
Object handler, ModelAndView modelAndView) throws Exception {
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response,
Object handler, Exception ex) throws Exception {
}
}
最后修改一下我们的配置类
@Configuration
public class MyInterceptorConfigurer implements WebMvcConfigurer {
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(new MyInterceptor());
}
}
现在,我们的配置类将会对所有方法进行拦截,接下来我们看一下不同的访问结果
很显然,访问的结果和之前的三次访问结果一模一样,但是不同的是,当我们现在访问sayHello是,控制台输出了一句话:访问的方法无需拦截
以上就是本人对于Spring拦截器的简单实现以及通过自定义注解实现访问拦截的test记录,其中的核心分别是Spring的
HandlerInterceptor接口
及其 public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) 方法
和Spring的
WebMvcConfigurer接口
及其 public void addInterceptors(InterceptorRegistry registry) 方法