1. 概述

本教程将带你快速了解 Maven 核心插件之一的 compiler 插件。关于其他核心插件的概述,可参考这篇文章

2. 插件目标

compiler 插件的核心作用是编译 Maven 项目的源代码。该插件包含两个目标(goal),且已自动绑定到 Maven 默认生命周期的特定阶段:

  • compile – 编译主代码目录下的源文件
  • testCompile – 编译测试代码目录下的源文件

以下是在 POM 中配置 compiler 插件的标准写法:

<plugin>
    <artifactId>maven-compiler-plugin</artifactId>
    <version>3.12.1</version>
    <configuration>
        ...
    </configuration>
</plugin>

最新版本可在此处查看:Maven 中央仓库

3. 核心配置

⚠️ 重要:默认情况下,compiler 插件生成兼容 Java 5 的字节码,无论你当前使用的是哪个版本的 JDK。我们可以通过以下配置修改此行为:

<configuration>
    <source>1.8</source>
    <target>1.8</target>
    <-- 其他自定义配置 -->
</configuration>

更简洁的写法是在 POM 属性中统一设置:

<properties>
    <maven.compiler.source>1.8</maven.compiler.source>
    <maven.compiler.target>1.8</maven.compiler.target>
</properties>

当需要向 javac 编译器传递参数时,compilerArgs 就派上用场了。例如,开启未检查操作的警告:

<configuration>
    <!-- 其他配置 -->
    <compilerArgs>
        <arg>-Xlint:unchecked</arg>
    </compilerArgs>
</configuration>

编译以下代码时:

public class Data {
    List<String> textList = new ArrayList();

    public void addText(String text) {
        textList.add(text);
    }

    public List getTextList() {
        return this.textList;
    }
}

控制台将输出警告信息:

[WARNING] ... Data.java:[7,29] unchecked conversion
  required: java.util.List<java.lang.String>
  found:    java.util.ArrayList

由于 compiler 插件的两个目标已自动绑定到生命周期,可直接通过以下命令触发:

mvn compile      # 编译主代码
mvn test-compile # 编译测试代码

4. Java 9+ 兼容性更新

4.1. 版本配置调整

Java 8 及之前的版本号格式为 1.x(如 1.8),而从 Java 9 开始,可直接使用主版本号:

<configuration>
    <source>9</source>
    <target>9</target>
</configuration>

同样支持在属性中定义:

<properties>
    <maven.compiler.source>9</maven.compiler.source>
    <maven.compiler.target>9</maven.compiler.target>
</properties>

⚠️ 版本要求

  • Maven ≥ 3.5.0(Java 9 支持起始版本)
  • maven-compiler-plugin ≥ 3.8.0

完整配置示例:

<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-compiler-plugin</artifactId>
            <version>3.12.1</version>
            <configuration>
                <source>9</source>
                <target>9</target>
            </configuration>
        </plugin>
    </plugins>
</build>

4.2. 模块化构建实战

假设我们要编译一个引用了其他模块包的类:

public class MavenCompilerPlugin {
    public static void main(String[] args) {
        System.out.println("The XML namespace prefix is: "
          + XML_NS_PREFIX);
    }
}

直接编译会报错:

[ERROR] COMPILATION ERROR :
[ERROR] .../MavenCompilerPlugin.java:[3,20]
  package javax.xml is not visible
  (package javax.xml is declared in module java.xml,
  but module com.baeldung.maven.java9 does not read it)
[ERROR] .../MavenCompilerPlugin.java:[3,1]
  static import only from classes and interfaces
[ERROR] .../MavenCompilerPlugin.java:[7,62]
  cannot find symbol
symbol:   variable XML_NS_PREFIX
location: class com.baeldung.maven.java9.MavenCompilerPlugin

踩坑解决:创建 module-info.java 声明模块依赖:

module com.baeldung.maven.java9 {
    requires java.xml;
}

重新执行编译命令:

mvn -q clean compile exec:java \
  -Dexec.mainClass="com.baeldung.maven.java9.MavenCompilerPlugin"

成功输出:

The XML namespace prefix is: xml

5. 总结

本文系统解析了 Maven compiler 插件的核心功能与配置技巧,特别针对 Java 9+ 的模块化特性提供了实战方案。完整示例代码可在 GitHub 项目 中获取。


原始标题:Maven Compiler Plugin | Baeldung