选择使用哪种 AOP 声明风格
一旦您决定方面是实现给定需求的最佳方法,您如何决定是在使用 Spring AOP 还是 AspectJ 以及在方面语言(代码)风格、@AspectJ 注解风格还是 Spring XML 风格之间做出选择?这些决定受许多因素的影响,包括应用程序需求、开发工具和团队对 AOP 的熟悉程度。
Spring AOP 还是完整 AspectJ?
使用最简单的可行方案。Spring AOP 比使用完整 AspectJ 更简单,因为它不需要将 AspectJ 编译器/织入器引入您的开发和构建流程。如果您只需要建议对 Spring Bean 的操作执行,则 Spring AOP 是正确的选择。如果您需要建议 Spring 容器未管理的对象(例如域对象,通常),则需要使用 AspectJ。如果您希望建议除简单方法执行之外的其他连接点(例如,字段获取或设置连接点等),也需要使用 AspectJ。
当您使用 AspectJ 时,您可以选择 AspectJ 语言语法(也称为“代码风格”)或 @AspectJ 注解风格。如果方面在您的设计中扮演重要角色,并且您可以使用 Eclipse 的AspectJ 开发工具 (AJDT) 插件,则 AspectJ 语言语法是首选选项。它更简洁明了,因为该语言是专门为编写方面而设计的。如果您不使用 Eclipse 或只有几个在应用程序中不发挥主要作用的方面,您可能需要考虑使用 @AspectJ 风格,坚持在您的 IDE 中使用常规 Java 编译,并在您的构建脚本中添加一个方面织入阶段。
@AspectJ 还是 XML 用于 Spring AOP?
如果您选择使用 Spring AOP,则可以选择 @AspectJ 或 XML 风格。需要考虑各种权衡。
XML 风格可能对现有的 Spring 用户最熟悉,并且它由真正的 POJO 支持。在使用 AOP 作为配置企业服务的工具时,XML 可能是一个不错的选择(一个好的测试是您是否认为切点表达式是配置的一部分,您可能希望独立更改它)。使用 XML 风格,从您的配置中可以清楚地看出系统中存在哪些方面。
XML 风格有两个缺点。首先,它没有完全将它解决的需求的实现封装在一个地方。DRY 原则指出,任何知识在系统中都应该有一个单一、明确、权威的表示。当使用 XML 风格时,如何实现需求的知识在支持 Bean 类的声明和配置文件中的 XML 之间拆分。当您使用 @AspectJ 风格时,此信息封装在一个模块中:方面。其次,XML 风格在其表达能力方面比 @AspectJ 风格略有局限:仅支持“单例”方面实例化模型,并且无法组合在 XML 中声明的命名切点。例如,在 @AspectJ 风格中,您可以编写如下内容
-
Java
-
Kotlin
@Pointcut("execution(* get*())")
public void propertyAccess() {}
@Pointcut("execution(com.xyz.Account+ *(..))")
public void operationReturningAnAccount() {}
@Pointcut("propertyAccess() && operationReturningAnAccount()")
public void accountPropertyAccess() {}
@Pointcut("execution(* get*())")
fun propertyAccess() {}
@Pointcut("execution(com.xyz.Account+ *(..))")
fun operationReturningAnAccount() {}
@Pointcut("propertyAccess() && operationReturningAnAccount()")
fun accountPropertyAccess() {}
在 XML 风格中,您可以声明前两个切点
<aop:pointcut id="propertyAccess"
expression="execution(* get*())"/>
<aop:pointcut id="operationReturningAnAccount"
expression="execution(com.xyz.Account+ *(..))"/>
XML 方法的缺点是您无法通过组合这些定义来定义accountPropertyAccess
切点。
@AspectJ 风格支持其他实例化模型和更丰富的切点组合。它具有将方面作为模块化单元的优势。它还具有 @AspectJ 方面可以被 Spring AOP 和 AspectJ 理解(因此也可以被它们使用)的优势。因此,如果您以后决定需要 AspectJ 的功能来实现其他需求,您可以轻松迁移到经典的 AspectJ 设置。一般来说,Spring 团队更喜欢 @AspectJ 风格来处理超出企业服务简单配置的自定义方面。