Skip to content

Commit 5b962dd

Browse files
committed
Use xUnit v3 through Microsoft Testing Platform
Remaining issues * HTML logger: could not find an equivalent for Microsoft.Testing.Platform * Stryker: has early support for MTP with `dotnet stryker -t mtp` but the results are currently not 100% (which they should) * The VSTest target is not called anymore when running `dotnet test` under the .NET 10 SDK ⇒ coverage related targets are not run anymore, see microsoft/testfx#6719 and danielpalme/ReportGenerator#767 * Requires an additional coverage.xml file instead of the much simpler ExcludeByAttribute=GeneratedCodeAttribute that could be configured directly in the csproj * A regression was introduced in the .NET SDK 10.0.101, requiring explicit --configuration option when running dotnet commands, see dotnet/sdk#52358 * Coverage is empty when `ContinuousIntegrationBuild` is set to `true` when using Microsoft.Testing.Extensions.CodeCoverage 18.5.1 or later (`dotnet test -p:ContinuousIntegrationBuild=true` produces empty coverage but `dotnet test -p:ContinuousIntegrationBuild=false` produces correct coverage)
1 parent a0d7ba7 commit 5b962dd

4 files changed

Lines changed: 49 additions & 41 deletions

File tree

.github/workflows/continuous-integration.yml

Lines changed: 13 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,10 @@ jobs:
3131
echo "NUGET_PACKAGES=D:\nuget" >> $env:GITHUB_ENV
3232
- name: 🧑‍🔧 Install .NET SDK
3333
uses: actions/setup-dotnet@v5
34+
with:
35+
dotnet-version: |
36+
10.0.x
37+
8.0.x
3438
- name: ℹ️ Show .NET info
3539
run: dotnet --info
3640
- name: 💾 Retrieve cached NuGet packages
@@ -43,9 +47,11 @@ jobs:
4347
- name: ⚙️ Restore NuGet packages
4448
run: dotnet restore
4549
- name: 🏗 Build solution
46-
run: dotnet build --no-restore
50+
# --configuration should not be needed, see https://github.com/dotnet/sdk/issues/52358
51+
run: dotnet build --no-restore --configuration ${{ env.Configuration }}
4752
- name: 🧪 Run tests
48-
run: dotnet test --no-build
53+
# --configuration should not be needed, see https://github.com/dotnet/sdk/issues/52358
54+
run: dotnet test --no-build --configuration ${{ env.Configuration }}
4955
- name: 📤 Upload received files from failing tests
5056
uses: actions/upload-artifact@v5
5157
if: failure()
@@ -77,7 +83,7 @@ jobs:
7783
if: matrix.os == 'ubuntu-latest' && env.CODECOV_TOKEN != ''
7884
uses: codecov/codecov-action@v5
7985
with:
80-
files: coverage/*/coverage.cobertura.xml
86+
files: coverage/*/*.cobertura.xml
8187
token: ${{ env.CODECOV_TOKEN }}
8288
- name: ☂️ Upload coverage report to Codacy
8389
env:
@@ -86,9 +92,10 @@ jobs:
8692
uses: codacy/codacy-coverage-reporter-action@v1
8793
with:
8894
project-token: ${{ env.CODACY_PROJECT_TOKEN }}
89-
coverage-reports: coverage/*/coverage.cobertura.xml
95+
coverage-reports: coverage/*/*.cobertura.xml
9096
- name: 📦 Create NuGet package
91-
run: dotnet pack --no-build --output .
97+
# --configuration should not be needed, see https://github.com/dotnet/sdk/issues/52358
98+
run: dotnet pack --no-build --output . --configuration ${{ env.Configuration }}
9299
- name: 📤 Upload NuGet package artifact
93100
if: matrix.os == 'ubuntu-latest'
94101
uses: actions/upload-artifact@v5
@@ -101,7 +108,7 @@ jobs:
101108
if: matrix.os == 'ubuntu-latest' && env.STRYKER_DASHBOARD_API_KEY != ''
102109
run: |
103110
dotnet tool restore
104-
dotnet tool run dotnet-stryker --reporter dashboard --open-report:dashboard --version ${GITHUB_REF_NAME} --dashboard-api-key ${{ env.STRYKER_DASHBOARD_API_KEY }} --configuration ${{ env.Configuration }}
111+
dotnet tool run dotnet-stryker --test-runner mtp --reporter dashboard --open-report:dashboard --version ${GITHUB_REF_NAME} --dashboard-api-key ${{ env.STRYKER_DASHBOARD_API_KEY }} --configuration ${{ env.Configuration }}
105112
- name: 📝 Retrieve release notes from tag
106113
if: matrix.os == 'ubuntu-latest' && startsWith(github.ref, 'refs/tags/')
107114
run: |

