How to Measure Test Coverage in Invoker Tests with JaCoCo

During the development of the P2 Maven Plugin, I wanted to get an overview about the test coverage of the code. The tests of this plugin can be divided in two groups:

  • Unit tests, that is written with Java, Groovy and JUnit;
  • integration tests, that is written with Maven Invoker Plugin

JaCoCo is the defacto standard for test coverage measurement in the Java ecosystem. For the unit tests, the JaCoCo configuration was not a challenge. How this configuration looks like can be read in the post "Test Coverage Reports For Maven Projects In SonarQube 8.3.x".

The challenge was how to integrate JaCoCo into the invoker tests. When running invoker tests, Maven starts for each invoker test an own Maven process. So the question is how to integrate the JaCoCo Agent for the measurement in each new Maven process. I cheated in the invoker tests of the project "JaCoCo Maven Plugin" how they integrate JaCoCo into the Maven Invoker Plugin.

JaCoCo Configuration in Maven Invoker Plugin

First of all, it is required, that the JaCoCo Maven Plugin is configured with its goal prepare-agent in your POM. Then the JaCoCo agent binary has to download into the local m2 repository of each invoker test. For this use case, the Maven Invoker Plugin has the configuration parameter extraArguments in its goal invoker:install. This parameter defines extra dependencies, that need to be installed on the local repository in addition to the dependencies that are defined in the test POM. In our case, the JaCoCo agent.

2  <extraArtifacts>
3    <extraArtifact>org.jacoco:org.jacoco.agent:${jacoco.version}:jar:runtime</extraArtifact>
4  </extraArtifacts>

In the last step, the JaCoCo Agent has to configured. Therefore, we use the JaCoCo Maven Plugin property jacoco.propertyName. In our case, the JaCoCo Agent should use the Maven Opts defined by the invoker plugin. If you want to limit the Java package for the test coverage measurement, you can use the JaCoCo Maven Plugin property jacoco.includes.

2   <!-- Enable recording of coverage during execution of maven-invoker-plugin -->
3   <jacoco.propertyName>invoker.mavenOpts</jacoco.propertyName>
4   <jacoco.includes>org.reficio.p2.*</jacoco.includes>

Now JaCoCo creates a measurement of the coverage based on unit tests AND based on the integration tests.

The whole JaCoCo configuration can be found in the P2 Maven Plugin POM.