65

已修复:这是maven-compiler-plugin 3.1 中的一个已知错误

我正在将 1000 多个 java-sources 项目的基于 ant 的构建转换为 maven。到目前为止一切顺利,但每次启动mvn compile它都会重新编译所有内容(而不是重用旧类)

使用mvn -X compile报告

[DEBUG] Stale source detected: /project_path/src/main/java/package_path/AFile1.java
[DEBUG] Stale source detected: /project_path/src/main/java/package_path/AFile2.java
...

仅适用于某个包中的文件,可能未从其余代码中引用;不是我的来源,我只是想对构建进行 mavenize)

编译不会失败,并且正在生成具有更新时间戳的类

/project_path/target/classes/package_path/AFile1.class
/project_path/target/classes/package_path/AFile2.class
...

但是,在查看时间戳时,java 文件自昨天以来没有更改,并且类文件是最新的。为什么这些来源被确定为陈旧的?我该如何调试这个问题?

即使没有发生任何更改,也必须重新编译 1k+ 文件是一件很麻烦的事……


样本输出:

$ mvn clean compile
[INFO] Scanning for projects...
[INFO]                                                                         
[INFO] ------------------------------------------------------------------------
[INFO] Building MyProject 1.9.0-SNAPSHOT
[INFO] ------------------------------------------------------------------------
[WARNING] The POM for net.sourceforge:jffmpeg:jar:1.1.0 is missing, no dependency information available
[INFO] 
[INFO] --- maven-clean-plugin:2.4.1:clean (default-clean) @ my-project ---
[INFO] Deleting /project_path/target
[INFO] 
[INFO] --- maven-resources-plugin:2.5:resources (default-resources) @ my-project ---
[debug] execute contextualize
[INFO] Using 'UTF-8' encoding to copy filtered resources.
[INFO] skip non existing resourceDirectory /project_path/src/main/resources
[INFO] 
[INFO] --- maven-compiler-plugin:3.1:compile (default-compile) @ my-project ---
[INFO] Changes detected - recompiling the module!
[INFO] Compiling 1162 source files to project_path/target/classes
....
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 11.215s
[INFO] Finished at: Tue Jul 30 12:42:25 CEST 2013
[INFO] Final Memory: 25M/429M
[INFO] ------------------------------------------------------------------------



$ mvn compile
[INFO] Scanning for projects...
[INFO]                                                                         
[INFO] ------------------------------------------------------------------------
[INFO] Building MyProject 1.9.0-SNAPSHOT
[INFO] ------------------------------------------------------------------------
[WARNING] The POM for net.sourceforge:jffmpeg:jar:1.1.0 is missing, no dependency information available
[INFO] 
[INFO] --- maven-resources-plugin:2.5:resources (default-resources) @ my-project ---
[debug] execute contextualize
[INFO] Using 'UTF-8' encoding to copy filtered resources.
[INFO] skip non existing resourceDirectory /project_path/src/main/resources
[INFO] 
[INFO] --- maven-compiler-plugin:3.1:compile (default-compile) @ my-project ---
[INFO] Changes detected - recompiling the module!
[INFO] Compiling 1162 source files to /project_path/target/classes
... 
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 12.140s
[INFO] Finished at: Tue Jul 30 12:42:44 CEST 2013
[INFO] Final Memory: 22M/379M
[INFO] ------------------------------------------------------------------------
4

9 回答 9

39

这是 maven-compiler-plugin 3.1 中的一个已知问题。它正在https://issues.apache.org/jira/browse/MCOMPILER-209中进行跟踪(useIncrementalCompilation标志已损坏)。

该问题与另一个 3.1 错误无关,https://issues.apache.org/jira/browse/MCOMPILER-205(其中不产生 .class 输出的文件始终标记为“陈旧”)。

在进一步测试之后,回到 3.0 并没有真正解决问题(它只在下一个mvn clean compile.整个代码库)。useIncrementalCompilationfalse

于 2013-07-30T13:12:04.567 回答
33

Maven 可能会显示如下消息:

[INFO] 检测到更改 - 重新编译模块!

因为项目中有一个空的 java 文件(或全部注释掉),它永远不会编译成类文件。

您可以通过使用 -X 运行 maven 来确定 maven 重建的原因。看看上面的消息。

于 2017-10-18T01:46:05.800 回答
13

面临同样的问题。mvn compile带有选项的Maven-X表明问题是由package-info.java文件引起的。

[调试] 检测到过时的源:.../package-info.java

问题是没有为.class文件生成package-info.java

在此 PR 中找到了解决方案:https ://github.com/apache/flink/pull/5644/files 引用MCOMPILER-205

<compilerArgs>
    <arg>-Xpkginfo:always</arg>
