如何在没有 -lib 或全局安装的情况下将可选任务加载到 ant 中? [英] How to load an optional task into ant without -lib or global installation?

查看:24
本文介绍了如何在没有 -lib 或全局安装的情况下将可选任务加载到 ant 中?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想在 ant 中使用 FTP 任务,并且我找到了合适的 jar 文件并且一切正常.我已将 jar 文件与构建中使用的其他文件一起放在libs"目录中.唯一的问题是用户必须运行ant -lib commons-net-ftp-2.0.jar"才能进行构建;我真的更希望可以不带参数地运行ant".

I want to use the FTP task in ant, and I have found the appropriate jar files and got everything working fine. I have put the jar files in a "libs" directory alongside the other files used in the build. The only problem is that the user must run "ant -lib commons-net-ftp-2.0.jar" to make a build; I would really prefer that it were possible to just run "ant" with no arguments.

阅读ant 可选任务安装页面,我看到有五种方式一可以在 ant 中加载额外的库,但没有一个是我真正想要的.我不想强迫用户对其系统进行任何修改以运行此任务;应该可以从我们产品源文件夹内的libs"目录中加载它.所以这意味着设置全局 CLASSPATH 也不行(无论如何这都是一个坏主意).

Reading the ant optional tasks intallation page, I see that there are five ways one can load up extra libraries in ant, and none of them are really what I'm looking for. I do not want to force the user to make any modifications to their system to run this task; it should be possible to just load it from the "libs" directory inside of our product's source folder. So that means setting the global CLASSPATH is also out (which is a bad idea anyways).

如文档中所述,最后一个选项是首选方法...从构建脚本本身单独加载 jarfile.我过去曾使用 ant-contrib 任务和 JUnit 完成此操作,并且想在这里执行此操作,但我不知道如何完成此操作.FTP 任务不支持嵌套的类路径元素,而且我不知道通过 taskdef 加载此库所需的 XML 资源.如何从 ant 中加载库?

The last option, as noted in the documentation, is the preferred approach... loading the jarfiles individually from the build script itself. I have done this in the past with the ant-contrib tasks and JUnit, and would like to do that here, but I don't see how I can accomplish this. The FTP task doesn't support a nested classpath element, and I don't know the XML resource I would need to load this library via a taskdef. How can I load the libraries from within ant?

为了回应到目前为止发布在这里的答案和问题,我使用的是 ant 1.7.1.制作一个 ftp taskdef 肯定是行不通的;引发以下错误:

In response to the answers and questions which have been posted here so far, I'm using ant 1.7.1. Making an ftp taskdef definitely does not work; that throws the following error:

构建失败/my/path/build.xml:13: 找不到 taskdef 类 org.apache.tools.ant.taskdefs.optional.net.FTP

BUILD FAILED /my/path/build.xml:13: taskdef class org.apache.tools.ant.taskdefs.optional.net.FTP cannot be found

也许这是因为类名错误.如果我只有一个 jarfile,我究竟如何找到我应该使用的类名?它没有记录在任何地方,我在 jar 中找不到任何类似于该路径的内容.

Perhaps this is because the classname is wrong. How exactly do I find the classname I'm supposed to use if I only have a jarfile? It's not documented anywhere, and I couldn't find anything in the jar itself resembling that path.

推荐答案

您遇到的问题是由于使用的类加载器不同.Commons Net 类必须由加载 FTP 任务的同一个类加载器加载.由于 FTP 任务在启动时由 Ant 加载,因此您需要将 Commons Net 添加到 Ant 的类路径中,以便由同一个类加载器加载它.这就是文档为您提供 4 种不同方法来执行此操作的原因.

The problem you are having is due to the different class-loaders in use. The Commons Net classes must be loaded by the same class-loader that loads the FTP task. Because the FTP task is loaded by Ant on start-up, you need to add the Commons Net to Ant's classpath so that it is loaded by the same class-loader. That's why the documentation gives you 4 different ways to do this.

我同意它们都不理想(CLASSPATH 环境变量是最糟糕的).解决此问题的一种方法是为您的项目提供一个 shell 脚本,该脚本调用 Ant 并传递适当的 -lib 参数.然后你让人们使用它而不是直接调用 Ant.事实上,您可以巧妙地将其命名为ant",以便它运行而不是路径上现有的ant"(这仅适用于当前目录在路径上且位于其他目录之前的情况).

I agree that none of them are ideal (the CLASSPATH environment variable being the worst). One way around this is to supply a shell script with your project that invokes Ant and passes the apporpriate -lib argument. You then get people to use this rather than invoking Ant directly. In fact, you could deviously name it 'ant' so that it gets run instead of the existing 'ant' on the path (this only works if the current directory is on the path, ahead of other directories).

文档中的第五个选项理论上很棒.他们终于在 1.7.0 中修复了类加载问题.不幸的是,正如您提到的,没有人改装 FTP 任务以采用类路径.您可以尝试提交增强请求,但这在短期内无济于事.

The fifth option in the documentation is great in theory. They finally fixed the class-loading problems in 1.7.0. Unfortunately, as you mention, nobody retro-fitted the FTP task to take a classpath. You could try submitting an enhancement request, but this won't help in the short term.

还有另一种选择,它并不比其他选择好.与确保加载 FTP 任务的类加载器加载 Commons Net 类不同,您可以确保加载 Commons Net 类的类加载器加载 FTP 任务.为此,您必须从 Ant 安装的lib"目录中删除 ant-commons-lib.jar 文件.这意味着 FTP 任务不会在启动时加载.这实际上就是为什么可选任务被分解成这么多独立的 JAR 的原因——以便它们可以被单独删除.将此 JAR 文件与 Commons Net JAR 文件放在一起,以便可以同时加载.然后你可以做这样的事情(我试过这个并且有效):

There is one other option, which isn't any better than the others. Instead of making sure that the Commons Net classes are loaded by the class-loader that loads the FTP task, you could make sure that the FTP task is loaded by the class-loader that loads the Commons Net classes. To do this you have to remove the ant-commons-lib.jar file from the 'lib' directory of the Ant installation. This means that the FTP task won't get loaded on start-up. This is actually why the optional tasks are broken up into so many separate JARs - so that they can be individually removed. Put this JAR file alongside the Commons Net JAR file so that it can be loaded at the same time. Then you can do something like this (I tried this and it works):

<taskdef name="ftp"
         classname="org.apache.tools.ant.taskdefs.optional.net.FTP">
  <classpath>
    <pathelement location="${basedir}/lib/ant-commons-net.jar"/>
    <pathelement location="${basedir}/lib/commons-net-2.0.jar"/>
  </classpath>
</taskdef>
<ftp server="yourserver.com"
     userid="anonymous"
     password="blah">
  <fileset dir="somedirectory"/>
</ftp>

但这可能是比仅使用 -lib 开关(有或没有包装脚本)更糟糕的选择.我唯一能想到的另一件事是尝试找到要使用的第三方 FTP 任务而不是默认任务.

But this is probably a worse option than just using the -lib switch (with or without a wrapper script). The only other thing I can think of is to try to find a third-party FTP task to use instead of the default one.

这篇关于如何在没有 -lib 或全局安装的情况下将可选任务加载到 ant 中?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