Ruby coverage simplecov json file does not work

INFO: Sensor Ruby Sensor [ruby] (done) | time=17035ms
INFO: Sensor SimpleCov Sensor for Ruby coverage [ruby]
ERROR: Cannot read coverage report file, expecting standard SimpleCov resultset JSON format: 'coverage/.resultset.json'
java.lang.ClassCastException: class org.sonarsource.analyzer.commons.internal.json.simple.JSONObject cannot be cast to class org.sonarsource.analyzer.commons.internal.json.simple.JSONArray (org.sonarsource.analyzer.commons.internal.json.simple.JSONObject and org.sonarsource.analyzer.commons.internal.json.simple.JSONArray are in unnamed module of loader org.sonar.classloader.ClassRealm @6928f576)
	at org.sonarsource.ruby.plugin.SimpleCovSensor.mergeFrameworkCoverages(SimpleCovSensor.java:121)
	at org.sonarsource.ruby.plugin.SimpleCovSensor.mergeFileCoverages(SimpleCovSensor.java:114)
	at org.sonarsource.ruby.plugin.SimpleCovSensor.execute(SimpleCovSensor.java:71)
	at org.sonar.scanner.sensor.AbstractSensorWrapper.analyse(AbstractSensorWrapper.java:48)
	at org.sonar.scanner.sensor.ModuleSensorsExecutor.execute(ModuleSensorsExecutor.java:85)
	at org.sonar.scanner.sensor.ModuleSensorsExecutor.lambda$execute$1(ModuleSensorsExecutor.java:59)
	at org.sonar.scanner.sensor.ModuleSensorsExecutor.withModuleStrategy(ModuleSensorsExecutor.java:77)
	at org.sonar.scanner.sensor.ModuleSensorsExecutor.execute(ModuleSensorsExecutor.java:59)
	at org.sonar.scanner.scan.ModuleScanContainer.doAfterStart(ModuleScanContainer.java:82)
	at org.sonar.core.platform.ComponentContainer.startComponents(ComponentContainer.java:136)
	at org.sonar.core.platform.ComponentContainer.execute(ComponentContainer.java:122)
	at org.sonar.scanner.scan.ProjectScanContainer.scan(ProjectScanContainer.java:386)
	at org.sonar.scanner.scan.ProjectScanContainer.scanRecursively(ProjectScanContainer.java:382)
	at org.sonar.scanner.scan.ProjectScanContainer.doAfterStart(ProjectScanContainer.java:351)
	at org.sonar.core.platform.ComponentContainer.startComponents(ComponentContainer.java:136)
	at org.sonar.core.platform.ComponentContainer.execute(ComponentContainer.java:122)
	at org.sonar.scanner.bootstrap.GlobalContainer.doAfterStart(GlobalContainer.java:141)
	at org.sonar.core.platform.ComponentContainer.startComponents(ComponentContainer.java:136)
	at org.sonar.core.platform.ComponentContainer.execute(ComponentContainer.java:122)
	at org.sonar.batch.bootstrapper.Batch.doExecute(Batch.java:72)
	at org.sonar.batch.bootstrapper.Batch.execute(Batch.java:66)
	at org.sonarsource.scanner.api.internal.batch.BatchIsolatedLauncher.execute(BatchIsolatedLauncher.java:46)
	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
	at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
	at java.base/java.lang.reflect.Method.invoke(Unknown Source)
	at org.sonarsource.scanner.api.internal.IsolatedLauncherProxy.invoke(IsolatedLauncherProxy.java:60)
	at com.sun.proxy.$Proxy0.execute(Unknown Source)
	at org.sonarsource.scanner.api.EmbeddedScanner.doExecute(EmbeddedScanner.java:189)
	at org.sonarsource.scanner.api.EmbeddedScanner.execute(EmbeddedScanner.java:138)
	at org.sonarsource.scanner.cli.Main.execute(Main.java:112)
	at org.sonarsource.scanner.cli.Main.execute(Main.java:75)
	at org.sonarsource.scanner.cli.Main.main(Main.java:61)

