AOP(Aspect-Oriented Programming,面向切面编程)通知类型分为以下几种:
1. 前置通知(Before Advice):在目标方法执行前执行的通知类型。通过该通知类型可以在执行目标方法前进行一些操作,例如参数校验、日志记录等。示例代码如下:
@Aspect
@Component
public class LogAspect {
@Before("execution(* com.example.demo.service.*.*(..))")
public void before(JoinPoint joinPoint) {
System.out.println("method " + joinPoint.getSignature().getName() + " start...");
}
}
2. 后置通知(After Advice):在目标方法执行后执行的通知类型。该通知类型可以在目标方法执行结束后进行一些操作,例如日志记录、事务提交等。示例代码如下:
@Aspect
@Component
public class LogAspect {
@After("execution(* com.example.demo.service.*.*(..))")
public void after(JoinPoint joinPoint) {
System.out.println("method " + joinPoint.getSignature().getName() + " end...");
}
}
3. 返回通知(After Returning Advice):在目标方法执行后返回结果时执行的通知类型。该通知类型可以获取目标方法返回的结果并进行一些操作,例如对结果进行处理、日志记录等。示例代码如下:
@Aspect
@Component
public class LogAspect {
@After("execution(* com.example.demo.service.*.*(..))")
public void after(JoinPoint joinPoint) {
System.out.println("method " + joinPoint.getSignature().getName() + " end...");
}
}
4. 异常通知(After Throwing Advice):在目标方法执行发生异常时执行的通知类型。该通知类型可以获取目标方法抛出的异常并进行一些操作,例如异常处理、日志记录等。示例代码如下:
@Aspect
@Component
public class LogAspect {
@AfterThrowing(value = "execution(* com.example.demo.service.*.*(..))", throwing = "e")
public void afterThrowing(JoinPoint joinPoint, Exception e) {
System.out.println("method " + joinPoint.getSignature().getName() + " throw exception: " + e.getMessage());
}
}
5. 环绕通知(Around Advice):在目标方法执行前后都执行的通知类型。该通知类型可以控制目标方法的执行,例如在执行前后进行一些操作、修改参数、返回结果等。示例代码如下:
@Aspect
@Component
public class LogAspect {
@Around("execution(* com.example.demo.service.*.*(..))")
public Object around(ProceedingJoinPoint joinPoint) throws Throwable {
System.out.println("method " + joinPoint.getSignature().getName() + " start...");
Object result = joinPoint.proceed();
System.out.println("method " + joinPoint.getSignature().getName() + " end...");
return result;
}
}
通知类型总结
知识点1:@After
名称 | @After |
---|---|
类型 | 方法注解 |
位置 | 通知方法定义上方 |
作用 | 设置当前通知方法与切入点之间的绑定关系,当前通知方法在原始切入点方法后运行 |
知识点2:@AfterReturning
名称 | @AfterReturning |
---|---|
类型 | 方法注解 |
位置 | 通知方法定义上方 |
作用 | 设置当前通知方法与切入点之间绑定关系,当前通知方法在原始切入点方法正常执行完毕后执行 |
知识点3:@AfterThrowing
名称 | @AfterThrowing |
---|---|
类型 | 方法注解 |
位置 | 通知方法定义上方 |
作用 | 设置当前通知方法与切入点之间绑定关系,当前通知方法在原始切入点方法运行抛出异常后执行 |
知识点4:@Around
名称 | @Around |
---|---|
类型 | 方法注解 |
位置 | 通知方法定义上方 |
作用 | 设置当前通知方法与切入点之间的绑定关系,当前通知方法在原始切入点方法前后运行 |
环绕通知注意事项
-
环绕通知必须依赖形参ProceedingJoinPoint才能实现对原始方法的调用,进而实现原始方法调用前后同时添加通知
-
通知中如果未使用ProceedingJoinPoint对原始方法进行调用将跳过原始方法的执行
-
对原始方法的调用可以不接收返回值,通知方法设置成void即可,如果接收返回值,最好设定为Object类型
-
原始方法的返回值如果是void类型,通知方法的返回值类型可以设置成void,也可以设置成Object
-
由于无法预知原始方法运行后是否会抛出异常,因此环绕通知方法必须要处理Throwable异常