我在我的pom.xml文件中配置了Maven JaCoCo插件,如下所示:
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<jacoco.version>0.5.9.201207300726</jacoco.version>
</properties>
<profiles>
<profile>
<id>jacoco4</id>
<build>
<plugins>
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<version>${jacoco.version}</version>
<executions>
<execution>
<goals>
<goal>prepare-agent</goal>
</goals>
<configuration
<destfile>${project.build.directory}/target/jacoco.exec</destfile>
<datafile>${project.build.directory}/target/jacoco.exec</datafile>
<output>file</output>
<append>true</append>
</configuration>
</execution>
<execution>
<id>report</id>
<phase>prepare-package</phase>
<goals>
<goal>report</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
</profile>
</profiles>
我正在使用Windows 7和apache-maven-3.0.4插件。当我从cygwin终端或命令提示终端输入mvn -P jacoco4 install
时,Maven下载并运行JaCoCo插件,但是jacoco.exec
文件似乎没有被创建。以下是错误消息:
[ERROR] Unable to read execution data file C:\Users\brownru\workspace64new\vps9\vps-fileserver\target\jacoco.exec: C:\Users\brownru\workspace64new\vps9\vps-fileserver\target\jacoco.exec (The system cannot find the file specified)
java.io.FileNotFoundException: C:\Users\brownru\workspace64new\vps9\vps-fileserver\target\jacoco.exec (The system cannot find the file specified)
at java.io.FileInputStream.open(Native Method)
at java.io.FileInputStream.<init>(FileInputStream.java:120)
at org.jacoco.maven.ReportMojo.loadExecutionData(ReportMojo.java:251)
at org.jacoco.maven.ReportMojo.executeReport(ReportMojo.java:228)
at org.jacoco.maven.ReportMojo.execute(ReportMojo.java:217)
at org.apache.maven.plugin.DefaultBuildPluginManager.executeMojo(DefaultBuildPluginManager.java:101)
at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:209)
at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:153)
at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:145)
at org.apache.maven.lifecycle.internal.LifecycleModuleBuilder.buildProject(LifecycleModuleBuilder.java:84)
at org.apache.maven.lifecycle.internal.LifecycleModuleBuilder.buildProject(LifecycleModuleBuilder.java:59)
at org.apache.maven.lifecycle.internal.LifecycleStarter.singleThreadedBuild(LifecycleStarter.java:183)
at org.apache.maven.lifecycle.internal.LifecycleStarter.execute(LifecycleStarter.java:161)
at org.apache.maven.DefaultMaven.doExecute(DefaultMaven.java:320)
at org.apache.maven.DefaultMaven.execute(DefaultMaven.java:156)
at org.apache.maven.cli.MavenCli.execute(MavenCli.java:537)
at org.apache.maven.cli.MavenCli.doMain(MavenCli.java:196)
at org.apache.maven.cli.MavenCli.main(MavenCli.java:141)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.codehaus.plexus.classworlds.launcher.Launcher.launchEnhanced(Launcher.java:290)
at org.codehaus.plexus.classworlds.launcher.Launcher.launch(Launcher.java:230)
at org.codehaus.plexus.classworlds.launcher.Launcher.mainWithExitCode(Launcher.java:409)
at org.codehaus.plexus.classworlds.launcher.Launcher.main(Launcher.java:352)
无论是否在插件的配置中包含destfile
和datafile
说明符,都会显示此错误消息:
<destfile>${project.build.directory}/target/jacoco.exec</destfile>
<datafile>${project.build.directory}/target/jacoco.exec</datafile>
有人可以告诉我我做错了什么吗?
我和jacoco和maven有同样的麻烦。它与父pom覆盖了surefire的配置有关。在这种情况下,该插件没有使用定义代理的参数(对于jvm参数)。
解决方案是将“argLine”配置元素放回原位
<plugin>
<artifactId>maven-surefire-plugin</artifactId>
<configuration>
<argLine>${argLine}</argLine>
</configuration>
</plugin>
完整的插件conf看起来像
<plugin>
<artifactId>maven-surefire-plugin</artifactId>
<configuration>
<skip>true</skip>
</configuration>
<executions>
<execution>
<id>unit-test</id>
<phase>test</phase>
<goals>
<goal>test</goal>
</goals>
<configuration>
<skip>${maven.test.skip}</skip>
<argLine>${argLine}</argLine>
<excludes>
<exclude>**/*IntegrationTest.java</exclude>
</excludes>
</configuration>
</execution>
<execution>
<id>integration-test</id>
<phase>integration-test</phase>
<goals>
<goal>test</goal>
</goals>
<configuration>
<skip>${skipITs}</skip>
<argLine>${argLine}</argLine>
<includes>
<include>**/*IntegrationTest.java</include>
</includes>
</configuration>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<version>0.5.10.201208310627</version>
<configuration>
<skip>${maven.test.skip}</skip>
<destFile>${basedir}/target/coverage-reports/jacoco-unit.exec</destFile>
<dataFile>${basedir}/target/coverage-reports/jacoco-unit.exec</dataFile>
<output>file</output>
<append>true</append>
</configuration>
<executions>
<execution>
<id>jacoco-initialize</id>
<goals>
<goal>prepare-agent</goal>
</goals>
</execution>
<execution>
<id>jacoco-site</id>
<phase>verify</phase>
<goals>
<goal>report</goal>
</goals>
</execution>
</executions>
</plugin>
希望它会有用
好吧,我想我弄清楚发生了什么。
默认情况下,jacoco插件在测试阶段之前“运行”(通常在prepare-agent
生命周期阶段运行initialize目标),当它运行时,它只是将名为“argLine”的maven属性设置为像-javaagent=jacoco.jar
这样的东西
例如:
[INFO] argLine设置为-javaagent:/usernamed/.m2/repository/org/jacoco/org.jacoco.agent/ 0.5.6.201201232323 / org.jacoco.agent-0.5.6.201201232323-runtime.jar = destfile = / path /到/目标/ jacoco.exec
默认情况下,maven-surefire-plugin基本上将这个属性(如果它被设置为任何东西)“prepends”到它的分叉java测试进程,所以他们得到了货物。例如:java ${argLine ends up here}> -jar /xxx/surefirebooter3741906822495182152.jar
通常(没有jacoco),如果你还要将自己的其他东西添加到argLine(例如,-Xmx1G
等),你只需在surefire配置中设置它,就像
<build>
<plugins>
<plugin>
<artifactId>maven-surefire-plugin</artifactId>
<configuration>
<argLine>-Xmx1G</argLine>
</configuration>
</plugin>
但是,如果您正在使用jacoco,则不能通过设置全局属性this way来正常执行此操作(这是pom的根全局属性):
<properties>
<argLine>-Xmx1G</argLine>
</properties>
如果你设置<configuration><argLine>
然后它基本上覆盖了系统属性,所以jacoco参数不会传递给子进程。所以这就是你使用房产方式的原因。如果您指定属性argLine
,那么jacoco只会将其参数添加到您指定的任何内容,然后surefire将使用它。
但是,如果你的父pom已经将插件的<configuration><argLine>
设置为某种东西怎么办?或者,如果你自己设置它?它基本上将使用该值而不是jacoco正在设置的属性(您已指定手动覆盖)。
如果你自己指定<configuration><argLine>
,你可以将argLine更改为属性(见上文),并删除<configuration><argLine>
,它应该工作。如果您无法控制父级,并且父级为argline指定了某些内容,则您需要使用<configuration><argLine>${argLine} -Xmx1G</argLine>
路由。这是为了指示它忽略父设置此值的任何内容,而是使用argLine(一个jacoco为您设置)。 (我不清楚是否有一种简单的方法可以“添加”父pom对此值的值,如果有人知道如何在这里发表评论的话。)
但是,如果jacoco没有针对某些目标或某些配置文件运行怎么办?然后变量${argLine}
永远不会被设置,你可能会遇到这样的错误:
目标org.apache.maven.plugins的执行默认测试:maven-surefire-plugin:2.14:测试失败:分叉的虚拟机终止而没有说再见。 VM崩溃或System.exit调用? [错误]命令是/ bin / sh -c cd ... java'$ {argLine}'...
事实证明,当jacoco运行时,它只会“添加”到名为argLine的属性中。所以你可以安全地将<properties><argLine></argLine></properties>
添加到你的pom中(除非你已经在父pom中设置了那个,否则你不需要添加任何东西)。如果曾经调用jacoco,它会添加它。如果没有,它被设置为空字符串,这是好的。还不清楚是否有一种方法可以“添加”属性的父级值,所以它要么继承它,要么知道它存在,要么将其指定为空。
所以,最后对我来说,因为我的上游(无法访问)父母pom宣称它是这样的
<configuration><argList>${argList}</argList></configuration>
我被迫基本上遵循那条路线,因为它已经设置在(我的控制之外)父母pom中,因此:
<configuration><argList>${argList} -Xmx1G</argList></configuration>
注意,如果你的pom中有这个,那么Intellij会抱怨并且“不添加任何设置”给你的单元测试:
<configuration><argLine>${argLine} -DcustomOption=X...</argLine>
但是根本不要声明一个名为argLine的属性(即使它在命令行mvn上工作就好了)。修复/解决:声明一个空的'argLine'全局属性,和/或只是将你的-DcustomOption=X
移动到属性声明,见上文。如果您“仅”在属性声明中设置它,那么为了让IntelliJ选择它,您还需要<configuration><argLine>${argLine}</argLine>...
:|
不幸的是,即使这还不够,它还是使用了IntelliJ + maven。不知道为什么。改变了我解析时间的方式,所以不必弄乱区域(即在代码中“让他们正确”)。
我也遇到了这个问题:JaCoCo没有生成'jacoco.exec'输出文件,这意味着不会发生代码覆盖率分析。
在我的情况下,也是由于在Maven Surefire插件中使用了一个自定义argLine,它覆盖了JaCoCo Maven插件argLine,导致JaCoCo无法执行。
为了解决这个问题,我使用了JaCoCo可选参数“propertyName”将其argLine导出到Maven属性,并将其包含在Surefire argLine中:
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<configuration>
<propertyName>jacoco.agent.argLine</propertyName>
</configuration>
...
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>2.10</version>
<configuration>
<argLine>-XX:-UseSplitVerifier ${jacoco.agent.argLine}</argLine>
</configuration>
</plugin>
但是,当在Netbeans中运行单个测试时,这会导致问题。因为在这种情况下没有执行JaCoCo插件,所以“jacoco.agent.argLine”变量未初始化并且在运行任何测试之前Surefire失败。
向pom添加空白属性“jacoco.agent.argLine”解决了运行单个测试时的问题,但这也阻止了JaCoCo在执行时导出其argLine,从而有效地禁用了JaCoCo。
我使用的解决方案的最后一部分是添加一个创建空白属性的配置文件,并仅在指定单个测试时激活:
<profiles>
<profile>
<activation>
<property>
<name>test</name>
</property>
</activation>
<properties>
<jacoco.agent.argLine></jacoco.agent.argLine>
</properties>
</profile>
</profiles>
我遇到了同样的问题,并通过使用以下命令代替jacoco修复:报告 -
mvn -X org.jacoco:jacoco-maven-plugin:report
我使用配置:
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<version>${jacoco.version}</version>
<configuration>
<skip>${skipTests}</skip>
</configuration>
<executions>
<execution>
<id>jacoco-initialize</id>
<phase>initialize</phase>
<goals>
<goal>prepare-agent</goal>
</goals>
</execution>
<execution>
<id>jacoco-site</id>
<phase>package</phase>
<goals>
<goal>report</goal>
</goals>
</execution>
</executions>
</plugin>
更新:声纳生成的配置(sonar-pom.xml):
<plugin>
<artifactId>maven-surefire-plugin</artifactId>
<version>2.12</version>
<executions>
<execution>
<id>default-test</id>
<phase>test</phase>
<goals>
<goal>test</goal>
</goals>
<configuration>
<excludedGroups>server,ignore,integration</excludedGroups>
</configuration>
</execution>
</executions>
<configuration>
<excludedGroups>server,ignore,integration</excludedGroups>
<argLine>-javaagent:/tmp/jacocoagent3671192291664069011.jar=destfile=target/jacoco.exec,excludes=*_javassist_*</argLine>
<testFailureIgnore>true</testFailureIgnore>
</configuration>
</plugin>
一个问题 - 如何为每个构建定义“jacocoagent3671192291664069011.jar”。应该是:
$M2_HOME/repository/org/jacoco/org.jacoco.agent/${jacoco.version}/org.jacoco.agent-${jacoco.version}-runtime.jar