springboot 拦截方式探究

2024/10/9 拦截

在我们完成项目开发后,当应用运行一段时间或许发现,由于之前的设计考虑不周,需要对业务逻辑代码做下增强,我们大多是不愿动原有的代码的,毕竟我们的代码能跑起来就尽量不要动,是我们大多数开发者所期望的。我们就来看一下springboot中如何处理拦截,织入代码。我们常用的技术手段有:过滤器(Filter),拦截器(HandlerInterceptor),ControllerAdvice注解,Aop。

注意的是ControllerAdvice注解只能用在controller上,Filter只要是Java语言都可以,Interceptor只能用于Spring框架。

# 执行顺序

Filter--->Interceptor--->ControllerAdvice--->Aop--->Controller。

# 1. Filter

Filter是用于处理HTTP请求的组件,它允许你在请求到达Controller之前或之后执行某些操作。Filter通常用于执行一些通用的任务,如日志记录、权限检查、性能监控等。在Spring Boot中,你可以通过实现javax.servlet.Filter接口来创建自定义的Filter。然后,将这个Filter注册到Spring的Web应用程序上下文中。

public class CustomFilter implements Filter {
@Override
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
throws IOException, ServletException {
// 在请求到达Controller之前或之后执行某些操作
chain.doFilter(request, response);
1
2
3
4
5
6

# 2. Interceptor

Interceptor是用于处理HTTP请求和响应的组件。与Filter类似,Interceptor也可以在请求到达Controller之前或之后执行某些操作。但是,与Filter不同的是,Interceptor可以访问Controller方法的参数。在Spring MVC中,你可以通过实现org.springframework.web.servlet.HandlerInterceptor接口来创建自定义的Interceptor。

public class CustomInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
throws Exception {
// 在请求到达Controller之前执行某些操作
return true;
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView)
throws Exception {
// 在请求到达Controller之后,但在视图渲染之前执行某些操作
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
throws Exception {
// 在请求完成之后执行某些操作,包括视图渲染和异常处理
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18

# 3. ControllerAdvice

ControllerAdvice是一种特殊的Aspect,它允许你在Controller方法出现异常时执行特定的操作,或者在Controller方法返回特定的视图时执行特定的操作。ControllerAdvice也可以用来实现全局的异常处理和数据验证。在Spring MVC中,你可以通过实现org.springframework.web.bind.annotation.ControllerAdvice或org.springframework.web.servlet.mvc.method.annotation.ModelAndViewResolverAdvice接口来创建自定义的ControllerAdvice。

@ControllerAdvice
public class GlobalExceptionHandler {
@ExceptionHandler(value = YourExceptionClass.class)
public ResponseEntity handleYourException(YourExceptionClass ex) {
// 处理YourExceptionClass类型的异常
return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(ex.getMessage());
}
}
1
2
3
4
5
6
7
8

# 4. Aop

Aop(面向切面编程)是Spring框架提供的一种支持面向切面编程的机制。它允许你将一些与业务逻辑无关的代码(如日志记录、事务管理等)从业务逻辑代码中分离出来,从而提高代码的可重用性和可维护性。在Spring Boot中,你可以通过使用@AspectJ或@Aspect注解以及Spring AOP库来创建自定义的Aspect。一个Aspect是一个类,它包含了一个或多个切点(pointcut)和一个或多个通知(advice)。切点定义了Aspect应该“织入”(weave)哪些方法,而通知定义了在方法被织入时应执行哪些操作。

@Aspect
public class LoggingAspect {
@Before("execution(* com.example.service.*.*(..))") // 定义切点
public void logBefore() {
// 在方法执行之前执行特定的操作(如日志记录)
}
}
1
2
3
4
5
6
7