</compilerArgs>

意思是:

始终为每个 package-info.java 文件生成 package-info.class。

于 2019-07-12T09:41:17.910 回答
7

我的情况略有不同,所以我只是添加这个以防其他人有同样的问题。我的项目没有生成的类,也没有package-info.java;只有. .java_src/main/java

tl;博士

更新到maven-compiler-plugin3.1 或者使用maven-compiler-plugin3.0 并且不要设置<overwrite>true</overwrite>maven-resources-plugin.


长版

在 src 树更改为零的情况下,Maven 总是显示如下输出:

$ mvn -o compile

[INFO] --- maven-compiler-plugin:3.0:compile (default-compile) @ my-project ---
[INFO] Changes detected - recompiling the module!
[INFO] Compiling 134 source files to /home/me/my/project/target/classes

我认为这是maven-resources-plugin我的项目正在使用的父 POM 中的配置。

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-resources-plugin</artifactId>
    <configuration>
        <overwrite>true</overwrite>
    </configuration>
</plugin>

从父 POM 中删除此插件,或在我的项目中重新定义以<overwrite>false</overwrite>修复增量构建问题。

<overwrite>false</overwrite>我想知道为什么在设置Maven 再次进行增量构建后我必须进行两次构建,因此进一步调查。这仅仅是因为第一次编译生成了一个文件(称为inputFiles.lst),用于确定已更改的文件,因此在下一次编译时它可以使用该文件来检测更改。对 MCOMPILER-187的评论证实了这一点。

我意识到我使用的是maven-compiler-plugin3.0,可以升级到

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-compiler-plugin</artifactId>
    <version>3.1</version>
</plugin>

这也解决了这个问题。3.1 使用maven-shared-incremental1.1(而不是maven-compiler-plugin3.0 使用的 1.0。请注意,MCOMPILER-187MSHARED-264是涵盖更改的 2 个错误。

所以回到 maven-compiler-plugin 3.0,我观察到target/maven-status/maven-compiler-plugin/compile/default-compile/inputFiles.lst不是用<overwrite>true</overwrite>set 生成的。因此,这可能是项目在使用 maven-compiler-plugin 3.0 时无法进行增量构建的原因。

显然,通常不需要每次编译都覆盖资源,但这里的主要问题是它inputFiles.lst永远不会生成,因此 Maven 将永远无法进行增量构建。因此,请检查是否存在inputFiles.lst另一个插件,因为它可能以某种方式导致它无法生成。

于 2014-03-26T15:47:31.963 回答
4

我不明白为什么,但是 tucuxi 的答案的解决方案在我的情况下不起作用。在我的项目中,特殊工具生成了数千个文件,重新编译可能会浪费很多时间。

我尝试了以下插件配置(Java 级别 1.5):

<plugin>
    <artifactId>maven-compiler-plugin</artifactId>
    <version>3.1</version>
    <configuration>
        <source>1.5</source>
        <target>1.5</target>
        <useIncrementalCompilation>true</useIncrementalCompilation>
    </configuration>
</plugin>

在第二次运行时,没有检测到过时的文件,但插件再次重新编译了所有项目。似乎默认情况下实际上禁用了增量编译,即使指定了 useIncrementalCompilation=true 仍然无法正常工作。

经过一番谷歌搜索后,我只是将 useIncrementalCompilation 参数值从“true”更改为“yes”,这对我有用。

@另见stackoverflow.com/a/19653164/1848640

于 2014-03-21T13:20:50.167 回答
2

如果您确定没有变化,您可以传入-Dmaven.main.skip. 我有一个项目在运行 Proguard 后执行此操作,因为这是重用 Proguarded jar 进行测试的唯一方法。(注意:我在 Proguard 之前和之后运行相同的单元测试,以确保 Proguard 没有破坏任何东西。为了使这尽可能接近标准 Maven 工作流程,我在 Surefire 中运行 pre-Proguard 和 post- Proguard 在故障安全中运行。)

于 2018-07-22T04:21:33.393 回答
1

类名和文件名不匹配也会产生此错误。

于 2020-07-15T17:19:13.863 回答
0

我将 maven 编译器插件回滚到 2.3.2 版本,它只用 java 8 编译修改过的类而没有问题。

于 2019-01-21T18:50:12.203 回答
0

另一种可能发生的情况是,如果您的源文件位置和包名称不匹配。

例如,如果您有一个源文件,src/main/java/com/example/MyClass.java但该类是在一个不匹配的com.example.util包中声明的:

package com.example.util;

class MyClass { ... }

编译后的类文件最终会出现target/classes/com/example/util/MyClass.class,这会混淆“陈旧文件”检查。

于 2018-10-26T14:16:50.800 回答