Spring AOP

简介: Spring AOP

什么是 AOP

面向切面编程

利用 AOP 可以对业务逻辑的各个部分进行隔离,从而使得业务逻辑各部分之间的 耦合度 降低,提高程序的可重用性,同时提高了开发的效率。

AOP 底层原理

AOP 底层使用了 动态代理


  1. 有接口情况 使用的是 JDK 动态代理

  1. 没有接口情况 使用的是 CGLIB 动态代理

编写 JDK 动态代理代码

//(1)创建接口,定义方法
public interface UserDao {
     public int add(int a,int b);
     public String update(String id);
}
//(2)创建接口实现类,实现方法
public class UserDaoImpl implements UserDao {
     @Override
     public int add(int a, int b) {
         return a+b;
     }
     @Override
     public String update(String id) {
         return id;
     }
}



AOP 术语

  1. 连接点

类里面的哪些方法可以被增强,这些方法就叫做 连接点。


  1. 切入点

实际被真正增强的方法,称为 切入点。


  1. 通知(增强)
  • 实际增强的逻辑部分称为 通知(增强)。
  • 通知有多种类型:
  • 前置通知
  • 后置通知 (有异常这个不会执行的)
  • 环绕通知
  • 异常通知
  • 最终通知


  1. 切面(切入点+额外功能)

指的是 动作,把通知应用到切入点的过程。

Spring 基于 AspectJ 框架实现 AOP 操作。

基于注解使用 AOP


切入点表达式

  1. 切入点表达式作用: 知道对哪个类里面的哪个方法进行增强
  2. 语法结构:execution([权限修饰符] [返回类型] [类全路径] [方法名称][参数列表])


举例1: 对 com.snow.dao.BookDao 类里面的 add 进行增强

execution(* com.snow.dao.BookDao.add(…))

举例 2:对 com.snow.dao.BookDao 类里面的所有的方法进行增强

execution(* com.snow.dao.BookDao.* (…))

举例 3:对 com.snow.dao 包里面所有类,类里面所有方法进行增强

execution(* com.snow.dao.. (…))


也可以这样:

@AfterReturning(pointcut = "@annotation(controllerLog)", returning = "jsonResult")
public void doAfterReturning(JoinPoint joinPoint, Log controllerLog, Object jsonResult) {
    handleLog(joinPoint, controllerLog, null, jsonResult);
}

@Aspect

标注在类上面,表示切面类

@Around

ProceedingJoinPoint



实操

创建 被增强的类 和 被增强的方法

@Component
public class User {
    //  被增强的方法
    public void add() {
        System.out.println("add.......");
    }
}


创建 增强类 和 增强方法

//增强的类
@Component
@Aspect //  生成代理对象
public class UserProxy {
    //前置通知
    //@Before 注解表示作为前置通知
    @Before(value = "execution(* com.snow.spring5.aopanno.User.add(..))")
    public void before() {
        System.out.println("before.........");
    }
    //后置通知(返回通知):有异常不会执行这个的
    @AfterReturning(value = "execution(* com.snow.spring5.aopanno.User.add(..))")
        public void afterReturning() {
        System.out.println("afterReturning.........");
    }
    //最终通知:不管有没有异常 都会执行
    @After(value = "execution(* com.snow.spring5.aopanno.User.add(..))")
    public void after() {
        System.out.println("after.........");
    }
    //异常通知
    @AfterThrowing(value = "execution(* com.snow.spring5.aopanno.User.add(..))")
        public void afterThrowing() {
        System.out.println("afterThrowing.........");
    }
    //环绕通知
    @Around(value = "execution(* com.snow.spring5.aopanno.User.add(..))")
    public void around(ProceedingJoinPoint proceedingJoinPoint) throws 
        Throwable {
        System.out.println("环绕之前.........");
        //被增强的方法执行
        proceedingJoinPoint.proceed();
        System.out.println("环绕之后.........");
    }
}



优化——相同的切入点做一个提取

//相同切入点抽取
@Pointcut(value = "execution(* com.snow.spring5.aopanno.User.add(..))")
public void pointdemo() {
}

//前置通知
@Before(value = "pointdemo()")
public void before() {
    System.out.println("before.........");
}

//最终通知
@After(value = "pointdemo()")
public void before() {
    System.out.println("after.........");
}




有多个增强类多同一个方法进行增强,设置增强类优先级

(1)在增强类上面添加注解 @Order(数字类型值),数字类型值越小优先级越高

@Component 
@Aspect 
@Order(1) 
public class PersonProxy  


TODO 获取被代理对象的参数


相关文章
|
24天前
|
监控 Java API
掌握 Spring Boot AOP:使用教程
Spring Boot 中的面向切面编程(AOP)为软件开发提供了一种创新方法,允许开发者将横切关注点与业务逻辑相分离。这不仅提高了代码的复用性和可维护性,而且还降低了程序内部组件之间的耦合度。下面,我们深入探讨如何在 Spring Boot 应用程序中实践 AOP,以及它为项目带来的种种益处。
|
1月前
|
安全 Java Spring
Spring之Aop的底层原理
Spring之Aop的底层原理
|
1月前
|
Java 关系型数据库 MySQL
利用Spring AOP技术实现一个读写分离
利用Spring AOP技术实现一个读写分离
34 0
|
3天前
|
Java 开发者 Spring
Spring AOP的切点是通过使用AspectJ的切点表达式语言来定义的。
【5月更文挑战第1天】Spring AOP的切点是通过使用AspectJ的切点表达式语言来定义的。
13 5
|
3天前
|
XML Java 数据格式
Spring AOP
【5月更文挑战第1天】Spring AOP
19 5
|
3天前
|
Java 编译器 开发者
Spring的AOP理解
Spring的AOP理解
|
3天前
|
XML Java 数据格式
如何在Spring AOP中定义和应用通知?
【4月更文挑战第30天】如何在Spring AOP中定义和应用通知?
10 0
|
3天前
|
安全 Java 开发者
在Spring框架中,IoC和AOP是如何实现的?
【4月更文挑战第30天】在Spring框架中,IoC和AOP是如何实现的?
15 0
|
4天前
|
Java 测试技术 开发者
【亮剑】如何通过自定义注解来实现 Spring AOP,以便更加灵活地控制方法的拦截和增强?
【4月更文挑战第30天】通过自定义注解实现Spring AOP,可以更灵活地控制方法拦截和增强。首先定义自定义注解,如`@MyCustomAnnotation`,然后创建切面类`MyCustomAspect`,使用`@Pointcut`和`@Before/@After`定义切点及通知。配置AOP代理,添加`@EnableAspectJAutoProxy`到配置类。最后,在需拦截的方法上应用自定义注解。遵循保持注解职责单一、选择合适保留策略等最佳实践,提高代码可重用性和可维护性。记得测试AOP逻辑。
|
4天前
|
缓存 监控 Java
【Spring系列笔记】AOP
面向切面编程就是面向特定方法编程。通过将横切关注点(cross-cutting concerns)从主要业务逻辑中分离出来,提供一种更好的代码模块化和可维护性。 横切关注点指的是在应用程序中横跨多个模块或层的功能,例如日志记录、事务管理、安全性、缓存、异常处理等。
16 0