spring-aop - 来自 ExceptionHandler 的 @AfterReturning 不起作用
问题描述
我有一个 GlobalExceptionHandler 类,其中包含多个用 @ExceptionHandler 注释的方法。
@ExceptionHandler({ AccessDeniedException.class })
public final ResponseEntity<Object> handleAccessDeniedException(
Exception ex, WebRequest request) {
return new ResponseEntity<Object>(
"Access denied message here", new HttpHeaders(), HttpStatus.FORBIDDEN);
}
我有一个 AOP,假设在异常处理程序返回响应后触发。
@AfterReturning(value="@annotation(exceptionHandler)",returning="response")
public void afterReturningAdvice(JoinPoint joinPoint, Object response) {
//do something
}
但是在处理程序返回有效响应后,不会触发 @AfterReturning。
尝试了完整的限定名但不起作用
@AfterReturning(value = "@annotation(org.springframework.web.bind.annotation.ExceptionHandler)", returning = "response"){
public void afterReturningAdvice(JoinPoint joinPoint, Object response) {
//do something
}
解决方案
请阅读文档以了解 Spring 框架中的代理机制。
假设ExceptionHandler
编写的代码具有以下格式
@ControllerAdvice
public class TestControllerAdvice {
@ExceptionHandler({ AccessDeniedException.class })
final public ResponseEntity<Object> handleAccessDeniedException(
Exception ex, WebRequest request) {
return new ResponseEntity<Object>(
"Access denied message here", new HttpHeaders(), HttpStatus.FORBIDDEN);
}
}
与该问题有关的文档中的关键点是
Spring AOP 使用 JDK 动态代理或 CGLIB 为给定的目标对象创建代理。
如果要代理的目标对象实现了至少一个接口,则使用 JDK 动态代理。目标类型实现的所有接口都被代理。如果目标对象没有实现任何接口,则创建一个 CGLIB 代理。
使用 CGLIB,不能建议最终方法,因为它们不能在运行时生成的子类中被覆盖。
- OP 根据评论和提示确定了该问题,此答案可供将来参考。
推荐阅读
- r - 双变量不连续函数的曲面
- php - 'python' 不是使用 PHP passthru() 的内部或外部命令、可运行程序或批处理文件
- php - Converge API - 检查 API 是否可用
- c++ - 如何决定我应该使用全局变量还是应该使用堆?
- python - Pandas cumsum + cumcount 多列
- java - 在 JAVA 和 PHP 中加密返回不同的结果
- python - python-glob2 例子不清楚
- nginx - 在 nginx.conf 中使用环境变量或参数
- android - 从房间中的实体中检索列表类型字段
- c# - 在对象列表中查找第一个匹配的字符串值