Spring AOP 快速入门

参考资料

https://www.bilibili.com/video/BV1Fi4y1S7ix?p=31&vd_source=c581024b8cd9585ec6a75c56ac05571a

1. AOP简介

  • AOP 面向切面编程,一种编程范式,指导开发者如何组织程序结构。
  • 作用:非侵入式的进行功能增强。

2. 核心概念

在这里插入图片描述

3. AOP 入门案例

  1. 导入依赖
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-aop</artifactId>
            <version>5.3.20</version>
        </dependency>

        <dependency>
            <groupId>org.aspectj</groupId>
            <artifactId>aspectjweaver</artifactId>
            <version>1.9.6</version>
        </dependency>
  1. 通知类
@Component  //注入容器
@Aspect     //告诉Spring这是个通知类,
public class MyAdvice {
    
    

    @Pointcut("execution(* com.xin.web.service.impl.*.*(..))")
    public void pt() {
    
    
    }

    @Before("pt()")   //绑定通知和切入点
    public void timeMethod() {
    
      //通知方法
        System.out.println(System.currentTimeMillis());
    }
}
  1. 业务逻辑类
@Service("userService")
@Scope("singleton")
public class UserServiceImpl implements UserService {
    
    

    @Autowired
    private UserDao userDao;

    @Override
    public void save(User user) {
    
    
        System.out.println("执行插入操作");
        userDao.save(user);
    }

    @Override
    public void remove() {
    
    
        System.out.println("执行删除操作");
        userDao.remove();
    }

    @Override
    public void update() {
    
    
        System.out.println("执行修改操作");
        userDao.update();
    }

    @Override
    public void findAll() {
    
    
        System.out.println("执行查询操作");
        userDao.findAll();
    }
}
  1. Spring配置类开启注解
@Configuration //配置类
@ComponentScan("com.xin") //配置包扫描路径
@PropertySource("classpath:db.properties") //加载Properties文件
@Import({
    
    JDBCConfig.class, MyBatisConfig.class}) //
@EnableAspectJAutoProxy  //开启AOP 代理
public class SpringConfig {
    
    

}

4. AOP 工作流程

在这里插入图片描述

5. AOP 切入点表达式

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

6. AOP 通知类型

在这里插入图片描述

@Component
@Aspect
public class MyAdvice {
    
    

    @Pointcut("execution(* com.xin.web.service.*Service.*(..))")
    public void pt() {
    
    
    }

    @Before("pt()")
    public void timeMethod() {
    
    
        System.out.println("前置通知");
    }

    @After("pt()")
    public void after() {
    
    
        System.out.println("后置通知");
    }

    @Around("pt()")
    public void around(ProceedingJoinPoint pjp) throws Throwable {
    
    
        System.out.println("环绕前通知");
        pjp.proceed();
        System.out.println("环绕后通知");
    }

    @AfterReturning("pt()")
    public void afterReturning() {
    
    
        System.out.println("方法返回后通知");
    }

    @AfterThrowing("pt()")
    public void afterThrowing() {
    
    
        System.out.println("异常后通知");
    }
}

在这里插入图片描述
在这里插入图片描述

7. AOP 通知获取 参数、返回值、异常

在这里插入图片描述

参数

@Component
@Aspect
public class MyAdvice {
    
    

    @Pointcut("execution(* com.xin.web.service.*Service.*(..))")
    public void pt() {
    
    
    }

    @Before("pt()")
    public void before(JoinPoint joinPoint) {
    
    
        //获取原始类的形参
        Object[] args = joinPoint.getArgs();
        System.out.println(Arrays.toString(args));
    }

    @Around("pt()")
    public Object around(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
    
    
        //获取原始类的形参
        Object[] args = proceedingJoinPoint.getArgs();
        System.out.println(Arrays.toString(args));
        
        Object result = proceedingJoinPoint.proceed(args);
        return result;
    }
}

返回值

只有环绕通知和返回后通知 能拿到返回值。

@Component
@Aspect
public class MyAdvice {
    
    

    @Pointcut("execution(* com.xin.web.service.*Service.*(..))")
    public void pt() {
    
    
    }

    @Around("pt()")
    public Object around(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
    
    
        //获取返回值
        Object result = proceedingJoinPoint.proceed();
        return result;
    }

    @AfterReturning(value = "pt()",returning = "result")//指定接受返回值的形参
    public void afterReturning(Object result){
    
    
        //原始类方法的返回值
        System.out.println(result);
    }
    
    @AfterReturning(value = "pt()", returning = "result")//指定接受返回值的形参
    public void afterReturning(JoinPoint joinPoint, Object result) {
    
     //如果需要用JoinPoint,那么两个形参的顺序必须是 JoinPoint在前
        //原始类方法的返回值
        System.out.println(result);
    }
}

异常

只有环绕通知和异常后通知有。

@Component
@Aspect
public class MyAdvice {
    
    

    @Pointcut("execution(* com.xin.web.service.*Service.*(..))")
    public void pt() {
    
    
    }

    @Around("pt()")
    public Object around(ProceedingJoinPoint proceedingJoinPoint) {
    
    
        //获取返回值
        Object result = null;
        try {
    
    
            result = proceedingJoinPoint.proceed();
        } catch (Throwable throwable) {
    
    
            //捕获原始类方法的异常
            throwable.printStackTrace();
        }
        return result;
    }

    @AfterThrowing(value = "pt()",throwing = "e")//设置形参接受返回值
    public void afterThrowing(Throwable e){
    
    
        //原始类方法的异常
        System.out.println(e);
    }
}

猜你喜欢

转载自blog.csdn.net/ZHHX666/article/details/125819821