Ubuntu 22.04 安装 Apache Props Ant Library 指南

在 Ubuntu 22.04 上从零安装并验证 Apache Props Ant Library(ant-props 1.0.0)的完整指南,覆盖 Maven 依赖与 jar 直用两种方案。

Apache Props Ant LibraryApache Props Ant Library2026/10/15

Ubuntu 22.04 安装 Apache Props Ant Library 指南

目标:在 Ubuntu 22.04 上完成 Apache Props Ant Library(构件 org.apache.ant:ant-props:1.0.0)的安装与运行验证,覆盖 Maven 依赖集成(方案 A)与 jar 直用(方案 B)两条路线,并实测嵌套变量展开、字符串运算等核心能力(实测通过)。

一、环境信息

本文所有命令与回显均在以下环境实测采集:

项目值
操作系统Ubuntu 22.04.5 LTS(x86_64)
内核Linux 6.8.0-138-generic
JDKOpenJDK 17.0.20.1(apt 包 openjdk-17-jdk)
AntApache Ant 1.10.12(apt 包 ant)
MavenApache Maven 3.6.3(apt 包 maven)
Props Ant Libraryorg.apache.ant:ant-props:1.0.0(jar 33260 字节,SHA-1 da89e11da0ab59ce1b1ea5e79a220f98a73c5792)
实验目录/opt/props-antlib(构件仓库)、/root/props-demo(独立 Ant 工程)、/root/props-maven-demo(Maven 工程)

💡 技术拓展:ant-props 属于 Apache Ant 官方 AntLib 家族。查询其真实版本谱系最可靠的方式是直接读取 Maven Central 的 metadata:

$ curl -s --max-time 30 https://repo1.maven.org/maven2/org/apache/ant/ant-props/maven-metadata.xml
<?xml version="1.0" encoding="UTF-8"?>
<metadata>
  <groupId>org.apache.ant</groupId>
  <artifactId>ant-props</artifactId>
  <versioning>
    <latest>1.0.0</latest>
    <release>1.0.0</release>
    <versions>
      <version>1.0.0</version>
    </versions>
    <lastUpdated>20260627124331</lastUpdated>
  </versioning>
</metadata>

结论:ant-props 目前仅发布 1.0.0 一个版本,<latest> 与 <release> 均为 1.0.0,无需纠结版本选择。该 jar 只包含 5 个属性委托器类,运行时依赖 Ant 1.8.0 及以上版本(其 POM 以 1.8.0 编译),JDK 层面 8 与 17 均实测可用(见 5.4)。

二、前置条件

  1. 具备 root 或 sudo 权限,可以执行 apt 安装。
  2. 机器可访问 Maven Central(repo1.maven.org)。连通性验证实测回显如下:
$ curl -sI --max-time 20 https://repo1.maven.org/maven2/org/apache/ant/ant-props/1.0.0/ant-props-1.0.0.jar | head -3
HTTP/2 200
date: Thu, 15 Oct 2026 06:03:38 GMT
content-type: application/java-archive
  1. 基础工具 curl 需要先安装(Ubuntu 22.04 最小安装默认不带):
$ apt-get update
$ apt-get install -y curl
  1. 磁盘空间:openjdk-17-jdk 连同依赖约占用 500 MB,maven 约 10 MB,ant 约 5 MB,预留 1 GB 以上即可。

三、版本选型说明

需要选型的组件有三个:JDK、Ant、ant-props。选型依据与实测结论如下。

3.1 ant-props 版本

唯一版本 1.0.0(见第一节 metadata 回显),无历史版本包袱,直接使用。

3.2 Ant 版本

💡 技术拓展:Ant 有两种获取渠道,特性有差异:

渠道版本来源特点
apt 仓库1.10.12Ubuntu archive安装即用,ANT_HOME 固定为 /usr/share/ant,支持 antlib 自动发现(实测)
Apache 官方二进制包1.10.18dlcdn.apache.org / archive.apache.org版本最新,需要自行解压维护,本文用于 maven:3.9-eclipse-temurin-17 服务器上的交叉验证