INFO: Sensor SimpleCov Sensor for Ruby coverage [ruby] (done) | time=39ms

I am using gitlab and sonar-scanner to analyze Ruby project as part of the CI pipeline.
I am generating .resultset.json under the coverage folder.

sonar.ruby.coverage.reportPaths=coverage/.resultset.json

I can see the artifact in the directory (i.e. .resultset.json file). Still the Sonarqube complains about the simplecov output file.

Sonarqube server: Community Edition Version 8.1 (build 31237)
Scanner: sonarsource/sonar-scanner-cli:latest

Can someone tell me what is going wrong here ?

Greetings,

Can you attach the coverage/.resultset.json file?

Colin

Hello,

You might want to have a look there

If it does not solve your problem, providing us the coverage/.resultset.json file as @Colin_SonarSource suggested would help a lot.

Best,
Quentin

1 Like

.resultset.txt (68.7 KB)

I have already read that. There the issue is that the user has given the output from simplecov-json output.
I have simply using the output from simplecov output json. That is not working!!!

Thanks for the file, it is indeed not what the plugin is expecting (extra Json object containing “lines” and “branches”). See this example file for comparison.

Can you describe more precisely how you are creating this file? Is it something like this:

require 'simplecov'
require 'simplecov-json'

# Generate HTML and JSON reports
SimpleCov.formatters = SimpleCov::Formatter::MultiFormatter.new([
  SimpleCov::Formatter::HTMLFormatter,
  SimpleCov::Formatter::JSONFormatter
])

SimpleCov.start do
  some_config_option 'foo'
end

As a first guess, did you enable branch coverage measurement?

SimpleCov.start do
  enable_coverage :branch
end

If yes, can you try to disable it see if it resolve the problem?

it is just the

just a require 'simplecov' in the spec file. No explicit formatter settings to generate HTML or JSON reports. No other options are set. (like you have shown)

yes I have enabled the branch coverage measurement like so in .simplecov file

SimpleCov.start 'rails' do
  enable_coverage :branch
end

I disabled the line enable_coverage :branch and the results are still the same.

.resultset.2.txt (58.0 KB)

I get the same exception.

ERROR: Cannot read coverage report file, expecting standard SimpleCov resultset JSON format: 'coverage/.resultset.json'java.lang.ClassCastException: class org.sonarsource.analyzer.commons.internal.json.simple.JSONObject cannot be cast to class org.sonarsource.analyzer.commons.internal.json.simple.JSONArray (org.sonarsource.analyzer.commons.internal.json.simple.JSONObject and org.sonarsource.analyzer.commons.internal.json.simple.JSONArray are in unnamed module of loader org.sonar.classloader.ClassRealm @6928f576)	at org.sonarsource.ruby.plugin.SimpleCovSensor.mergeFrameworkCoverages(SimpleCovSensor.java:121)

I have no idea where the lines data come from!!!
Can someone please tell me.

I managed to identify the origin of the problem, simplecov introduced branches coverage in 0.18 and modified the format of the .json file.
You can see here an interesting discussion in another project impacted by the same problem.

There is a ticket to track this issue.

The only workaround that I see currently is to use a previous version of simplecov (<= 0.17.x).

Thanks for spotting this problem.

Quentin

1 Like

Thank you for investigating it.

I really appreciate it.

1 Like

I know this is kinda old but we fixed this in our CI pipeline while using simplecov > 0.17.1 by running tests and then before executing solar-scanner:

 ruby -rjson -e 'sqube = JSON.load(File.read("coverage/.resultset.json"))["RSpec"]["coverage"].transform_values {|lines| lines["lines"]}; total = { "RSpec" => { "coverage" => sqube, "timestamp" => Time.now.to_i }}; puts JSON.dump(total)' > coverage/.resultset.solarqube.json

Then changing sonar-project.properties to include sonar.ruby.coverage.reportPaths=coverage/.resultset.solarqube.json seems to make it work.

Anyway the scanner inside solarqube should be changed to reflect the simplecov changes since 0.18 :slight_smile: