Antlib 文件是一个根元素为 antlib 的 xml 文件。Antlib 的元素是 Apache Ant 定义任务,例如 Taskdef 或任何扩展 org.apache.tools.ant.taskdefs.AntlibDefinition 的 Ant 任务。
当前与 Ant 捆绑在一起的声明集执行此操作的是
一组任务和类型可以在 antlib 文件中一起定义。例如,文件 sample.xml 包含以下内容
<?xml version="1.0"?>
<antlib>
<typedef name="if" classname="org.acme.ant.If"/>
<typedef name="scriptpathmapper"
classname="org.acme.ant.ScriptPathMapper"
onerror="ignore"/>
<macrodef name="print">
<attribute name="file"/>
<sequential>
<concat taskname="print">
<fileset dir="." includes="@{file}"/>
</concat>
</sequential>
</macrodef>
</antlib>
它定义了两种类型或任务,if 和 scriptpathmapper。此 antlib 文件可以在构建脚本中使用,如下所示
<typedef file="sample.xml"/>
<typedef> 的其他属性也可以使用。例如,假设 sample.xml 位于包含类的 jar 文件 sample.jar 中,以下构建片段将定义 if 和 scriptpathmapper 任务/类型,并将它们放置在命名空间 URI samples:/acme.org 中。
<typedef resource="org/acme/ant/sample.xml"
uri="samples:/acme.org"/>
然后可以按如下方式使用这些定义
<sample:if valuetrue="${props}" xmlns:sample="samples:/acme.org">
<sample:scriptpathmapper language="beanshell">
some bean shell
</sample:scriptpathmapper>
</sample:if>
具有模式 antlib:java.package 的命名空间 URI 会得到特殊处理。
当 Ant 遇到具有此模式的命名空间 URI 的元素时,它将检查默认类路径中的包目录中是否存在名为 antlib.xml 的资源。
例如,假设文件 antcontrib.jar 已放置在目录 ${ant.home}/lib 中,并且它包含资源 net/sf/antcontrib/antlib.xml,其中包含所有 antcontrib 的定义,以下构建文件将自动加载 antcontrib 定义在位置 HERE
<project default="deletetest" xmlns:antcontrib="antlib:net.sf.antcontrib">
<macrodef name="showdir">
<attribute name="dir"/>
<sequential>
<antcontrib:shellscript shell="bash"> <!-- HERE -->
ls -Rl @{dir}
</antcontrib:shellscript>
</sequential>
</macrodef>
<target name="deletetest">
<delete dir="a" quiet="yes"/>
<mkdir dir="a/b"/>
<touch file="a/a.txt"/>
<touch file="a/b/b.txt"/>
<delete>
<fileset dir="a"/>
</delete>
<showdir dir="a"/>
</target>
</project>
资源位于默认类路径中的要求可能会在 Ant 的未来版本中删除。
如果您想将 antlib 与本地 Ant 安装分开,例如因为您想将该 jar 保存在项目的 SCM 系统中,则必须指定一个类路径,以便 Ant 可以找到该 jar。最好的解决方案是使用 <taskdef> 加载 antlib。
<project xmlns:antcontrib="antlib:net.sf.antcontrib"> <taskdef uri="antlib:net.sf.antcontrib" resource="net/sf/antcontrib/antlib.xml" classpath="path/to/ant-contrib.jar"/> <target name="iterate"> <antcontrib:for param="file"> <fileset dir="."/> <sequential> <echo message="- @{file}"/> </sequential> </antcontrib:for> </target> </project>
在 antlib 中定义的定义可以在 antlib 中使用。但是,定义所在的命名空间取决于使用 antlib 的 <typedef>。为了解决这个问题,在 antlib 执行期间,定义将放置在命名空间 URI ant:current 中。例如,以下 antlib 定义了任务 <if>、类型 <isallowed> 和一个宏 <ifallowed>,该宏使用任务和类型
<antlib xmlns:current="ant:current">
<taskdef name="if" classname="org.acme.ant.If"/>
<typedef name="isallowed" classname="org.acme.ant.Isallowed"/>
<macrodef name="ifallowed">
<attribute name="action"/>
<element name="do"/>
<sequential>
<current:if>
<current:isallowed test="@{action}"/>
<current:then>
<do/>
</current:then>
</current:if>
</sequential>
</macrodef>
</antlib>
Antlib 可以使用其他 antlib。
由于 antlib 中定义的名称位于调用 <typedef> 或通过自动元素解析指定的命名空间 URI 中,因此可以重复使用核心 Ant 类型和任务中的名称,前提是调用方使用命名空间 URI。例如,以下 antlib 可用于为各种任务定义默认值
<antlib xmlns:antcontrib="antlib:net.sf.antcontrib">
<presetdef name="javac">
<javac deprecation="${deprecation}"
debug="${debug}"/>
</presetdef>
<presetdef name="delete">
<delete quiet="yes"/>
</presetdef>
<presetdef name="shellscript">
<antcontrib:shellscript shell="bash"/>
</presetdef>
</antlib>
这可以按如下方式使用
<project xmlns:local="localpresets">
<typedef file="localpresets.xml" uri="localpresets"/>
<local:shellscript>
echo "hello world"
</local:shellscript>
</project>