如何在ANT中参数化路径?

时间:2010-03-24 04:10:34

标签: ant path

我在名为 build-dependencies.xml

的文件中定义了以下内容
<?xml version="1.0" encoding="UTF-8"?>
<project name="build-dependencies">
  ...
  <path id="common-jars">
    <fileset file="artifacts/project-1/jar/some*.jar" />
    <fileset file="artifacts/project-2/jar/someother*.jar" />
  </path>
  ...
</project>

我将其包含在 build.xml 文件的顶部。现在我需要将artifacts文件夹作为参数,以便在执行不同的目标时可以更改它。 有这个...

<?xml version="1.0" encoding="UTF-8"?>
<project name="build-dependencies">
  ...
  <path id="common-jars">
    <fileset file="${artifacts}/project-1/jar/some*.jar" />
    <fileset file="${artifacts}/project-2/jar/someother*.jar" />
  </path>
  ...
</project>

...并在目标中定义“artifacts”属性(并更改它)不起作用,因为当在 build-dependencies.xml 中定义路径时,似乎发生了属性替换

我该如何解决这个问题?我想的一种方法是使用参数化宏并在实际使用路径之前调用它,但这看起来并不优雅。像这样:

<macrodef name="create-common-jars">
  <attribute name="artifacts"/>
  <sequential>
    <path id="common-jars">
      <fileset file="@{artifacts}/project-1/jar/some*.jar" />
      <fileset file="@{artifacts}/project-2/jar/someother*.jar" />
    </path>
  </sequential>
</macrodef>

编辑:常春藤和命令行参数不是一个选项。

6 个答案:

答案 0 :(得分:3)

您不需要参数化路径。你想要一个PatternSet。您可以在顶层定义模式集,然后在需要时在各个目标中引用它。以你的例子:

<?xml version="1.0" encoding="UTF-8"?>
<project name="build-dependencies">
  ...
  <patternset id="common-jars">
    <include name="project-1/jar/some*.jar" />
    <include name="project-2/jar/someother*.jar" />
  </patternset>
  ...
  <path id="instrumented-jars">
    <fileset dir="instrumented">
      <patternset refid="common-jars" />
    </fileset>
  </path>
  ...
  <path id="standard-jars">
    <fileset dir="not-instrumented">
      <patternset refid="common-jars" />
    </fileset>
  </path>
  ...
</project>

答案 1 :(得分:0)

让我们调用你的文件build.xml。所以你通过运行ant命令来执行它。在第一种情况下,工件名称在下面第三行定义的属性中进行硬编码

<?xml version="1.0" encoding="UTF-8"?>
<project name="build-dependencies">
<property name="artifacts" value="first-value" />
  ...
  <path id="common-jars">
    <fileset file="artifacts/project-1/jar/some*.jar" />
    <fileset file="artifacts/project-2/jar/someother*.jar" />
  </path>
  ...
</project>

现在,当您想要更改它并为该工件属性使用另一个值时,我们就这样运行脚本

ant -Dartifacts=new-value

这将覆盖build.xml

中的硬编码工件值

如果在ant目标方面工作,你可以做类似的事情,在第一行的目标中定义属性,如果你想覆盖默认值,那么在调用该目标时将该属性作为参数传递。

你的评论让我想起了别的什么。让开发人员创建artifacts-dir-name.xml文件。它只有一行:

<?xml version="1.0" encoding="UTF-8"?>
<project name="artifacts-file">
<property name="artifacts" value="new-value" />
</project>

现在在build.xml文件中,在定义artifacts属性的行之前,导入该文件:

<import file="artifacts-dir-name.xml" optional="true" />

现在在Eclipse中,如果此文件存在,则从中读取属性并将工件设置为“new-value”,否则从build.xml读取属性并将其设置为“first-value”。所有开发人员需要做的是确保该目录中存在artifacts-dir-name.xml文件。这也可以在Eclipse中运行。

答案 2 :(得分:0)

我建议使用ivy来管理类路径依赖项。 Ivy有一个称为配置的简洁概念,允许您根据其使用情况对工件集合进行分组。

这是我自己的构建文件之一的改编:

<target name="retrieve" description="3rd party dependencies">
    <ivy:resolve/>

    <ivy:cachepath pathid="build.path" conf="build"/>
    <ivy:cachepath pathid="runtime.path" conf="runtime"/>
</target>

配置在 ivy.xml 文件中管理(将替换 build-dependencies.xml 文件)

<ivy-module version="2.0">
    <info organisation="com.myspotontheweb" module="HelloWorld"/>

    <configurations>
        <conf name="build" description="jars needed for build" />
        <conf name="runtime" extends="build" description="jars needed at runtime" />
    </configurations>

    <dependencies>
        <dependency org="org1" name="project1" rev="1.0" conf="build->default"/>
        <dependency org="org2" name="project2" rev="1.0" conf="build->default"/>
        <dependency org="org3" name="project3" rev="1.0" conf="runtime->default"/>
        <dependency org="org4" name="project4" rev="1.0" conf="runtime->default"/>
    </dependencies>
</ivy-module>

与每个项目关联的jar工件将从在线maven存储库中自动下载和缓存,或者您可以创建自己的本地存储库来保存本地拥有的工件的集合。

答案 3 :(得分:0)

正在使用环境变量一个选项(如果在启动eclipse时设置它们将被拾取)?如果是这样,让每个人设置ARTIFACTS,这应该有效:

<?xml version="1.0" encoding="UTF-8"?>
<project name="build-dependencies">
  <property environment="env"/>
  <path id="common-jars">
    <fileset file="${env.ARTIFACTS}/project-1/jar/some*.jar" />
    <fileset file="${env.ARTIFACTS}/project-2/jar/someother*.jar" />
  </path>
</project>

答案 4 :(得分:0)

好吧,我认为除了使用带参数的宏并使用适当的工件文件夹创建路径之外,没有其他明显的方法可以让我做我想做的事情。

为了给出一些上下文,为什么我想要的是在单独的文件夹中使用“instrumented”和“not-instrumented”工件。在我的“目标”中,我可以改变工件模式。所以我现在做的是有一个宏:<initialise-build-settings artifacts-mode="instrumented" />,用于设置所有路径和其他变量。

感谢您的回答。

答案 5 :(得分:0)

您可以使用不同的依赖项执行此操作:

setpath.xml:

<project name="setpath">
  <target name="setCommonJars">
    <path id="common-jars">
      <fileset file="${param1}/some*.jar" />
      <fileset file="${param1}/someother*.jar" />
    </path>
  </target>
</project>

的build.xml:

<project name="Test path" basedir=".">
  <import file="./setpath.xml" />

  <target name="buildT1" depends="setT1,setCommonJars">
    <property name="jar-str" refid="common-jars" />
    <echo message="buildT1: ${jar-str}" />
  </target>

  <target name="buildT2" depends="setT2,setCommonJars">
    <property name="jar-str" refid="common-jars" />
    <echo message="buildT2: ${jar-str}" />
  </target>

  <target name="setT1">
    <property name="param1" value="t1" />
  </target>

  <target name="setT2">
    <property name="param1" value="t2" />
  </target>

</project>

如果你调用目标buildT1,那么将使用t1目录,如果你调用buildT2,那么将使用t2目录。