本文主用 apt 渠道的 1.10.12:命令一条装完,路径规范(/usr/share/ant),antlib 自动发现实测可用。官方 1.10.18 在其他环境交叉验证通过,行为一致。

3.3 JDK 版本

ant-props 1.0.0 源码层仅使用 Java 基础 API(反射、正则、URI 编码),对 JDK 无高要求。本文实测 JDK 17(主环境)与 JDK 8(1.8.0_504)均可正常运行,推荐 JDK 17。

四、方案 A:Maven 依赖安装

该方案不向系统安装任何 jar,ant-props 作为 Maven 工程依赖由 maven-antrun-plugin 拉起,适合构建流程全部由 Maven 驱动的团队。

4.1 安装 JDK 与 Maven

$ apt-get install -y openjdk-17-jdk maven

安装完成后确认版本(实测回显):

$ java -version
openjdk version "17.0.20.1" 2025-11-04
OpenJDK Runtime Environment (build 17.0.20.1+1-Ubuntu-1ubuntu125.04)
OpenJDK 64-Bit Server VM (build 17.0.20.1+1-Ubuntu-1ubuntu125.04, mixed mode, sharing)
$ mvn -version
Apache Maven 3.6.3
Maven home: /usr/share/maven
Java version: 17.0.20.1, vendor: Private Build, runtime: /usr/lib/jvm/java-17-openjdk-amd64
Default locale: en, platform encoding: UTF-8
OS name: "linux", version: "6.8.0-138-generic", arch: "amd64", family: "unix"

4.2 创建工程与 pom.xml

创建工程目录并写入 pom.xml:

$ mkdir -p /root/props-maven-demo
$ cd /root/props-maven-demo
$ vim pom.xml

