使用AspectJ的Spring AOP:加载时间编织

Sha*_*ane 8 aop spring aspectj load-time-weaving

如果我使用的是基于AspectJ的Spring AOP,那么我是否可以配置我的方面以使用加载时间编织?或者,当使用基于AspectJ的方法时,Spring AOP是否也支持运行时/编译时编织?

kri*_*aex 16

我认为我们应该注意不要混淆Spring AOP和AspectJ.

  • 就像singh101所说,Spring AOP是基于代理的,更准确地基于Java SE动态代理(用于接口)或CGLIB代理(用于类).它使用AspectJ语法的一个子集,是一种"AOP lite"方法,基本上仅限于方法执行切入点,缺少许多AspectJ切入点类型,如方法调用,类成员set/get,构造函数调用/执行等.从技术上讲,它与AspectJ非常不同,并且由于代理方法(调用间接)而总是会产生运行时开销.此外,它仅限于从bean类外部调用Spring Bean方法,即如果bean调用其自己的方法之一(因为它不通过相应的代理),它不起作用,并且它也不适用于非类-Spring Bean类(普通POJO).
  • 另一方面,AspectJ是一个完整的AOP框架,它不依赖于代理或Spring框架.但是,它可以很容易地包含在Spring应用程序中.它的工作原理是直接通过自己的编译器(它是Java编译器的超集)生成字节代码,或者使用现有的字节代码.AspectJ可以在编译期间使用(无运行时开销)或在类加载期间(加载时间编织,LTW).虽然LTW在应用程序启动期间有一点开销(但同样适用于Spring AOP),但两种AspectJ编织方法都没有由于调用间接而导致的运行时开销,因为没有涉及代理.
  • 关于AOP的Spring手册章很好地解释当Spring AOP不够强大或者太慢时,如何将完整的AspectJ集成到Spring中.

  • 我不是Spring用户.但我认为,如果做得好,你可以将两者结合起来.我没有读过您链接的书,但如果作者说如何做,我认为没有理由不这样做.我认为纯粹的AspectJ方面和它们所针对的bean没有被拾取两次是非常重要的(例如,一次通过Spring组件扫描,再一次通过LTW).干净地配置,这应该不是问题.祝好运! (2认同)

Ang*_*gad 8

Spring AOP是基于代理的.除非另有配置,否则Spring AOP会执行运行时编织.

编织:将方面与其他应用程序类型或对象链接以创建建议对象.这可以在编译时(例如,使用AspectJ编译器),加载时间或在运行时完成.与其他纯Java AOP框架一样,Spring AOP在运行时执行编织.

资料来源:http://docs.spring.io/spring/docs/4.0.1.RELEASE/spring-framework-reference/htmlsingle/#aop-introduction-defn


但是,您可以设置Spring来进行加载时编织.查看有关如何执行此操作的Spring文档:http: //docs.spring.io/spring/docs/3.2.0.RELEASE/spring-framework-reference/htmlsingle/#aop-aj-ltw

除此之外,您将@EnableLoadTimeWeaving在Java Config类中使用.设置非常简单,您的@Aspect课程不会改变.

开发人员只需修改构成应用程序上下文的一个或多个文件即可启用加载时编织,而不是依赖通常负责部署配置的管理员,例如启动脚本