Analyzing a header-only C++ library

Hi there. First things first:

  • ALM used: GitHub
  • CI system used: GitHub Actions
  • Languages of the repository: C++

I am developing a header-only C++ library and I want to analyze it using a free tier account at SonarCloud. I should say that I am also using a very similar configuration in another project where things work perfectly but the critical difference is that the other project has translation units of its own, that is, it is not a header-only library.

My problem is that SonarCloud apparently does not support analysis of pure headers isolated from the translation units they are included into. If I use the most straightforward configuration like this (the command line is broken into several lines for clarity here; authentication options not shown):

sonar-scanner
--define sonar.sources=include
--define sonar.cfamily.gcov.reportsPath=.
--define sonar.cfamily.cache.enabled=false
--define sonar.cfamily.threads=1
--define sonar.cfamily.build-wrapper-output=.

Then I get the obvious error:

The “build-wrapper-dump.json” file was found but 0 C/C++/Objective-C files were analyzed.

Okay, that is clear; indeed, there are no .cpp files under include/. Upon reading the docs on “Narrowing the scope” I modified the invocation as follows:

sonar-scanner
--define sonar.sources=include,tests/integration,tests/unit,tests/util
--define sonar.inclusions=include
--define sonar.cfamily.gcov.reportsPath=.
--define sonar.cfamily.cache.enabled=false
--define sonar.cfamily.threads=1
--define sonar.cfamily.build-wrapper-output=.

The sonar-scanner reported success but the web UI says that the project contains zero lines of code.

How do I invoke sonar-scanner correctly for a header-only project considering that I don’t want to analyze my tests?

Thanks!


Edit: I also tried this which failed with “0 C++ files were analyzed”:

sonar-scanner
--define sonar.sources=include
--define sonar.tests=tests/integration,tests/unit,tests/util
--define sonar.cfamily.gcov.reportsPath=.
--define sonar.cfamily.cache.enabled=false
--define sonar.cfamily.threads=1
--define sonar.cfamily.build-wrapper-output=.

I seem to have found a configuration that works:

sonar-scanner
--define sonar.sources=include,tests/unit,tests/integration
--define sonar.issue.ignore.allfile=a1,a2
--define sonar.issue.ignore.allfile.a1.fileRegexp='^#include.*catch\.hpp[>"]$'
--define sonar.issue.ignore.allfile.a2.fileRegexp='^auto main\([^)]*\) -> int$'
--define sonar.coverage.exclusions="tests/**/*"
--define sonar.cpd.exclusions="tests/**/*"
--define sonar.cfamily.gcov.reportsPath=.
--define sonar.cfamily.cache.enabled=false
--define sonar.cfamily.threads=1
--define sonar.cfamily.build-wrapper-output=.
--define sonar.branch.name="${GITHUB_REF##*/}"

The idea is that I declared the tests as project sources (sonar.sources), and then disabled rule checking (sonar.issue.ignore.allfile), coverage measurement (sonar.coverage.exclusions), and duplication detection (sonar.cpd.exclusions) on them.

I understood that this should have been enough to get things to work but for an unknown reason I also had to explicitly set the branch name via sonar.branch.name. Until I did that, SonarCloud could not discover more than one header file (of three) and more than one test file (of a dozen). I don’t think there should be any connection between setting the branch name and the ability to discover source files but that’s what I’m seeing.

Hello @pavel-kirienko,

We analyze source files that we compile with the build-wrapper command. So for the header file only you need to make sure that the build-wrapper command is clean building your test and your test in part of the source.

It shouldn’t be dependent on the branch name. It depends on what you at looking at. Main branch? analysis? short-lived branch PR new code analysis? For example, if you are looking at PR it will only show modified files.

Relevant doc on branches.
Thanks,

This topic was automatically closed 7 days after the last reply. New replies are no longer allowed.