pom.xml 完整内容(关键点:ant 与 ant-props 声明在 maven-antrun-plugin 的 <dependencies> 内,进入插件类路径;xmlns:props 声明在 <target> 上):

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  <modelVersion>4.0.0</modelVersion>

  <groupId>demo</groupId>
  <artifactId>props-antlib-demo</artifactId>
  <version>1.0.0</version>
  <packaging>jar</packaging>

  <properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <maven.compiler.release>17</maven.compiler.release>
  </properties>

  <dependencies>
    <dependency>
      <groupId>org.apache.ant</groupId>
      <artifactId>ant</artifactId>
      <version>1.10.18</version>
    </dependency>
    <dependency>
      <groupId>org.apache.ant</groupId>
      <artifactId>ant-props</artifactId>
      <version>1.0.0</version>
    </dependency>
  </dependencies>

  <build>
    <plugins>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-compiler-plugin</artifactId>
        <version>3.11.0</version>
      </plugin>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-antrun-plugin</artifactId>
        <version>3.1.0</version>
        <dependencies>
          <dependency>
            <groupId>org.apache.ant</groupId>
            <artifactId>ant</artifactId>
            <version>1.10.18</version>
          </dependency>
          <dependency>
            <groupId>org.apache.ant</groupId>
            <artifactId>ant-props</artifactId>
            <version>1.0.0</version>
          </dependency>
        </dependencies>
        <executions>
          <execution>
            <id>props-quickstart</id>
            <phase>validate</phase>
            <goals>
              <goal>run</goal>
            </goals>
            <configuration>
              <target xmlns:props="antlib:org.apache.ant.props" name="props-quickstart">
                <typedef resource="org/apache/ant/props/antlib.xml" classpathref="maven.plugin.classpath"/>
                <propertyhelper>
                  <props:nested/>
                  <props:stringops/>
                </propertyhelper>
                <property name="app.env" value="prod"/>
                <property name="db.user.prod" value="app_rw"/>
                <property name="db.pwd.prod" value="q1w2e3r4"/>
                <property name="x" value="foo/bar/baz.ext"/>
                <echo>[1] 嵌套展开 db.user = ${db.user.${app.env}}</echo>
                <echo>[2] 嵌套展开 db.pwd = ${db.pwd.${app.env}}</echo>
                <echo>[3] 未定义取默认 cache.max = ${cache.max:-512}</echo>
                <property name="cache.max" value="1024"/>
                <echo>[4] 已定义取原值 cache.max = ${cache.max:-512}</echo>
                <echo>[5] 删前缀最短 ${x}#*/ = ${x#*/}</echo>
                <echo>[6] 取扩展名 ${x}##*. = ${x##*.}</echo>
                <echo>[7] 删扩展名 ${x}%.* = ${x%.*}</echo>
                <property name="path.str" value="org/apache/ant/props"/>
                <echo>[8] 全部替换斜杠为点 = ${path.str//\//.}</echo>
                <echo>props-antlib quickstart OK</echo>
              </target>
            </configuration>
          </execution>
        </executions>
      </plugin>
    </plugins>
  </build>
</project>

pom 中的 8 条 echo 各含一个代表性用例:db.user.${app.env} 是二级嵌套展开,${db.pwd.${app.env}} 演示密码型配置的按环境取值(示例口令统一用 q1w2e3r4),${cache.max:-512} 演示未定义时的默认值,${x#*/} 等是类 Shell 的字符串运算,${path.str//\//.} 是全量替换。

4.3 构建验证

$ MAVEN_OPTS="-Xms256m -Xmx256m" mvn -B validate

实测回显(非首次运行;首次运行会额外下载 Maven 插件与依赖,实测耗时约 23 秒):

[INFO] -----------------------< demo:props-antlib-demo >-----------------------
[INFO] Building props-antlib-demo 1.0.0
[INFO] --------------------------------[ jar ]---------------------------------
[INFO]
[INFO] --- maven-antrun-plugin:3.1.0:run (props-quickstart) @ props-antlib-demo ---
[INFO] Executing tasks
[WARNING]      [echo] [1] 嵌套展开 db.user = app_rw
[WARNING]      [echo] [2] 嵌套展开 db.pwd = q1w2e3r4
[WARNING]      [echo] [3] 未定义取默认 cache.max = 512
[WARNING]      [echo] [4] 已定义取原值 cache.max = 1024
[WARNING]      [echo] [5] 删前缀最短 foo/bar/baz.ext#*/ = bar/baz.ext
[WARNING]      [echo] [6] 取扩展名 foo/bar/baz.ext##*. = ext
[WARNING]      [echo] [7] 删扩展名 foo/bar/baz.ext%.* = foo/bar/baz
[WARNING]      [echo] [8] 全部替换斜杠为点 = org.apache.ant.props
[WARNING]      [echo] props-antlib quickstart OK
[INFO] Executed tasks
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time:  0.546 s
[INFO] Finished at: 2026-10-15T06:05:39Z
[INFO] ------------------------------------------------------------------------

8 条用例全部按预期展开,BUILD SUCCESS 即验证通过。

4.4 要点小结

  • ant-props 声明为插件依赖而非工程依赖,因为委托器类必须与 antrun 内嵌的 Ant 运行时同一个类加载器可见,实测这样声明一次成功。
  • antrun 3.1.0 把 Ant echo 的输出路由到 WARN 级别,所以每行前面是 [WARNING],这是插件行为而非报错(详见第九节 Q3)。
  • <typedef classpathref="maven.plugin.classpath"/> 是 antrun 提供的内置引用,指向插件类路径,antlib.xml 由此被找到。

五、方案 B:jar 直用(独立 Ant)

该方案绕开 Maven,直接把 ant-props-1.0.0.jar 配合系统 Ant 使用,适合纯 Ant 构建体系。

5.1 下载构件并校验

$ mkdir -p /opt/props-antlib /root/props-demo
$ cd /opt/props-antlib
$ curl -s --max-time 120 -O https://repo1.maven.org/maven2/org/apache/ant/ant-props/1.0.0/ant-props-1.0.0.jar
$ curl -s --max-time 60 -O https://repo1.maven.org/maven2/org/apache/ant/ant-props/1.0.0/ant-props-1.0.0.jar.sha1
$ ls -l ant-props-1.0.0.jar
-rw-r--r-- 1 root root 33260 Oct 15 05:58 ant-props-1.0.0.jar
$ echo "期望: $(cat ant-props-1.0.0.jar.sha1)"
期望: da89e11da0ab59ce1b1ea5e79a220f98a73c5792
$ echo "实测: $(sha1sum ant-props-1.0.0.jar | awk '{print $1}')"
实测: da89e11da0ab59ce1b1ea5e79a220f98a73c5792

期望与实测 SHA-1 一致,构件完整。

5.2 随工程装载(typedef 指定 classpath)

把 jar 与构建文件放在同一目录,构建文件内用 <typedef uri="..." resource="..." classpath="..."/> 精确指定。先复制 jar 与构建文件:

$ cp /opt/props-antlib/ant-props-1.0.0.jar /root/props-demo/
$ cd /root/props-demo
$ vim quickstart.xml

quickstart.xml 完整内容:

<?xml version="1.0" encoding="UTF-8"?>
<project name="props-quickstart" default="run" xmlns:props="antlib:org.apache.ant.props">
  <typedef uri="antlib:org.apache.ant.props" resource="org/apache/ant/props/antlib.xml" classpath="ant-props-1.0.0.jar"/>

  <propertyhelper>
    <props:nested/>
    <props:stringops/>
  </propertyhelper>

  <target name="run">
    <property name="app.env" value="prod"/>
    <property name="db.user.prod" value="app_rw"/>
    <property name="db.pwd.prod" value="q1w2e3r4"/>
    <property name="x" value="foo/bar/baz.ext"/>
    <echo>[1] 嵌套展开 db.user = ${db.user.${app.env}}</echo>
    <echo>[2] 嵌套展开 db.pwd = ${db.pwd.${app.env}}</echo>
    <echo>[3] 未定义取默认 cache.max = ${cache.max:-512}</echo>
    <property name="cache.max" value="1024"/>
    <echo>[4] 已定义取原值 cache.max = ${cache.max:-512}</echo>
    <echo>[5] 删前缀最短 ${x}#*/ = ${x#*/}</echo>
    <echo>[6] 取扩展名 ${x}##*. = ${x##*.}</echo>
    <echo>[7] 删扩展名 ${x}%.* = ${x%.*}</echo>
    <property name="path.str" value="org/apache/ant/props"/>
    <echo>[8] 全部替换斜杠为点 = ${path.str//\//.}</echo>
    <echo>props-antlib quickstart OK</echo>
  </target>
</project>

注意 <typedef> 必须带 uri="antlib:org.apache.ant.props"。实测漏写 uri 时会得到第九节 Q1 的报错。运行验证:

$ cd /root/props-demo
$ export LANG=C.UTF-8
$ ANT_OPTS="-Xms256m -Xmx256m" ant -f quickstart.xml
Buildfile: /root/props-demo/quickstart.xml

run:
     [echo] [1] 嵌套展开 db.user = app_rw
     [echo] [2] 嵌套展开 db.pwd = q1w2e3r4
     [echo] [3] 未定义取默认 cache.max = 512
     [echo] [4] 已定义取原值 cache.max = 1024
     [echo] [5] 删前缀最短 foo/bar/baz.ext#*/ = bar/baz.ext
     [echo] [6] 取扩展名 foo/bar/baz.ext##*. = ext
     [echo] [7] 删扩展名 foo/bar/baz.ext%.* = foo/bar/baz
     [echo] [8] 全部替换斜杠为点 = org.apache.ant.props
     [echo] props-antlib quickstart OK

BUILD SUCCESSFUL
Total time: 0 seconds

5.3 系统级装载(ANT_HOME/lib 自动发现)

Ubuntu apt 版 Ant 的 ANT_HOME 是 /usr/share/ant。把 jar 复制进其 lib 目录后,构建文件只需在 project 上声明 xmlns,不再需要 typedef:

$ cp /opt/props-antlib/ant-props-1.0.0.jar /usr/share/ant/lib/
$ ls -l /usr/share/ant/lib/ant-props-1.0.0.jar
-rw-r--r-- 1 root root 33260 Oct 15 06:05 /usr/share/ant/lib/ant-props-1.0.0.jar

用一个只声明命名空间的构建文件验证自动发现。delegates.xml(节选头部,完整版见专栏《Apache Props Ant Library 1.0.0 属性任务与参数详解》):

<?xml version="1.0" encoding="UTF-8"?>
<project name="props-delegates" default="all" xmlns:props="antlib:org.apache.ant.props" xmlns:if="ant:if" xmlns:unless="ant:unless">

  <propertyhelper>
    <props:nested/>
    <props:stringops/>
    <props:types/>
    <props:conditions/>
    <props:encodeURL/>
  </propertyhelper>

该文件不含 typedef,依赖 ANT_HOME/lib 自动发现。实测运行(节选尾部):

$ cd /root/props-demo
$ export LANG=C.UTF-8
$ ant -f delegates.xml | tail -4
     [echo] [U3] 中文参数编码 = https://example.com/s?wd=%E8%9A%82%E8%9A%81&amp;tag=%E4%B8%AD%E6%96%87
     [echo] props-delegates all OK

BUILD SUCCESSFUL
Total time: 0 seconds

五个委托器全部加载成功。

💡 技术拓展:jar 的两种装载位置对比:

装载方式构建文件要求可移植性适用场景
typedef + classpath(jar 随工程目录)需要 typedef 元素高,拷走目录即可用工程自包含、无 root 权限
ANT_HOME/lib(系统目录)仅需 xmlns 声明低,依赖系统状态服务器统一安装、多工程共享

本文两种方式均实测通过。注意 ANT_HOME/lib 方式依赖 Ant 的 antlib 自动发现机制,Ubuntu apt 版 Ant 1.10.12 实测支持;个别发行版重打包的 Ant(如 el8 的 1.10.5)不支持,详见《CentOS 8 安装 Apache Props Ant Library 指南》FAQ。

5.4 JDK 8 兼容性实测

ant-props 对 JDK 无高要求,用 JDK 8 复跑同一构建验证(OpenJDK 8.0.504,apt 包 openjdk-8-jdk):

$ export JAVA_HOME=/usr/lib/jvm/java-8-openjdk-amd64
$ $JAVA_HOME/bin/java -version
openjdk version "1.8.0_504"
OpenJDK Runtime Environment (build 1.8.0_504-202507221519-...)
OpenJDK 64-Bit Server VM (build 25.504-b01, mixed mode)
$ cd /root/props-demo
$ export LANG=C.UTF-8
$ ant -f quickstart.xml | head -8
Buildfile: /root/props-demo/quickstart.xml

run:
     [echo] [1] 嵌套展开 db.user = app_rw
     [echo] [2] 嵌套展开 db.pwd = q1w2e3r4
     [echo] [3] 未定义取默认 cache.max = 512
     [echo] [4] 已定义取原值 cache.max = 1024

JDK 8 下行为与 JDK 17 完全一致。Ant 启动脚本会读取环境变量 JAVA_HOME 来选择 JVM,这是切换 JDK 的正确入口。

六、方案对比

维度方案 A:Maven 依赖方案 B:jar 直用
前置软件JDK + MavenJDK + Ant
jar 位置本地 Maven 仓库(~/.m2),自动管理/opt/props-antlib 或 /usr/share/ant/lib,手工管理
版本升级改 pom.xml 版本号替换 jar 文件、改 typedef 的 classpath
CI 亲和性高,mvn 一条命令中,需要预置 jar 或 -lib 参数
与既有 Ant 脚本兼容需迁入 antrun target直接复用
本文实测pom + antrun 3.1.0 通过typedef 与 ANT_HOME/lib 两路均通过

两个方案可以共存:CI 主链路走 Maven,遗留 Ant 脚本走 jar 直用,互不影响。

七、基础配置与运行参数

7.1 JVM 堆参数

Ant 与 Maven 都通过环境变量接收 JVM 参数,脚本启动时读取。推荐按 256 MB 配置:

$ export ANT_OPTS="-Xms256m -Xmx256m"
$ export MAVEN_OPTS="-Xms256m -Xmx256m"

参数位置与修改方法:ANT_OPTS/MAVEN_OPTS 是环境变量,临时修改用 export(如上),持久化写入 /etc/profile.d/props-antlib.sh 或 ~/.bashrc。Ant 的启动脚本(/usr/bin/ant,最终调用 /usr/share/ant/bin/ant)与 Maven 的启动脚本(/usr/bin/mvn)都会把该变量的值透传给 JVM。上一节所有运行均在 ANT_OPTS="-Xms256m -Xmx256m" 下完成,实测无内存压力。

7.2 中文输出编码

最小安装的 locale 缺省是 POSIX,echo 中文会变成问号。构建前导出 UTF-8 locale(或在 JVM 参数里指定编码):

$ export LANG=C.UTF-8

实测对比:未导出时 [1] 嵌套展开 显示为 [1] ??????;导出后中文正常(见 5.2 回显)。

7.3 propertyhelper 的声明位置

<propertyhelper> 必须出现在使用这些委托器展开的 <property> 之前。实测声明顺序的影响:

$ cd /root/props-demo
$ export LANG=C.UTF-8
$ ant -f pitfall.xml
Buildfile: /root/props-demo/pitfall.xml

all:
     [echo] [E1] helper 之前定义 early = ${cache.ttl:-60}
     [echo] [E2] helper 之后定义 late = 60

BUILD SUCCESSFUL
Total time: 0 seconds

其中 pitfall.xml 完整内容(jar 与该文件同目录):

<?xml version="1.0" encoding="UTF-8"?>
<project name="pit" default="all" xmlns:props="antlib:org.apache.ant.props">
  <property name="early" value="${cache.ttl:-60}"/>

  <propertyhelper>
    <props:nested/>
    <props:stringops/>
  </propertyhelper>

  <property name="late" value="${cache.ttl:-60}"/>

  <target name="all">
    <echo>[E1] helper 之前定义 early = ${early}</echo>
    <echo>[E2] helper 之后定义 late = ${late}</echo>
  </target>
</project>

propertyhelper 之前定义的 early 保留了字面量 ${cache.ttl:-60},因为属性值在定义那一刻就完成求值,当时委托器尚未挂载。规则:propertyhelper 置于 project 顶部、所有 property 之前。

八、多版本管理

ant-props 目前只有 1.0.0,但同一机制适用于未来的后续版本。做法是把各版本 jar 并列放在 /opt/props-antlib 下,工程内的 typedef 指向具体文件名:

$ cp /opt/props-antlib/ant-props-1.0.0.jar /opt/props-antlib/ant-props-1.1.0.jar
$ ls -l /opt/props-antlib/
total 72
-rw-r--r-- 1 root root 33260 Oct 15 05:58 ant-props-1.0.0.jar
-rw-r--r-- 1 root root 33008 Oct 15 05:58 ant-props-1.1.0.jar

工程文件把 classpath 属性改为 classpath="/opt/props-antlib/ant-props-1.1.0.jar" 即完成切换;antlib 命名空间 antlib:org.apache.ant.props 与版本无关,构建文件其余部分不变。上例中的 1.1.0 仅示意文件并列方式,当前官方发布的最新版本仍为 1.0.0。

若采用 ANT_HOME/lib 方式则按文件名覆盖替换,同一命名空间不允许两个版本同时生效,替换后用 ant -diagnostics 确认类路径上的 jar 已更新。

九、FAQ

9.1 报错 propertyhelper doesn't support the nested "nested" element.

实测原因:<typedef> 少了 uri="antlib:org.apache.ant.props" 属性。无 uri 的 typedef 把组件注册进默认命名空间,而 props:nested 前缀按 antlib 命名空间查找,两边对不上。实测报错原文:

/home/props-demo/quickstart.xml:6: propertyhelper doesn't support the nested "nested" element.

修复:补上 uri 属性(见 5.2),或把 jar 放入 /usr/share/ant/lib 后删除 typedef 仅留 xmlns 声明。

9.2 echo 中文显示问号

实测原因:locale 为 POSIX,JVM 默认字符集随之变为 ANSI_X3.4-1968。修复:export LANG=C.UTF-8 后重跑(对比见 7.2)。

9.3 Maven 构建里 echo 前缀是 [WARNING]

antrun 3.1.0 将 Ant 的标准输出路由到 Maven 的 WARN 级别日志,[WARNING] [echo] 前缀是正常回显不是告警,不影响 BUILD SUCCESS(回显见 4.3)。

9.4 ${x} 没有值也不报错,原样输出

Ant 对未定义属性的语义是保持字面量原样输出而不中断构建(stringops 的 ${cache.dummy:+none} 实测输出保持原样)。这既是容错也是坑:写错属性名不会失败,只会输出原样字符串。排障时优先核对属性名拼写与定义顺序。

9.5 JDK 8 能跑 ant-props 吗

能。5.4 实测 OpenJDK 1.8.0_504 与 JDK 17 输出一致,ant-props 1.0.0 未使用 8 以上的 API。

9.6 Maven 首次构建很慢

首次运行要下载 maven-antrun-plugin 3.1.0、ant 1.10.18、ant-props 1.0.0 及其传递依赖到 ~/.m2,实测约 23 秒(仓库可达性见第二节)。后续构建复用本地仓库,实测 0.546 秒。

9.7 ANT_OPTS 写在哪里生效

三种位置按优先级从临时到持久:命令行前缀 ANT_OPTS="-Xms256m -Xmx256m" ant -f quickstart.xml;shell 配置 ~/.bashrc;系统级 /etc/profile.d/props-antlib.sh。Ant 与 Maven 各有独立变量(ANT_OPTS 与 MAVEN_OPTS),互不共享。

十、卸载与清理

先预览要删除的包,确认无误再真正卸载。预览(-s 仅模拟不执行):

$ apt-get -s purge -y ant maven openjdk-17-jdk | grep -E "Purg" | head -6
Purg ant-optional [1.10.12-1]
Purg ant [1.10.12-1]
Purg maven [3.6.3-5]
Purg openjdk-17-jdk [17.0.20.1+1-1~22.04]

确认清单符合预期后执行卸载与文件清理(逐条列出,便于按需取舍):

$ apt-get purge -y ant ant-optional maven openjdk-17-jdk
$ apt-get autoremove -y
$ rm -f /usr/share/ant/lib/ant-props-1.0.0.jar
$ rm -rf /opt/props-antlib /root/props-demo /root/props-maven-demo
$ unset ANT_OPTS MAVEN_OPTS

清理后验证:

$ ant -version
bash: /usr/bin/ant: No such file or directory
$ ls /root/props-demo
ls: cannot access '/root/props-demo': No such file or directory

若 JVM 还要给其他服务使用,保留 openjdk-17-jdk 包,只卸载 ant 与 maven 即可。

十一、参考链接