Skip to content

Integration

Daniel Palme edited this page May 9, 2024 · 47 revisions

GitHub Actions

Add the GitHub Action from the Marketplace to your build pipeline.

Sample YAML code:

- name: Setup .NET Core # Required to execute ReportGenerator
  uses: actions/setup-dotnet@v3
  with:
    dotnet-version: 8.x
    dotnet-quality: 'ga'

- name: ReportGenerator
  uses: danielpalme/ReportGenerator-GitHub-Action@5
  with:
    reports: 'coverage.xml' # REQUIRED # The coverage reports that should be parsed (separated by semicolon). Globbing is supported.
    targetdir: 'coveragereport' # REQUIRED # The directory where the generated report should be saved.
    reporttypes: 'HtmlInline;Cobertura' # The output formats and scope (separated by semicolon) Values: Badges, Clover, Cobertura, OpenCover, CsvSummary, Html, Html_Dark, Html_Light, Html_BlueRed, HtmlChart, HtmlInline, HtmlInline_AzurePipelines, HtmlInline_AzurePipelines_Dark, HtmlInline_AzurePipelines_Light, HtmlSummary, Html_BlueRed_Summary, JsonSummary, Latex, LatexSummary, lcov, MarkdownSummary, MarkdownSummaryGithub, MarkdownDeltaSummary, MHtml, SvgChart, SonarQube, TeamCitySummary, TextSummary, TextDeltaSummary, Xml, XmlSummary
    sourcedirs: '' # Optional directories which contain the corresponding source code (separated by semicolon). The source directories are used if coverage report contains classes without path information.
    historydir: '' # Optional directory for storing persistent coverage information. Can be used in future reports to show coverage evolution.
    plugins: '' # Optional plugin files for custom reports or custom history storage (separated by semicolon).
    assemblyfilters: '+*' # Optional list of assemblies that should be included or excluded in the report. Exclusion filters take precedence over inclusion filters. Wildcards are allowed.
    classfilters: '+*' # Optional list of classes that should be included or excluded in the report. Exclusion filters take precedence over inclusion filters. Wildcards are allowed.
    filefilters: '+*' # Optional list of files that should be included or excluded in the report. Exclusion filters take precedence over inclusion filters. Wildcards are allowed.
    verbosity: 'Info' # The verbosity level of the log messages. Values: Verbose, Info, Warning, Error, Off
    title: '' # Optional title.
    tag: '${{ github.run_number }}_${{ github.run_id }}' # Optional tag or build version.
    license: '' # Optional license for PRO version. Get your license here: https://reportgenerator.io/pro
    customSettings: '' # Optional custom settings (separated by semicolon). See: https://github.com/danielpalme/ReportGenerator/wiki/Settings.
    toolpath: 'reportgeneratortool' # Default directory for installing the dotnet tool.

History

If you are using GitHub Actions and want to use history function you do not have to write a custom plugin for history storage. Instead you can store the history files as artifacts. So the build pipeline is something like this:

  • Download the previous history from artifacts (if available)
  • Generate the report and new history
  • Upload the new history to artifacts

Your YAML pipeline might look like this sample:

- name: Restore coverage history
  uses: dawidd6/action-download-artifact@v2
  with:
    name: CoverageHistory
    path: CoverageHistory
  continue-on-error: true

- name: ReportGenerator
  uses: danielpalme/ReportGenerator-GitHub-Action@5
  with:
    reports: '*Test*/TestResults/*/coverage.cobertura.xml'
    targetdir: 'CoverageReports'
    historydir: 'CoverageHistory'
    reporttypes: 'HtmlInline;Cobertura'

- name: Upload coverage report
  uses: actions/upload-artifact@v2
  with:
    name: CoverageReports
    path: CoverageReports

- name: Upload coverage history
  uses: actions/upload-artifact@v2
  with:
    name: CoverageHistory
    path: CoverageHistory

Azure DevOps (VSTS)

Azure DevOps extension