global.json

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,9 @@
33
"sdk": {
44
"version": "8.0.300",
55
"allowPrerelease": false,
6-
"rollForward": "latestFeature"
6+
"rollForward": "latestMajor"
7+
},
8+
"test": {
9+
"runner": "Microsoft.Testing.Platform"
710
}
811
}
Lines changed: 21 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -1,67 +1,57 @@
11
<Project Sdk="Microsoft.NET.Sdk">
22

33
<PropertyGroup>
4+
<OutputType>Exe</OutputType>
45
<TargetFramework>net8.0</TargetFramework>
56
<Nullable>enable</Nullable>
67
</PropertyGroup>
78

89
<ItemGroup>
910
<PackageReference Include="AwesomeAssertions" Version="9.4.0" />
10-
<PackageReference Include="coverlet.collector" Version="8.0.1" PrivateAssets="all" />
11-
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="18.4.0" />
11+
<!-- Starting with version 18.5.1, coverage is empty when ContinuousIntegrationBuild is set to true -->
12+
<PackageReference Include="Microsoft.Testing.Extensions.CodeCoverage" Version="[18.4.1, 18.5.1)" />
13+
<PackageReference Include="Microsoft.Testing.Extensions.TrxReport" Version="2.2.1" />
1214
<PackageReference Include="PublicApiGenerator" Version="11.5.4" />
1315
<PackageReference Include="ReportGenerator" Version="5.5.4" PrivateAssets="all" />
1416
<PackageReference Include="Serilog" Version="4.3.1" />
1517
<PackageReference Include="Serilog.Enrichers.Environment" Version="3.0.1" />
1618
<PackageReference Include="Serilog.Enrichers.Thread" Version="4.0.0" />
17-
<PackageReference Include="Verify" Version="31.15.0" GeneratePathProperty="true" />
1819
<PackageReference Include="Verify.XunitV3" Version="31.15.0" />
19-
<PackageReference Include="xunit.v3" Version="3.2.2" />
20-
<PackageReference Include="xunit.runner.visualstudio" Version="3.1.5" PrivateAssets="all" />
20+
<PackageReference Include="xunit.v3.mtp-v2" Version="3.2.2" />
2121
</ItemGroup>
2222

23-
<ItemGroup>
24-
<VSTestLogger Include="trx%3BLogFileName=TestResults-$(TargetFramework).trx" Visible="false" Condition="$(ContinuousIntegrationBuild) == 'true'" />
25-
<VSTestLogger Include="html%3BLogFileName=TestResults-$(TargetFramework).html" Visible="false" />
26-
</ItemGroup>
23+
<PropertyGroup Label="xUnit">
24+
<!-- UseMicrosoftTestingPlatformRunner is required for JetBrains Rider to see the tests when discovery is configured to use metadata (Settings | Build, Execution, Deployment | Unit Testing | xUnit.net) -->
25+
<UseMicrosoftTestingPlatformRunner>true</UseMicrosoftTestingPlatformRunner>
26+
<!-- TestingPlatformDotnetTestSupport is ignored with the .NET 10 SDK but is required for older SDKs -->
27+
<TestingPlatformDotnetTestSupport>true</TestingPlatformDotnetTestSupport>
28+
</PropertyGroup>
2729

2830
<PropertyGroup Label="Coverage">
2931
<RootDirectory>$([System.IO.Directory]::GetParent($(MSBuildProjectDirectory)))</RootDirectory>
30-
<CoverageReportDirectory>$([System.IO.Path]::Combine($(RootDirectory),'coverage',$(TargetFramework)))</CoverageReportDirectory>
31-
<VSTestResultsDirectory Condition="$(ContinuousIntegrationBuild) == 'true'">$(RootDirectory)</VSTestResultsDirectory>
32-
<VSTestResultsDirectory Condition="$(ContinuousIntegrationBuild) != 'true'">$([System.IO.Path]::Combine($(CoverageReportDirectory),'results'))</VSTestResultsDirectory>
33-
<VSTestCollect>XPlat Code Coverage%3BExcludeByAttribute=GeneratedCodeAttribute</VSTestCollect>
34-
<VSTestLogger>@(VSTestLogger)</VSTestLogger>
32+
<CoverageReportDirectory>$([System.IO.Path]::GetFullPath($([System.IO.Path]::Combine($(RootDirectory),'coverage',$(TargetFramework)))))</CoverageReportDirectory>
33+
<CoverageReportFile>$([System.IO.Path]::Combine($(CoverageReportDirectory),'$(MSBuildProjectName).cobertura.xml'))</CoverageReportFile>
34+
<ArgsCoverage>--coverage --coverage-output-format cobertura --coverage-output $(CoverageReportFile) --coverage-settings $([System.IO.Path]::GetFullPath($([System.IO.Path]::Combine($(MSBuildThisFileDirectory), 'coverage.xml'))))</ArgsCoverage>
35+
<ArgsTrx Condition="$(ContinuousIntegrationBuild) == 'true'"> --report-trx --report-trx-filename $(MSBuildProjectName).trx --results-directory $(RootDirectory)</ArgsTrx>
36+
<TestingPlatformCommandLineArguments>$(ArgsCoverage)$(ArgsTrx)</TestingPlatformCommandLineArguments>
3537
</PropertyGroup>
3638

