2010-05-13 55 views
4

在我的工作中,我们在一些Java项目中使用了AspectJ。为了使它与ant构建一起工作,我们已经将aspectjtools.jar放在ant/lib /中。如何覆盖存储在ant lib目录中的ant任务

我现在正在研究一个特定的Java项目,并且需要使用较新版本的aspectJ。我不想让每个使用该项目的人都更新其aspectjtools.jar的本地副本。相反,我尝试将新的aspectjtools.jar添加到项目的lib目录,并将以下行添加到build.xml中。

<taskdef 
    resource="org/aspectj/tools/ant/taskdefs/aspectjTaskdefs.properties" 
    classpath="./lib/aspectjtools.jar" /> 

然而,正如我希望的那样从蚂蚁/ lib目录/优先于我在类路径的taskdef指定JAR的ANT类加载器加载罐子这不起作用。

有什么办法可以强制ant选择签入我项目的jar吗?

+0

我一直在使用jarjar AspectJ的重新包装成不同的包装尝试,但这个似乎已经打破AspectJ和感觉就像一个巨人黑客,所以我不再追求这种做法。 – mchr 2010-05-13 15:28:07

+0

到目前为止,我的结论是,没有办法强制蚂蚁选择签入我的项目的jar。这感觉就像一个奇怪的设计选择,因为我预料特定项目的build.xml文件是选择要使用的任务版本的最佳位置。 – mchr 2010-05-14 08:11:36

+0

https://issues.apache.org/bugzilla/show_bug.cgi?id=6606 - 似乎是一个长期存在的错误。我正在阅读评论主题。 – mchr 2010-06-14 23:11:35

回答

3

我的问题的最终答案是否定的。 ANT目前没有办法使用ANT lib目录中优先于任务jar的项目中的任务jar。

3

难道你不能只更新iajc编译目标在类路径上使用新的jar?

不可能强制类加载器将给定的jar文件优先于另一个jar文件。如果你必须涉及同一类的几个版本,那么你应该考虑OSGI。

最简单的解决方案是仅使用来自项目或Maven/Ivy存储库的库,并忽略全局ant文件夹中的库。

一个例子:

<taskdef 
    resource="org/aspectj/tools/ant/taskdefs/aspectjTaskdefs.properties"> 
     <classpath> 
     <pathelement location="${basedir.dir}/lib/aspectjtools.jar"/> 
     </classpath> 
</taskdef> 

<target name="compile" > 
    <iajc outjar="demo.jar"> 
     <sourceroots> 
      <pathelement location=”src” /> 
     </sourceroots> 
     <aspectpath> 
      <pathelement 
       location="aspects_to_be_weaved_with_classes_in_sourceroots.jar" /> 
     </aspectpath> 
     <classpath> 
      <pathelement location="${basedir}/lib/aspectjrt.jar"/> 
     </classpath> 
    </iajc> 
    </target> 

更新: 您也可以使用其他的蚂蚁。如果您使用的是Eclipse,请直接从Ant视图中尝试捆绑的一个。

你也有另一种选择,但它有点困难。那就是使用AspectJ加载时织入来代替。如果你选择这个选项,你可以用一个普通的编译任务进行编译,但是你必须在启动时使用JVM代理进行编织。你可以阅读更多关于它here

我希望这有助于!

+0

感谢您的回答。我会测试明天是否有效。 – mchr 2010-05-13 21:13:55

+1

这并不能解决我的问题。 taskdef元素允许你指定一个类路径,但是我的测试显示这个类路径被插入到现有类路径的末尾。这意味着ANT将始终在ant/lib /目录中使用aspectjtools.jar,优先于taskdef类路径中指定的任何版本。 – mchr 2010-05-14 08:09:48

+1

感谢您的更新 - 我可以看到使用另一个蚂蚁副本将解决我的问题,但只有通过回避问题。 加载时间编织是另一个有效的解决方案,但感觉特别复杂。 ANT提供一个项目机制来强制使用哪个版本的任务真的是不合理吗? – mchr 2010-05-14 12:19:25

1

这是可能的。 你需要利用这一额外任务,以创建一个新的类加载器

http://enitsys.sourceforge.net/ant-classloadertask/

<!--Append the dependent jars to the classpath so we don't have to install them in the ant directory--> 
    <taskdef resource="net/jtools/classloadertask/antlib.xml" 
      classpath="${basedir.dir}/lib/ant-classloadertask.jar"/> 

    <classloader loader="ant.aspectj.loader" parentloader="project"> 
     <classpath> 
      <pathelement location="${basedir.dir}/lib/aspectjtools.jar"/> 
      <pathelement location="${basedir.dir}/lib/ant-classloadertask.jar"/> 
     </classpath> 
     <antparameters parentfirst="false"/> 
     <handler loader="org.apache.tools.ant.AntClassLoader" adapter="org.apache.tools.ant.taskdefs.classloader.adapter.AntClassLoaderAdapter"/> 
    </classloader> 

    <taskdef resource="org/aspectj/tools/ant/taskdefs/aspectjTaskdefs.properties" 
      classpath="${basedir.dir}/lib/aspectjtools.jar"" 
      loaderref="ant.aspectj.loader"/>