Add the Azure DevOps extension from the Marketplace to your build pipeline.
By using the Publish Code Coverage Results task you can embed the HTML report into the build results.
Please use a build agent that supports .NET Core (e.g. 'Hosted VS2017').

Sample YAML code:

- task: reportgenerator@5
  displayName: ReportGenerator
  inputs:
    reports: 'src\target\reports\coverage\coverage.opencover.xml'
    targetdir: '$(Build.SourcesDirectory)/coveragereport'
    reporttypes: 'HtmlInline_AzurePipelines;Cobertura;Badges'
    assemblyfilters: '-xunit*'

Attention

The PublishCodeCoverageResults@1 task from Microsoft regenerates the report with different settings and based on the supplied Coberatura file (see announcement). Moreover it does not necessarily use the latest version of ReportGenerator.
To disable the regeneration of the report, you can use the following environment variable in your build:

disable.coverage.autogenerate: 'true' # Global environment variable

- task: PublishCodeCoverageResults@1
  displayName: 'Publish code coverage results'
  inputs:
    codeCoverageTool: Cobertura
    summaryFileLocation: '$(Build.SourcesDirectory)/coveragereport/Cobertura.xml'
    reportDirectory: '$(Build.SourcesDirectory)/coveragereport'
  env:
    DISABLE_COVERAGE_AUTOGENERATE: 'true' # Local environment variable

The PublishCodeCoverageResults@1 will get deprecated.
Microsoft recommends to use the PublishCodeCoverageResults@2 instead.
The new version has several disadvantages regarding the report in the Code Coverage tab within Azure DevOps

  • No branch and method coverage
  • No details page for each class

Recommendation:
Use the setting publishCodeCoverageResults: true of the ReportGenerator task. This way you don't have to use the PublishCodeCoverageResults@1 or PublishCodeCoverageResults@2 task at all.

- task: reportgenerator@5
  displayName: ReportGenerator
  inputs:
    reports: 'coverage.xml'
    targetdir: 'coveragereport'
    publishCodeCoverageResults: true

If you want to use the PublishCodeCoverageResults@2 task you could additionally create an artifact containing the full coverage report generated by ReportGenerator. You can download the artifact and get full report with all features:

- publish: $(Build.SourcesDirectory)/coveragereport
  artifact: CoverageReports

History

If you are using Azure DevOps and want to use history function you do not have to write a custom plugin for history storage. Instead you can store the history files in Azure Artifacts as Universal Packages. So the build pipeline is something like this:

  • Get the previous history from Azure Artifacts
  • Generate the report and new history
  • Put the new history to Azure Artifacts

Your YAML pipeline might look like this sample:

variables:
  disable.coverage.autogenerate: 'true'
  codecoveragehistory.directory: '$(Build.ArtifactStagingDirectory)\history'
  codecoveragehistory.feedName: '$(Build.Repository.Name)-$(Build.SourceBranchName)'

https://devblogs.microsoft.com/devops/new-pccr-task/

- task: UniversalPackages@0
  displayName: Get code coverage history from Azure Artifacts
  continueOnError: true
  inputs:
    command: 'download'
    downloadDirectory: '$(codecoveragehistory.directory)'
    feedsToUse: 'internal'
    vstsFeed: 'xxxxxxx'
    vstsFeedPackage: '$(codecoveragehistory.feedName)'
    vstsPackageVersion: '0.*'
    
- task: reportgenerator@5
  displayName: 'Create Code coverage report'
  inputs:
    reports: '$(Build.SourcesDirectory)\**\coverage.cobertura.xml'
    targetdir: '$(Build.SourcesDirectory)\CodeCoverage'
    historydir: '$(codecoveragehistory.directory)'
    title: 'Merged code coverage for $(Build.Repository.Name)-$(Build.SourceBranchName)'