37-
<Target Name="GenerateHtmlCoverageReport" AfterTargets="VSTest" Condition="$(TargetFramework) != ''">
39+
<Target Name="GenerateCoverageReports" AfterTargets="VSTest" Condition="$(TargetFramework) != ''">
3840
<ItemGroup>
39-
<CoverageReport Include="$(VSTestResultsDirectory)/*/coverage.cobertura.xml" />
41+
<CoverageReport Include="$(CoverageReportDirectory)/*.cobertura.xml" />
4042
</ItemGroup>
4143
<ReportGenerator ReportFiles="@(CoverageReport)" TargetDirectory="$(CoverageReportDirectory)" ReportTypes="HtmlInline;TextSummary" />
4244
</Target>
4345

44-
<!-- Because of https://github.com/microsoft/vstest/issues/2378 -->
45-
<Target Name="MoveCoverageReport" AfterTargets="GenerateHtmlCoverageReport" Condition="$(TargetFramework) != ''">
46-
<Move SourceFiles="@(CoverageReport)" DestinationFolder="$(CoverageReportDirectory)" />
47-
<PropertyGroup>
48-
<CoverageReport>@(CoverageReport)</CoverageReport>
49-
</PropertyGroup>
50-
<ItemGroup>
51-
<CoverageReportParentDirectory Include="$([System.IO.Path]::Combine($(CoverageReport),'..'))" Condition="$(CoverageReport) != ''" />
52-
</ItemGroup>
53-
<RemoveDir Directories="@(CoverageReportParentDirectory)" />
54-
</Target>
55-
56-
<Target Name="DisplayCoverageSummary" AfterTargets="MoveCoverageReport" Condition="$(TargetFramework) != ''">
46+
<Target Name="DisplayCoverageSummary" AfterTargets="GenerateCoverageReports" Condition="$(TargetFramework) != ''">
5747
<PropertyGroup>
5848
<CatCommand Condition="!$([MSBuild]::IsOSPlatform('Windows'))">cat</CatCommand>
5949
<CatCommand Condition="$([MSBuild]::IsOSPlatform('Windows'))">type</CatCommand>
6050
</PropertyGroup>
6151
<Exec WorkingDirectory="$(CoverageReportDirectory)" Command="$(CatCommand) Summary.txt" />
6252
</Target>
63-
64-
<Target Name="OpenHtmlCoverageReport" AfterTargets="MoveCoverageReport" Condition="$(TargetFramework) != '' AND $(ContinuousIntegrationBuild) != 'true'">
53+
54+
<Target Name="OpenHtmlCoverageReport" AfterTargets="DisplayCoverageSummary" Condition="$(TargetFramework) != '' AND $(ContinuousIntegrationBuild) != 'true'">
6555
<PropertyGroup>
6656
<OpenCommand Condition="$([MSBuild]::IsOSPlatform('Linux'))">xdg-open</OpenCommand>
6757
<OpenCommand Condition="$([MSBuild]::IsOSPlatform('OSX'))">open</OpenCommand>
@@ -83,7 +73,4 @@
8373
<None Include="PublicApi.*.cs" />
8474
</ItemGroup>
8575

86-
<!-- See https://github.com/VerifyTests/Verify/issues/1513#issuecomment-3312366969 -->
87-
<Import Project="$([System.IO.Path]::Combine($(PkgVerify),'build','Verify.AfterMicrosoftNetSdk.props'))" />
88-
8976
</Project>

tests/coverage.xml

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
<?xml version="1.0" encoding="utf-8"?>
2+
<!-- https://learn.microsoft.com/en-us/dotnet/core/additional-tools/dotnet-coverage#settings -->
3+
<Configuration>
4+
<CodeCoverage>
5+
<Attributes>
6+
<Exclude>
7+
<Attribute>^System\.CodeDom\.Compiler\.GeneratedCodeAttribute$</Attribute>
8+
</Exclude>
9+
</Attributes>
10+
</CodeCoverage>
11+
</Configuration>

0 commit comments

Comments
 (0)