为什么AspectJ编译时不编织Spring的@Configurable工作?

更新5:我已经下载了基于最新Eclipse的最新Spring ToolsSuite IDE。 当我将项目导入为Maven项目时,Eclipse / STS似乎使用Maven目标来构建我的项目。 这意味着AspectJ最终在Eclipse中正常工作。

更新4:我最终只是使用Maven + AspectJ插件进行编译时编织,有效地绕过了Eclipse的机制。

更新3:似乎AspectJ的Eclipse插件破坏了Eclipse正确发布到Tomcat的能力。 只有删除项目中的AspectJfunction,才能让它再次正确发布。 很烦人。

更新2:我现在在Eclipse中工作了。 这样说让我感到非常不舒服,但我不知道如何使用Eclipse或Maven构建它。 它似乎是一个编译问题而不是运行时问题。

更新1:看来我已经通过Maven构建工作了,但我不知道如何。 Eclipse仍然无法正常工作。 我在pom.xml中唯一改变的是添加这些(无关紧要的?)配置参数:

1.6 1.6 true true true 

我实际上担心我会重复这个问题 ,其中一切都不一致。 随着我了解更多信息,我会更新此问题。

关于Eclipse,我通过采用我想编织的二进制方面取得了一些进展 – 在本例中是spring-aspects.jar – 并将其复制出我的类路径。 然后我将这个外部jar添加到我的Aspect Path中 。 执行此操作后,Eclipse在我的代码中正确显示了AspectJ标记。 令人讨厌的是,我不能将spring-aspects.jar留在我的Java Build Path中 ,这是由Maven通过Maven插件为我维护的。 但是,出于某种原因,除非将AspectJ插件显式添加到Aspect Path,否则AspectJ插件不会看到二进制方面。


原始post: @Configurable是一个Spring注释,它允许将依赖项注入到Spring外部实例化的对象中(例如,通过Hibernate或某些Factory类)。

我以前使用这个注释与加载时编织,它主要工作。 偶尔我会启动,没有任何东西会被注入。 这个问题催生了这个StackOverflow问题 。 答案并不多,但大多数人建议我尝试编译时编织,因为可靠性更高。

我为Eclipse和Maven安装了AspectJ插件。 这两者都产生了看似正确编译的类。 我在AspectJ编译之前在文本编辑器中打开了其中一个类,但没有找到对AspectJ的引用。 我在AspectJ编译后打开它,Eclipse和Maven生成的版本都引用了org.aspectj.weaver.MethodDeclarationLineNumber 。 这就是我认为它被正确编译的原因。 问题是,一旦部署,就不会注入依赖项。

My Spring applicationContext.xml确实包含以下内容:

    

以上所有标记为@Configurable的类都需要完成DI吗? 在从加载时编织到编译时编织的转换过程中,我从applicationContext.xml中删除了META-INF / aop.xml ,从我的context.xml中删除了Spring的Tomcat编织器。

我该如何进一步调查此问题? 可能的原因是什么?

它使用编译时编织在maven上工作,尝试添加以下插件:

  org.apache.maven.plugins maven-compiler-plugin  1.6 true 1.6 1.6    org.codehaus.mojo aspectj-maven-plugin   compile  1.6 1.6 false true   org.springframework spring-aspects     compile    test-compile  1.6 1.6 false   org.springframework spring-aspects     test-compile      org.aspectj aspectjweaver 1.6.4    

它作为两个单独的执行步骤完成,允许您添加不同的方面库以进行unit testing和编译。

您还需要为spring-aspects库添加以下依赖项:

   org.springframework spring-aspects compile  

我在我的应用程序中成功配置了加载时编织,如果这是您的替代方案。

我的环境:

  • JDK-1.6
  • 弹簧2.5.6
  • JPA与eclipselink-1.1.0

配置细节:

Spring XML配置:

             

spring注释

 @Configurable("baseEntity") public abstract class BaseEntity @Configurable("historyHandler") public class HistoryJpaHandler extends SessionEventAdapter implements HistoryHandler 

Java VM参数

 /bin/java -javaagent:/full/path/to/spring-agent-2.5.6.jar 

historyHandler和baseEntitty的实例由ecliselink创建。 historyHandler in baseEntitty and historyDao in historyHandler是由load-timeweaving设置的。

您可以在Eclipse运行配置或Tomcats catalina.sh/bat中设置VM参数。

如果没有为此批注正确配置弹簧,则创建@configurable类的字段Autowired会抛出NullPointerException。 请按照以下步骤使@configurable注释正常工作

这种方法称为AspectJ构建时编织,用于将弹簧bean注入非弹簧类

第一步是在eclipse中安装这些插件:

从这两个更新站点安装eclipse建议的任何内容:

 http://download.eclipse.org/tools/ajdt/43/update http://dist.springsource.org/release/AJDT/configurator/ 

安装完成后,右键单击项目并执行:

 Configure > Convert to Aspectj Maven > Update 

接下来,您需要将这些添加到您的pom.xml:

在依赖项下添加:

  org.springframework spring-aspects 4.0.2.RELEASE  

在插件下添加:

   org.codehaus.mojo aspectj-maven-plugin 1.5  true 1.7 1.7 ignore 1.7 UTF-8 false   org.springframework spring-aspects       compile test-compile      org.aspectj aspectjrt 1.7.0   org.aspectj aspectjtools 1.7.0    

重要提示:请勿在标记下使用任何 标记。 你的pom.xml需要是这样的:

  ....   ....  ....     ....  ....    

最后将到spring应用程序上下文配置文件中。

现在,您可以将POJO类注释为@Configurable并使用@Autowired注释在其中注入spring bean。 这样,无论何时创建该POJO的新实例,它都将自动配置(例如注入依赖项)。

就Eclipse类路径问题而言,您可能会发现这很有用。

m2eclipse插件具有可选的AJDT集成 。 该集成读取aspectj-maven-plugin配置的aspectLibraries部分,并将jar提供给Eclipse的Aspect Path。