Generating a single JaCoCo coverage report for a multi-module Maven project can be tricky. If you’re struggling to aggregate results from sub-modules into one report, this guide will walk you through the solution step-by-step.
The Problem: Multi-Module JaCoCo Reports Not Merging
When using the jacoco-maven-plugin
, you might encounter these issues:
- Individual modules generate
jacoco.exec
files, but no combined report. - The
report-aggregate
goal runs too early, producing an empty report. - The root POM configuration conflicts with sub-module builds.
Why This Happens
The root cause is often incorrect plugin configuration order:
- Maven builds modules in the order listed in the root POM’s
<modules>
section. - If the
report-aggregate
module runs before sub-modules, it can’t find theirjacoco.exec
files. - The
report-aggregate
goal must execute after all sub-modules have been built and tested.
Step-by-Step Solution
1. Root POM Configuration
Configure prepare-agent
in the root POM to instrument code during tests:
<build>
<plugins>
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<version>0.8.11</version>
<executions>
<execution>
<id>prepare-agent</id>
<goals>
<goal>prepare-agent</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
2. Create a Dedicated Report Aggregator Module
Add a new module (e.g., report-aggregate
) listed last in the root POM’s <modules>
:
<modules>
<module>sub-module1</module>
<module>sub-module2</module>
<module>report-aggregate</module>
</modules>
3. Configure the Aggregator Module’s POM
In report-aggregate/pom.xml
:
- Declare dependencies on all sub-modules.
- Bind
report-aggregate
to theverify
phase:
<dependencies>
<dependency>
<groupId>com.yourgroup</groupId>
<artifactId>sub-module1</artifactId>
<version>${project.version}</version>
</dependency>
<!-- Include other sub-modules -->
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<version>0.8.11</version>
<executions>
<execution>
<id>report-aggregate</id>
<phase>verify</phase>
<goals>
<goal>report-aggregate</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
Key Fixes and Best Practices
- Build Order Matters
Ensure the aggregator module is built last so it accesses finalizedjacoco.exec
files. - Avoid Redundant Configurations
Do not includereport-aggregate
in the root POM’s plugin setup—it belongs only in the aggregator module. - Verify Dependencies
Sub-modules must be listed as<dependencies>
(not<modules>
) in the aggregator’s POM. - Check Output Directory
The merged report is generated at:report-aggregate/target/site/jacoco-aggregate/index.html
.
Common Pitfalls
- ❌ Incorrect Phase Binding: If
report-aggregate
runs duringcompile
instead ofverify
, it skips test results. - ❌ Missing Dependencies: The aggregator module must depend on all sub-modules to ensure they’re built first.
- ❌ Root POM Conflicts: Avoid defining
report-aggregate
in the root POM’s plugin section.
Final Output
After running mvn clean verify
, open report-aggregate/target/site/jacoco-aggregate/index.html
to see the merged coverage report.
Keywords
- Merge JaCoCo reports multi-module Maven
- Aggregate JaCoCo coverage report
- Maven jacoco-maven-plugin report-aggregate
- Fix empty JaCoCo report
- Combine multiple jacoco.exec files
By following these steps, you’ll streamline coverage reporting for complex projects. For more details, refer to the official JaCoCo demo.