- task: UniversalPackages@0
  displayName: Publish code coverage history to Azure Artifacts
  inputs:
    command: 'publish'
    publishDirectory: '$(codecoveragehistory.directory)'
    feedsToUsePublish: 'internal'
    vstsFeedPublish: 'xxxxxx'
    vstsFeedPackagePublish: '$(codecoveragehistory.feedName)'
    versionOption: 'patch'
    packagePublishDescription: 'Code Coverage History for repository $(Build.Repository.Name) on branch $(Build.SourceBranchName)'
    verbosity: 'Information'

Manual setup

  1. Setup a VSTS build agent which runs on your machine: https://YOURACCOUNT.visualstudio.com/CoverageTest/_admin/_AgentQueue

  2. Commit/Push your project to VSTS.
    I created this sample project: VSTS_CoverageSample.zip
    It contains a .NET class library and a test project based on xUnit. It also contains two bat files which:

  3. Setup of build definition in VSTS. In this case I used the ".NET Desktop" template and made some modifications:

    • Removed the VsTest step
    • Added a Batch Script step after Build solution which executes the bat file with the following command: RunTests_$(BuildConfiguration).bat
      VSTS - Bat
    • Added a Publish Test Results step after Publish symbols path. This uploads the xUnit results to VSTS
      VSTS - Test results
    • Added a Publish Code Coverage Results step after Publish Test Results using the following configuration:
      VSTS - Publish code coverage
    • Overall build order:
      VSTS - Build order
  4. Execute build and see results
    VSTS - Build result

See also this article by @dotnetfer.

TeamCity

Navigate to General Settings of your Build Configuration Settings and add the following artifact path:

TARGETDIRECTORY_OF_REPORTGENERATOR/*.* => Coverage.zip

Now you can download the full report as a ZIP archive and also browse the report in TeamCity.

Gitlab

Add this Nuget package or install the global tool in your pipeline.

Your .gitlab-ci.yml pipeline will look like this:

stages:
  - build
  - test

build_job:
  stage: build
  script:
    - 'dotnet restore --packages .nuget'
    - 'dotnet publish -c Release .\MyProject\MyProject.csproj'

test_job:
  stage: test
  script:
    - 'mkdir coveragereports'
    - 'dotnet test -c Release --collect:"XPlat Code Coverage"'
    - '.\.nuget\reportgenerator\5.2.0\tools\net8.0\ReportGenerator.exe -reports:MyProject.Test\TestResults\*\coverage.cobertura.xml -targetdir:coveragereports "-reporttypes:Html;TeamCitySummary" -verbosity:Info -historydir:coveragehistory'
  coverage: '/##teamcity\[buildStatisticValue key=''CodeCoverageS'' value=''(\d+\.?\d*)''\]/'
  artifacts:
    paths:
      - '.\coveragereports'
  dependencies:
    - build_job

With this setup the coverage report is available as a build artifact.

The reporttype "TeamCitySummary" will make your coverage ratio available to Gitlab.
To evaluate it, navigate to "Settings" -> "CI/CD" -> "General pipelines" of your project.
Then enter the following pattern to the setting "Test coverage parsing":

`##teamcity\[buildStatisticValue key=\'CodeCoverageS\' value='(\d+\.?\d*)'\]`

Now you can use "Coverage report" badge.

Jenkins

Navigate to the Configure page of your project and add the following artifact path:

TARGETDIRECTORY_OF_REPORTGENERATOR/*.*

Now you download the full report as a ZIP archive and also browse the report in Jenkins.

You can also use the HTML Publisher Plugin.

By default Jenkins is very restrictive about JavaScript. If you use the default CSP rules you will only see a static report.
If you wish to use the JavaScript based dynamic features, then you have to change the CSP settings in Jenkins.
Navigate to the Jenkins Script Console and execute the following command:

System.setProperty("hudson.model.DirectoryBrowserSupport.CSP", "sandbox allow-scripts allow-same-origin; default-src 'self';")

CruiseControl .NET

See this tutorial: http://www.palmmedia.de/Blog/2012/9/27/cruisecontrol-net-integration-of-coverage-reports

Bitbucket

You can use this pipe for Bitbucket: https://bitbucket.org/loremfoobar/reportgenerator-coverage-bitbucket-pipe