Spring-AOP
AOP(Aspect-Oriented Programming,面向切面编程)可以添加额外行为到现有指定条件的一批Bean上,但是我们并不需要修改Bean的代码,这样可对额外行为和Bean本身的行为实现关注隔离。
◎切面:Aspect,编写额外行为的地方。
◎连接点:Join Point,被拦截的方法。
◎切点:PointCut,通过条件匹配一批连接点。
◎通知(5个):Advice,对于每个连接点需要做的行为。
◎目标对象:符合指定条件的Bean
◎前置通知:@Before,在切点方法前调用
◎后置通知:@AfterReturning,在切点方法后调用,可以接受返回值
◎异常通知:@AfterThrowing,当目标方法抛出异常后执行。可以访问到抛出的异常对象。
◎最终通知:@After,无论方法是否正常结束,都会执行
◎环绕通知:@Around最为强大的通知类型,可以完全控制目标方法的执行过程。它既可以执行前置处理,也可以在方法执行后执行后置处理,并决定是否继续执行目标方法以及如何返回结果。
使用AOP实现一个简单的例子,来简单入水
/**
* 自定义日志注解
* @Author : MengYansong
* @create 2024/1/30 10:32
*/
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Logging {
String value() default "";
}
/**
* 切面类
* @Author : MengYansong
* @create 2024/1/30 10:36
*/
@Aspect
@Component
public class LoggingAspect {
/**
* 连接点-找到注解位置
*/
@Pointcut("@annotation(org.dromara.test.aop.Logging)")
public void annotationPointCut(){}
@Before("annotationPointCut()")
public void beforeMethod(JoinPoint joinPoint){
// 获取被拦截方法的参数
String name = (String) joinPoint.getArgs()[0];
// 获取被拦截方法的注解信息
MethodSignature methodSelector = (MethodSignature) joinPoint.getSignature();
// 获取注解上的value值
String value = methodSelector.getMethod().getAnnotation(Logging.class).value();
System.out.println("对" + name + "进行" + value);
}
@AfterReturning(pointcut = "annotationPointCut()",returning = "ret")
public void afterMethod(JoinPoint joinPoint, String ret){
// 获取参数名称
String arg = (String) joinPoint.getArgs()[0];
// 获取注解信息
MethodSignature signature = (MethodSignature) joinPoint.getSignature();
// 获取注解上中的value
String name = signature.getMethod().getAnnotation(Logging.class).value();
System.out.println("对" + arg + "进行" + name + ",返回的名字是:" + ret);
}
}
/**
* 模拟业务实现
* @Author : MengYansong
* @create 2024/1/30 10:34
*/
@Service
public class PersonService {
@Logging("记录-人员新增操作")
public void add(String name){
System.out.println("人员新增");
}
@Logging("记录-人员修改操作")
public String edit(String name){
System.out.println("人员修改");
return name.toLowerCase();
}
}
/**
* 注入容器,模拟调用;直接启动SpringBoot就能显示结果
* @Author : MengYansong
* @create 2024/1/30 10:43
*/
@Configuration
public class JavaConfigA {
@Bean
CommandLineRunner aopCle(PersonService personService){
return args -> {
personService.add("小明");
personService.edit("小红");
};
}
}
--- 打印结果 ---
对小明进行记录-人员新增操作
人员新增
对小红进行记录-人员修改操作
人员修改
对小红进行记录-人员修改操作,返回的名字是:小红
Spring AOP的核心就是通过定义切面(Aspect)、切点(Pointcut)和通知(Advice),在目标方法执行的合适时机插入自定义逻辑,从而实现对交叉关注点的统一管理和处理。