Spring AOP是什么?

本文内容如有错误、不足之处,欢迎技术爱好者们一同探讨,在本文下面讨论区留言,感谢。

前言

大多数企业应用程序都具有一些常见的横切关注点,这些关注点适用于不同类型的对象和模块。一些常见的横切关注点是日志记录,事务管理,数据验证等。

在面向对象编程中,应用程序的模块化是通过类实现的,而在面向切面编程中,应用程序的模块化是通过 Aspects 实现的,它们被配置可以横向切面不同的类。

Spring AOP从无法通过常规的面向对象的编程模型实现的类中获取横切任务的直接依赖关系。例如,有一个单独的日志记录类,但是功能类也必须调用这些方法来实现整个应用程序的日志记录。

概述

AOP是一种编程范例,旨在通过允许跨领域关注点的分离来提高模块化。它是通过在现有代码中添加其他行为而无需修改代码本身来实现的。相反,可以分别声明此新代码和这些新行为。Spring的AOP框架可帮助开发人员实现这些跨领域的关注。

AOP的核心概念
  1. 切面Aspect): 切面由切点和增强(advice)组成。例如事务管理。Aspects 可以是通过 Spring XML 配置配置的普通类,也可以使用 Spring AspectJ 集成通过 @Aspect 注释将类定义为 Aspect
  2. 连接点Join Point): 能够被拦截的地方,因为 Spring AOP 是基于动态代理的,所以是方法拦截的。例如方法执行,异常处理,更改对象变量值等。在 Spring AOP 中,连接点始终是方法的执行。
  3. 增强Advice): Advices 是针对特定连接点采取的操作。就编程而言,它们是在应用程序中达到具有匹配切入点的特定连接点时执行的方法。可以将 Advices 视为 Struts2 拦截器或 Servlet 过滤器。
  4. 切点Pointcut): 切点是与连接点匹配的表达式,用于确定是否需要增强。Pointcut 使用与连接点匹配的不同类型的表达式,Spring 框架使用 AspectJ Pointcut 表达式语言。
  5. 目标对象Target Object): 它们是应用增强的对象。Spring AOP 是使用动态代理实现的,因此此对象始终是代理对象。这意味着将在运行时创建一个子类,在该子类中将拦截目标方法,并根据其配置包含增强。
  6. AOP代理AOP proxy):Spring AOP 实现使用JDK动态代理来创建包含目标类和增强调用的Proxy类,这些类称之为AOP代理类。我们还可以通过将CGLIB代理添加为 Spring AOP 项目中的依赖项来使用它。
  7. 织入Weaving): 将增强添加到目标类的具体连接点上的过程。这是通过切面与其他对象链接用来创建增强的代理对象的过程。这可以在编译时,加载时或运行时完成。Spring AOP 在运行时执行编织。
通知 Advice
  • AOP 中的一个重要术语是通知。它是切面在特定的连接点处采取的操作。
  • 连接点是程序的执行点,例如方法的执行或异常的处理。在 Spring AOP 中,连接点始终代表方法的执行。
  • 切入点是匹配联接点的谓词或表达式。
  • 通知与切入点表达式关联,并在与该切入点匹配的任何连接点处运行。
  • Spring 默认使用 AspectJ 切入点表达语言。

具体如下图所示:图片地址:https://howtodoinjava.com/spring-aop-tutorial/

在这里插入图片描述

AOP advices的几种类型
  • 前置增强Before advice): Advice 执行在连接点之前,但是它不能阻止执行流程前进到连接点(除非它引发异常)。
  • 后置增强After returning advice): 连接点正常完成后要执行的通知。
  • 抛出增强After throwing advice): 如果方法因抛出异常而退出,则执行增强。
  • Final增强After advice): 无论连接点退出的方式如何(正常或异常返回),均执行增强。
  • 环绕增强Around advice): 环绕连接点的增强,例如方法调用。这是最有力的增强。环绕增强可以在方法调用之前和之后执行自定义行为。它还负责选择是返回连接点还是通过返回自己的返回值或引发异常来捷径增强的方法执行。
例子
Maven依赖

编写代码前,需要将 Spring AOP 依赖项导入到项目中:

pom.xml

<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-context</artifactId>
    <version>4.1.4.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-context-support</artifactId>
    <version>4.1.4.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-aop</artifactId>
    <version>4.1.4.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.aspectj</groupId>
    <artifactId>aspectjrt</artifactId>
    <version>1.6.11</version>
</dependency>
<dependency>
    <groupId>org.aspectj</groupId>
    <artifactId>aspectjweaver</artifactId>
    <version>1.6.11</version>
</dependency>
切面和切入点表达式

编写带有 @Aspect 注释的切面类,并编写切入点表达式以匹配连接点方法。

@Aspect
public class EmployeeCRUDAspect {
     
    @Before("execution(* EmployeeManager.getEmployeeById(..))")			//连接点 表达式
    public void logBeforeV1(JoinPoint joinPoint)
    {
        System.out.println("EmployeeCRUDAspect.logBeforeV1() : " + joinPoint.getSignature().getName());
    }
}
方法(joint points)

编写要在其上执行建议并与切入点表达式匹配的方法。

EmployeeManager.java

@Component
public class EmployeeManager
{
    public EmployeeDTO getEmployeeById(Integer employeeId) {
        System.out.println("Method getEmployeeById() called");
        return new EmployeeDTO();
    }
}

在上面的示例中,*logBeforeV1()*将在 *getEmployeeById()*方法之前执行,因为它与连接点表达式匹配。

运行应用

运行应用同时查看控制台输出:

TestAOP.java

public class TestAOP
{
    @SuppressWarnings("resource")
    public static void main(String[] args) {
  
        ApplicationContext context = new ClassPathXmlApplicationContext
                            ("com/howtodoinjava/demo/aop/applicationContext.xml");
 
        EmployeeManager manager = context.getBean(EmployeeManager.class);
  
        manager.getEmployeeById(1);
    }
}

控制台:

EmployeeCRUDAspect.logBeforeV1() : getEmployeeById
Method getEmployeeById() called
Spring aop tutorial for beginners with example.
参考资料

Spring AOP Tutorial Example(Spring AOP教程示例)

Chapter 6. Aspect Oriented Programming with Spring(第6章使用Spring进行面向切面的编程)

Introduction to Spring AOP(Spring AOP简介

Spring AOP Overview(Spring AOP概述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值