I have a complex java project with many maven modules. Some of these modules are covered by unit tests. Coverage results from this tests are propagated to sonarcloud instance.
I also have special module for integration tests, where are performed more complex tests.
Next to this modules is another special module just for jacoco coverage aggregation.
My goal is to increase coverage by including results from integration tests module, but for some reason these tests are completely ignored.
The structure of the project is something like this:
Could you provide a full, debug analysis log, please?
The analysis / scanner log is what’s output from the analysis command. Hopefully, the log you provide - redacted as necessary - will include that command as well.
[INFO] 15:55:53.425 Load/download plugins
[DEBUG] 15:55:53.446 Download plugin 'license' to '/home/petr/.sonar/_tmp/fileCache18133159224027425965.tmp'
[DEBUG] 15:55:53.447 --> GET https://scanner.sonarcloud.io/plugins/license/versions/7ce4b55d3b3f57a1119a281188e54928.jar
[DEBUG] 15:55:53.918 <-- 200 OK https://scanner.sonarcloud.io/plugins/license/versions/7ce4b55d3b3f57a1119a281188e54928.jar (470ms, 17405-byte body)
[DEBUG] 15:55:53.922 Download plugin 'text' to '/home/petr/.sonar/_tmp/fileCache2619409670578742892.tmp'
[DEBUG] 15:55:53.922 --> GET https://scanner.sonarcloud.io/plugins/text/versions/11a9b9e5d76fe507aaf1738f48e0b383.jar
[DEBUG] 15:55:59.428 <-- 200 OK https://scanner.sonarcloud.io/plugins/text/versions/11a9b9e5d76fe507aaf1738f48e0b383.jar (5505ms, 7022155-byte body)
[INFO] 15:56:00.315 Load/download plugins (done) | time=6890ms
[DEBUG] 15:56:00.316 Plugins not loaded because they are optional: [abap, sonarapex, csharp, cpp, cobol, dbd, dbdjavafrontend, dbdpythonfrontend, flex, go, web, jcl, javasymbolicexecution, java, javascript, kotlin, php, pli, plsql, python, rpg, ruby, sonarscala, swift, tsql, vbnet, vb, security, securitycsharpfrontend, securityjsfrontend, securityjavafrontend, securityphpfrontend, securitypythonfrontend, dart]
[DEBUG] 15:56:00.341 Plugins loaded:
[DEBUG] 15:56:00.341 * JaCoCo 1.3.0.1538 (jacoco)
[DEBUG] 15:56:00.341 * License for SonarLint 8.0.0.56531 (license)
[DEBUG] 15:56:00.341 * IaC Code Quality and Security 1.34.0.12019 (iac)
[DEBUG] 15:56:00.341 * Text Code Quality and Security 2.15.0.3845 (text)
[DEBUG] 15:56:00.341 * XML Code Quality and Security 2.10.0.4108 (xml)
The scanner now only downloads the language analyzers that are relevant to the project. The Java analyzer is not loaded, which means that the scanner didn’t find any Java files (i.e. any coverable files) in your project.
Other than the addition of the -X flag, did you run this job as you normally do?
And I’m just realizing that you haven’t mentioned how your integration test results are produced. Are these also JaCoCo reports, or something else?
And are your reports in the coverage-aggregation module imported properly? Because going module to module in the log, I see that some reports are imported successfully, and some are not. E.G.:
[DEBUG] 16:23:54.357 Reading report '/home/petr/Dokumenty/jfxsoft/jfxsoft.easymvc.parent/jfxsoft.easymvc.procedure-activator/target/site/jacoco-aggregate/jacoco.xml'
...
[WARNING] 16:23:58.236 No coverage report can be found with sonar.coverage.jacoco.xmlReportPaths='/home/petr/Dokumenty/jfxsoft/jfxsoft.easymvc.parent/jfxsoft.easymvc/target/site/jacoco-aggregate/jacoco.xml'. Using default locations: target/site/jacoco/jacoco.xml,target/site/jacoco-it/jacoco.xml,build/reports/jacoco/test/jacocoTestReport.xml
...
[WARNING] 16:23:58.383 No coverage report can be found with sonar.coverage.jacoco.xmlReportPaths='/home/petr/Dokumenty/jfxsoft/jfxsoft.easymvc.parent/jfxsoft.easymvc.concurrent/target/site/jacoco-aggregate/jacoco.xml'. Using default locations: target/site/jacoco/jacoco.xml,target/site/jacoco-it/jacoco.xml,build/reports/jacoco/test/jacocoTestReport.xml
...
[WARNING] 16:23:58.623 No coverage report can be found with sonar.coverage.jacoco.xmlReportPaths='/home/petr/Dokumenty/jfxsoft/jfxsoft.easymvc.parent/jfxsoft.easymvc.config/target/site/jacoco-aggregate/jacoco.xml'. Using default locations: target/site/jacoco/jacoco.xml,target/site/jacoco-it/jacoco.xml,build/reports/jacoco/test/jacocoTestReport.xml
...
Not all modules are covered with tests that is why coverage report is not found.
Yes, I’m using JaCoCo reports. Most interesting modules for you IMHO are:
jfxsoft.easymvc.it - here are performed integration tests
jfxsoft.easymvc.coverage - here should be aggregated coverage from all modules
When module has unit tests, results are sent to sonar and coverage is calculated. For example module “jfxsoft.easymvc.procedure” contains few unit tests and I can see some coverage in sonar.
That is what I’m doing. In coverage module I have in the end one big result. When I analyze this result in IntelliJ, I get 30% coverage. The issue is that sonarcloud is ignoring this file.
Every module inherits following configuration of JaCoCo configuration:
<!-- org.jacoco.jacoco-maven-plugin -->
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<version>${maven.jacoco.plugin.version}</version>
<executions>
<!-- Prepares the property pointing to the JaCoCo runtime agent which
is passed as VM argument when Maven the Surefire plugin is executed. -->
<execution>
<id>pre-unit-test</id>
<goals>
<goal>prepare-agent</goal>
</goals>
<configuration>
<destFile>${project.build.directory}/coverage-reports/jacoco-ut.exec</destFile>
<!-- Sets the name of the property containing the settings for JaCoCo
runtime agent. -->
<propertyName>jacoco.agent.argLine</propertyName>
<append>true</append>
</configuration>
</execution>
<!-- Ensures that the code coverage report for unit tests is created
after unit tests have been run. -->
<execution>
<id>post-unit-test</id>
<phase>test</phase>
<goals>
<goal>report</goal>
</goals>
<configuration>
<!-- Sets the path to the file which contains the execution data. -->
<dataFile>${project.build.directory}/coverage-reports/jacoco-ut.exec</dataFile>
<!-- Sets the output directory for the code coverage report. -->
<outputDirectory>${project.reporting.outputDirectory}/jacoco-ut</outputDirectory>
</configuration>
</execution>
<execution>
<id>pre-integration-test</id>
<goals>
<goal>prepare-agent-integration</goal>
</goals>
<configuration>
<destFile>${project.build.directory}/coverage-reports/jacoco-it.exec</destFile>
<!-- Sets the name of the property containing the settings for JaCoCo
runtime agent. -->
<propertyName>jacoco.agent.it.argLine</propertyName>
<append>true</append>
</configuration>
</execution>
<!-- Ensures that the code coverage report for integration tests is created
after unit tests have been run. -->
<execution>
<id>post-integration-test</id>
<phase>post-integration-test</phase>
<goals>
<goal>report-integration</goal>
</goals>
<configuration>
<!-- Sets the path to the file which contains the execution data. -->
<dataFile>${project.build.directory}/coverage-reports/jacoco-it.exec</dataFile>
<!-- Sets the output directory for the code coverage report. -->
<outputDirectory>${project.reporting.outputDirectory}/jacoco-it</outputDirectory>
</configuration>
</execution>
<!-- Merge jacoco results -->
<execution>
<id>merge-unit-and-integration</id>
<phase>post-integration-test</phase>
<goals>
<goal>merge</goal>
</goals>
<configuration>
<fileSets>
<fileSet>
<directory>${project.build.directory}/coverage-reports/</directory>
<includes>
<include>jacoco-ut.exec</include>
<include>jacoco-it.exec</include>
</includes>
</fileSet>
</fileSets>
<destFile>${project.build.directory}/coverage-reports/jacoco.all.exec</destFile>
</configuration>
</execution>
<!-- Aggregate results -->
<execution>
<id>create-merged-report</id>
<phase>post-integration-test</phase>
<goals>
<goal>report</goal>
</goals>
<configuration>
<dataFile>${project.build.directory}/coverage-reports/jacoco.all.exec</dataFile>
<outputDirectory>${project.reporting.outputDirectory}/jacoco-aggregate</outputDirectory>
</configuration>
</execution>
</executions>
</plugin>
On top of this configuration is special configuration of “coverage” module which I have posted in my first post. As you can see I’m merging UT and IT into single report. Than in “coverage” module I’m merging report of each module into a single big coverage.