diff --git a/.gitignore b/.gitignore
index 177132965..19ba249cd 100644
--- a/.gitignore
+++ b/.gitignore
@@ -303,4 +303,6 @@ __pycache__/
.AssemblyAttributes
DeterministicTest.props
test/coverlet.integration.determisticbuild/*.txt
-test/coverlet.integration.determisticbuild/runsettings
\ No newline at end of file
+test/coverlet.integration.determisticbuild/runsettings
+
+coverage.cobertura.xml
diff --git a/Directory.Build.props b/Directory.Build.props
index 7a716a812..9373b11bf 100644
--- a/Directory.Build.props
+++ b/Directory.Build.props
@@ -14,6 +14,7 @@
truepreview$(NoWarn);NU5105;CS1591
+ true
https://api.nuget.org/v3/index.json;
@@ -24,8 +25,4 @@
true
-
-
-
-
diff --git a/Directory.Build.targets b/Directory.Build.targets
index aea1e02e7..a2859274b 100644
--- a/Directory.Build.targets
+++ b/Directory.Build.targets
@@ -1,32 +1,4 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
diff --git a/Directory.Packages.props b/Directory.Packages.props
new file mode 100644
index 000000000..3826d83dd
--- /dev/null
+++ b/Directory.Packages.props
@@ -0,0 +1,60 @@
+
+
+ true
+ true
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/Documentation/ConsumeNightlyBuild.md b/Documentation/ConsumeNightlyBuild.md
index 8f9309335..3901f70a5 100644
--- a/Documentation/ConsumeNightlyBuild.md
+++ b/Documentation/ConsumeNightlyBuild.md
@@ -8,9 +8,9 @@ To consume nightly builds, create a `NuGet.Config` in your root solution directo
-
+
-
+
@@ -18,36 +18,44 @@ To consume nightly builds, create a `NuGet.Config` in your root solution directo
## Install packages
-### Visual Studio:
+### Visual Studio
\
Example:\

-### NuGet (Package Manager console):
+### NuGet (Package Manager console)
+
```powershell
PM> Install-Package coverlet.msbuild -Version X.X.X-preview.X.XXX -Source https://pkgs.dev.azure.com/tonerdo/coverlet/_packaging/coverlet-nightly/nuget/v3/index.json
```
+
Example:
+
```powershell
PM> Install-Package coverlet.msbuild -Version 3.0.4-preview.4.g5de0ad7d60 -Source https://pkgs.dev.azure.com/tonerdo/coverlet/_packaging/coverlet-nightly/nuget/v3/index.json
```
-### .NET CLI:
+### .NET CLI
+
```bash
dotnet add package coverlet.msbuild --version X.X.X-preview.X.XXX --source https://pkgs.dev.azure.com/tonerdo/coverlet/_packaging/coverlet-nightly/nuget/v3/index.json
```
+
Example:
+
```bash
dotnet add package coverlet.msbuild --version 3.0.4-preview.4.g5de0ad7d60 --source https://pkgs.dev.azure.com/tonerdo/coverlet/_packaging/coverlet-nightly/nuget/v3/index.json
```
-### MSBuild project file:
+### MSBuild project file
```xml
```
+
Example:
+
```xml
-```
\ No newline at end of file
+```
diff --git a/Documentation/DeterministicBuild.md b/Documentation/DeterministicBuild.md
index aa984e2dd..31fd2dae7 100644
--- a/Documentation/DeterministicBuild.md
+++ b/Documentation/DeterministicBuild.md
@@ -4,16 +4,17 @@ Support for deterministic builds is available **only** in the `msbuild` (`/p:Col
From a coverage perspective, deterministic builds create some challenges because coverage tools usually need access to complete source file metadata (ie. local path) during instrumentation and report generation. These files are reported inside the `.pdb` files, where debugging information is stored.
-In local (non-CI) builds, metadata emitted to pdbs are not "deterministic", which means that source files are reported with their full paths. For example, when we build the same project on different machines we'll have different paths emitted inside pdbs, hence, builds are "non deterministic".
+In local (non-CI) builds, metadata emitted to pdbs are not "deterministic", which means that source files are reported with their full paths. For example, when we build the same project on different machines we'll have different paths emitted inside pdbs, hence, builds are "non deterministic".
As explained above, to improve the level of security of generated artifacts (for instance, DLLs inside the NuGet package), we need to apply some signature (signing with certificate) and validate before usage to avoid possible security issues like tampering.
Finally, thanks to deterministic CI builds (with the `ContinuousIntegrationBuild` property set to `true`) plus signature we can validate artifacts and be sure that the binary was built from specific sources (because there is no hard-coded variable metadata, like paths from different build machines).
-# Deterministic report
+## Deterministic report
-Coverlet supports also deterministic reports(for now only for cobertura coverage format).
+Coverlet supports also deterministic reports(for now only for cobertura coverage format).
If you include `DeterministicReport` parameters for `msbuild` and `collectors` integrations resulting report will be like:
+
```xml
@@ -25,8 +26,8 @@ If you include `DeterministicReport` parameters for `msbuild` and `collectors` i
...
```
-As you can see we have empty `` element and the `filename` start with well known deterministic fragment `/_/...`
+As you can see we have empty `` element and the `filename` start with well known deterministic fragment `/_/...`
**Deterministic build is supported without any workaround since version 3.1.100 of .NET Core SDK**
## Workaround only for .NET Core SDK < 3.1.100
diff --git a/Documentation/Examples.md b/Documentation/Examples.md
index 55f8169f0..2a6e5cc0b 100644
--- a/Documentation/Examples.md
+++ b/Documentation/Examples.md
@@ -1,4 +1,5 @@
# Examples
+
## MSBuild Integration
* Using `/p:MergeWith` feature `Documentation/Examples/MSBuild/MergeWith/MergeWith.sln`
diff --git a/Documentation/Examples/MSBuild/DeterministicBuild/HowTo.md b/Documentation/Examples/MSBuild/DeterministicBuild/HowTo.md
index 44b9f2b1f..7afec0315 100644
--- a/Documentation/Examples/MSBuild/DeterministicBuild/HowTo.md
+++ b/Documentation/Examples/MSBuild/DeterministicBuild/HowTo.md
@@ -1,6 +1,7 @@
-To run test we need to generates packages to reference in on test project.
+To run test we need to generates packages to reference in on test project.
Run from repo root
-```
+
+```shell
C:\git\coverlet
λ dotnet pack
Microsoft (R) Build Engine version 16.5.0+d4cbfca49 for .NET Core
@@ -23,31 +24,31 @@ Copyright (C) Microsoft Corporation. All rights reserved.
coverlet.core -> C:\git\coverlet\src\coverlet.core\bin\Debug\netstandard2.0\coverlet.core.dll
coverlet.collector -> C:\git\coverlet\src\coverlet.collector\bin\Debug\netcoreapp2.0\coverlet.collector.dll
coverlet.msbuild.tasks -> C:\git\coverlet\src\coverlet.msbuild.tasks\bin\Debug\netstandard2.0\coverlet.msbuild.tasks.dll
- coverlet.console -> C:\git\coverlet\src\coverlet.console\bin\Debug\netcoreapp2.2\coverlet.console.dll
- coverlet.console -> C:\git\coverlet\src\coverlet.console\bin\Debug\netcoreapp2.2\coverlet.console.dll
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.collector.1.3.0-preview.6.ga0e22ec622.nupkg'.
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.console.1.7.2-preview.6.ga0e22ec622.nupkg'.
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.console.1.7.2-preview.6.ga0e22ec622.snupkg'.
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.collector.1.3.0-preview.6.ga0e22ec622.snupkg'.
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.msbuild.2.9.0-preview.6.ga0e22ec622.nupkg'.
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.msbuild.2.9.0-preview.6.ga0e22ec622.snupkg'.
+ coverlet.console -> C:\git\coverlet\src\coverlet.console\bin\Debug\net6.0\coverlet.console.dll
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.collector.6.0.1-preview.6.g918cd179e0.nupkg'.
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.collector.6.0.1-preview.6.g918cd179e0.snupkg'.
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.msbuild.6.0.1-preview.6.g918cd179e0.nupkg'.
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.msbuild.6.0.1-preview.6.g918cd179e0.snupkg'.
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.console.6.0.1-preview.6.g918cd179e0.nupkg'.
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.console.6.0.1-preview.6.g918cd179e0.snupkg'.
```
+
Add msbuild package version generated to `"..\Documentation\Examples\MSBuild\DeterministicBuild\XUnitTestProject1\XUnitTestProject1.csproj"`
+
```xml
- netcoreapp3.1
+ net6.0false
-
-
-
-
-
-
+
+
+
+
+ allruntime; build; native; contentfiles; analyzers; buildtransitive
@@ -58,14 +59,15 @@ Add msbuild package version generated to `"..\Documentation\Examples\MSBuild\Det
-
```
+
Go to test project folder and run
-```
+
+```shell
C:\git\coverlet\Documentation\Examples\MSBuild\DeterministicBuild (detbuilddocs -> origin)
λ dotnet test /p:CollectCoverage=true /p:DeterministicSourcePaths=true
-Test run for C:\git\coverlet\Documentation\Examples\MSBuild\DeterministicBuild\XUnitTestProject1\bin\Debug\netcoreapp3.1\XUnitTestProject1.dll(.NETCoreApp,Version=v3.1)
-Microsoft (R) Test Execution Command Line Tool Version 16.5.0
+Test run for C:\git\coverlet\Documentation\Examples\MSBuild\DeterministicBuild\XUnitTestProject1\bin\Debug\net6.0\XUnitTestProject1.dll(.NETCoreApp,Version=v6.0)
+Microsoft (R) Test Execution Command Line Tool Version 17.5.0
Copyright (c) Microsoft Corporation. All rights reserved.
Starting test execution, please wait...
@@ -94,8 +96,10 @@ Calculating coverage result...
| Average | 100% | 100% | 100% |
+---------+------+--------+--------+
```
-You should see on output folder the coverlet source root mapping file generated.
+
+You should see on output folder the coverlet source root mapping file generated.
This is the confirmation that you're running coverage on deterministic build.
+
+```text
+Documentation\Examples\MSBuild\DeterministicBuild\XUnitTestProject1\bin\Debug\net6.0\CoverletSourceRootsMapping
```
-Documentation\Examples\MSBuild\DeterministicBuild\XUnitTestProject1\bin\Debug\netcoreapp3.1\CoverletSourceRootsMapping
-```
\ No newline at end of file
diff --git a/Documentation/Examples/MSBuild/DeterministicBuild/XUnitTestProject1/XUnitTestProject1.csproj b/Documentation/Examples/MSBuild/DeterministicBuild/XUnitTestProject1/XUnitTestProject1.csproj
index de3e88f32..f59a5b534 100644
--- a/Documentation/Examples/MSBuild/DeterministicBuild/XUnitTestProject1/XUnitTestProject1.csproj
+++ b/Documentation/Examples/MSBuild/DeterministicBuild/XUnitTestProject1/XUnitTestProject1.csproj
@@ -1,15 +1,14 @@
-
+
- netcoreapp3.1
+ net6.0false
-
-
-
-
+
+
+ allruntime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/Documentation/Examples/MSBuild/MergeWith/HowTo.md b/Documentation/Examples/MSBuild/MergeWith/HowTo.md
index c157b7b80..4135a1379 100644
--- a/Documentation/Examples/MSBuild/MergeWith/HowTo.md
+++ b/Documentation/Examples/MSBuild/MergeWith/HowTo.md
@@ -1,9 +1,9 @@
**Run from solution root sln**
-To merge report togheter you need to run separate test and merge in one `json` format file.
+To merge report together you need to run separate test and merge in one `json` format file.
Last command will join and create final needed format file.
-```
+```shell
dotnet test XUnitTestProject1\XUnitTestProject1.csproj /p:CollectCoverage=true /p:CoverletOutput=../CoverageResults/
dotnet test XUnitTestProject2\XUnitTestProject2.csproj /p:CollectCoverage=true /p:CoverletOutput=../CoverageResults/ /p:MergeWith="../CoverageResults/coverage.json"
dotnet test XUnitTestProject3\XUnitTestProject3.csproj /p:CollectCoverage=true /p:CoverletOutput=../CoverageResults/ /p:MergeWith="../CoverageResults/coverage.json" /p:CoverletOutputFormat="opencover"
@@ -11,13 +11,14 @@ dotnet test XUnitTestProject3\XUnitTestProject3.csproj /p:CollectCoverage=true
You can merge also running `dotnet test` and merge with single command from a solution file, but you need to ensure that tests will run sequentially(`-m:1`). This slow down testing but avoid invalid coverage result.
-```
+```shell
dotnet test /p:CollectCoverage=true /p:CoverletOutput=../CoverageResults/ /p:MergeWith="../CoverageResults/coverage.json" /p:CoverletOutputFormat=\"opencover,json\" -m:1
```
+
N.B. You need to specify `json` format plus another format(the final one), because Coverlet can only merge proprietary format. At the end you can delete temporary `coverage.json` file.
You can also merge the coverage result and generate another valid format to export the content than opencover, like cobertura.
-```
+```shell
dotnet test /p:CollectCoverage=true /p:CoverletOutput=../CoverageResults/ /p:MergeWith="../CoverageResults/coverage.json" /p:CoverletOutputFormat=\"cobertura,json\" -m:1
```
diff --git a/Documentation/Examples/MSBuild/MergeWith/XUnitTestProject1/XUnitTestProject1.csproj b/Documentation/Examples/MSBuild/MergeWith/XUnitTestProject1/XUnitTestProject1.csproj
index 76ecf3d44..e549327fa 100644
--- a/Documentation/Examples/MSBuild/MergeWith/XUnitTestProject1/XUnitTestProject1.csproj
+++ b/Documentation/Examples/MSBuild/MergeWith/XUnitTestProject1/XUnitTestProject1.csproj
@@ -1,18 +1,18 @@
-
+
- netcoreapp3.1
+ net6.0false
-
+ allruntime; build; native; contentfiles; analyzers; buildtransitive
-
-
-
+
+
+
diff --git a/Documentation/Examples/MSBuild/MergeWith/XUnitTestProject2/XUnitTestProject2.csproj b/Documentation/Examples/MSBuild/MergeWith/XUnitTestProject2/XUnitTestProject2.csproj
index 6c938c759..be361474f 100644
--- a/Documentation/Examples/MSBuild/MergeWith/XUnitTestProject2/XUnitTestProject2.csproj
+++ b/Documentation/Examples/MSBuild/MergeWith/XUnitTestProject2/XUnitTestProject2.csproj
@@ -1,18 +1,18 @@
-
+
- netcoreapp3.1
+ net6.0false
-
+ allruntime; build; native; contentfiles; analyzers; buildtransitive
-
-
-
+
+
+
diff --git a/Documentation/Examples/MSBuild/MergeWith/XUnitTestProject3/XUnitTestProject3.csproj b/Documentation/Examples/MSBuild/MergeWith/XUnitTestProject3/XUnitTestProject3.csproj
index d5267e6a2..c622ecd0a 100644
--- a/Documentation/Examples/MSBuild/MergeWith/XUnitTestProject3/XUnitTestProject3.csproj
+++ b/Documentation/Examples/MSBuild/MergeWith/XUnitTestProject3/XUnitTestProject3.csproj
@@ -1,18 +1,18 @@
-
+
- netcoreapp3.1
+ net6.0false
-
+ allruntime; build; native; contentfiles; analyzers; buildtransitive
-
-
-
+
+
+
diff --git a/Documentation/Examples/VSTest/DeterministicBuild/HowTo.md b/Documentation/Examples/VSTest/DeterministicBuild/HowTo.md
index 96d94ef1b..0e18ffafc 100644
--- a/Documentation/Examples/VSTest/DeterministicBuild/HowTo.md
+++ b/Documentation/Examples/VSTest/DeterministicBuild/HowTo.md
@@ -1,6 +1,7 @@
-To run test we need to generates packages to reference in on test project.
+To run test we need to generates packages to reference in on test project.
Run from repo root
-```
+
+```shell
C:\git\coverlet
λ dotnet pack
Microsoft (R) Build Engine version 16.5.0+d4cbfca49 for .NET Core
@@ -23,30 +24,31 @@ Copyright (C) Microsoft Corporation. All rights reserved.
coverlet.core -> C:\git\coverlet\src\coverlet.core\bin\Debug\netstandard2.0\coverlet.core.dll
coverlet.collector -> C:\git\coverlet\src\coverlet.collector\bin\Debug\netcoreapp2.0\coverlet.collector.dll
coverlet.msbuild.tasks -> C:\git\coverlet\src\coverlet.msbuild.tasks\bin\Debug\netstandard2.0\coverlet.msbuild.tasks.dll
- coverlet.console -> C:\git\coverlet\src\coverlet.console\bin\Debug\netcoreapp2.2\coverlet.console.dll
- coverlet.console -> C:\git\coverlet\src\coverlet.console\bin\Debug\netcoreapp2.2\coverlet.console.dll
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.collector.1.3.0-preview.6.ga0e22ec622.nupkg'.
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.console.1.7.2-preview.6.ga0e22ec622.nupkg'.
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.console.1.7.2-preview.6.ga0e22ec622.snupkg'.
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.collector.1.3.0-preview.6.ga0e22ec622.snupkg'.
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.msbuild.2.9.0-preview.6.ga0e22ec622.nupkg'.
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.msbuild.2.9.0-preview.6.ga0e22ec622.snupkg'.
+ coverlet.console -> C:\git\coverlet\src\coverlet.console\bin\Debug\net6.0\coverlet.console.dll
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.collector.6.0.1-preview.6.g918cd179e0.nupkg'.
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.collector.6.0.1-preview.6.g918cd179e0.snupkg'.
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.msbuild.6.0.1-preview.6.g918cd179e0.nupkg'.
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.msbuild.6.0.1-preview.6.g918cd179e0.snupkg'.
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.console.6.0.1-preview.6.g918cd179e0.nupkg'.
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.console.6.0.1-preview.6.g918cd179e0.snupkg'.
```
+
Add collectors package version generated to `"..\Documentation\Examples\VSTest\DeterministicBuild\XUnitTestProject1\XUnitTestProject1.csproj"`
+
```xml
- netcoreapp3.1
+ net6.0false
-
-
-
-
-
+
+
+
+
+
@@ -56,12 +58,14 @@ Add collectors package version generated to `"..\Documentation\Examples\VSTest\D
```
+
Go to test project folder and run
-```
+
+```shell
C:\git\coverlet\Documentation\Examples\VSTest\DeterministicBuild (detbuilddocs -> origin)
λ dotnet test --collect:"XPlat Code Coverage" /p:DeterministicSourcePaths=true -- DataCollectionRunSettings.DataCollectors.DataCollector.Configuration.DeterministicReport=true
-Test run for C:\git\coverlet\Documentation\Examples\VSTest\DeterministicBuild\XUnitTestProject1\bin\Debug\netcoreapp3.1\XUnitTestProject1.dll(.NETCoreApp,Version=v3.1)
-Microsoft (R) Test Execution Command Line Tool Version 16.5.0
+Test run for C:\git\coverlet\Documentation\Examples\VSTest\DeterministicBuild\XUnitTestProject1\bin\Debug\netcoreapp3.1\XUnitTestProject1.dll(.NETCoreApp,Version=v6.0)
+Microsoft (R) Test Execution Command Line Tool Version 17.5.0
Copyright (c) Microsoft Corporation. All rights reserved.
Starting test execution, please wait...
@@ -75,8 +79,10 @@ Total tests: 1
Passed: 1
Total time: 1,3472 Seconds
```
-You should see on output folder the coverlet source root mapping file generated.
+
+You should see on output folder the coverlet source root mapping file generated.
This is the confirmation that you're running coverage on deterministic build.
+
+```text
+Documentation\Examples\VSTest\DeterministicBuild\XUnitTestProject1\bin\Debug\net6.0\CoverletSourceRootsMapping_XUnitTestProject1
```
-Documentation\Examples\VSTest\DeterministicBuild\XUnitTestProject1\bin\Debug\netcoreapp3.1\CoverletSourceRootsMapping_XUnitTestProject1
-```
\ No newline at end of file
diff --git a/Documentation/Examples/VSTest/DeterministicBuild/XUnitTestProject1/XUnitTestProject1.csproj b/Documentation/Examples/VSTest/DeterministicBuild/XUnitTestProject1/XUnitTestProject1.csproj
index ea3c58201..642b38552 100644
--- a/Documentation/Examples/VSTest/DeterministicBuild/XUnitTestProject1/XUnitTestProject1.csproj
+++ b/Documentation/Examples/VSTest/DeterministicBuild/XUnitTestProject1/XUnitTestProject1.csproj
@@ -1,14 +1,15 @@
- netcoreapp3.1
+ net6.0false
+ false
-
-
-
+
+
+
diff --git a/Documentation/Examples/VSTest/HelloWorld/HowTo.md b/Documentation/Examples/VSTest/HelloWorld/HowTo.md
index 548105f9f..d965d05e1 100644
--- a/Documentation/Examples/VSTest/HelloWorld/HowTo.md
+++ b/Documentation/Examples/VSTest/HelloWorld/HowTo.md
@@ -1,11 +1,11 @@
**Run from XUnitTestProject1 folder**
-```
+```shell
dotnet test --collect:"XPlat Code Coverage"
```
With custom runsettings file
-```
+```shell
dotnet test --collect:"XPlat Code Coverage" --settings runsettings.xml
-```
\ No newline at end of file
+```
diff --git a/Documentation/Examples/VSTest/HelloWorld/XUnitTestProject1/XUnitTestProject1.csproj b/Documentation/Examples/VSTest/HelloWorld/XUnitTestProject1/XUnitTestProject1.csproj
index 3000c34e8..87be69a78 100644
--- a/Documentation/Examples/VSTest/HelloWorld/XUnitTestProject1/XUnitTestProject1.csproj
+++ b/Documentation/Examples/VSTest/HelloWorld/XUnitTestProject1/XUnitTestProject1.csproj
@@ -1,15 +1,16 @@
- netcoreapp3.1
+ net6.0false
+ false
-
-
-
-
+
+
+
+ allruntime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/Documentation/GlobalTool.md b/Documentation/GlobalTool.md
index cf50232c3..06b4e87db 100644
--- a/Documentation/GlobalTool.md
+++ b/Documentation/GlobalTool.md
@@ -42,9 +42,11 @@ Options:
```
NB. For a [multiple value] options you have to specify values multiple times i.e.
-```
+
+```shell
--exclude-by-attribute 'Obsolete' --exclude-by-attribute 'GeneratedCode' --exclude-by-attribute 'CompilerGenerated'
```
+
For `--merge-with` [check the sample](Examples.md).
## Code Coverage
@@ -61,7 +63,7 @@ After the above command is run, a `coverage.json` file containing the results wi
_Note: The `--no-build` flag is specified so that the `/path/to/test-assembly.dll` isn't rebuilt_
-## Code Coverage for integration tests and end-to-end tests.
+## Code Coverage for integration tests and end-to-end tests
Sometimes, there are tests that doesn't use regular unit test frameworks like xunit. You may find yourself in a situation where your tests are driven by a custom executable/script, which when run, could do anything from making API calls to driving Selenium.
@@ -188,8 +190,9 @@ coverlet --target --targetargs --exclude-by-att
### Source Files
You can also ignore specific source files from code coverage using the `--exclude-by-file` option
- - Can be specified multiple times
- - Use file path or directory path with globbing (e.g `dir1/*.cs`)
+
+* Can be specified multiple times
+* Use file path or directory path with globbing (e.g `dir1/*.cs`)
```bash
coverlet --target --targetargs --exclude-by-file "**/dir1/class1.cs"
@@ -202,15 +205,17 @@ Coverlet gives the ability to have fine grained control over what gets excluded
Syntax: `--exclude '[Assembly-Filter]Type-Filter'`
Wildcards
-- `*` => matches zero or more characters
-- `?` => the prefixed character is optional
+
+* `*` => matches zero or more characters
+* `?` => the prefixed character is optional
Examples
- - `--exclude "[*]*"` => Excludes all types in all assemblies (nothing is instrumented)
- - `--exclude "[coverlet.*]Coverlet.Core.Coverage"` => Excludes the Coverage class in the `Coverlet.Core` namespace belonging to any assembly that matches `coverlet.*` (e.g `coverlet.core`)
- - `--exclude "[*]Coverlet.Core.Instrumentation.*"` => Excludes all types belonging to `Coverlet.Core.Instrumentation` namespace in any assembly
- - `--exclude "[coverlet.*.tests?]*"` => Excludes all types in any assembly starting with `coverlet.` and ending with `.test` or `.tests` (the `?` makes the `s` optional)
- - `--exclude "[coverlet.*]*" --exclude "[*]Coverlet.Core*"` => Excludes assemblies matching `coverlet.*` and excludes all types belonging to the `Coverlet.Core` namespace in any assembly
+
+* `--exclude "[*]*"` => Excludes all types in all assemblies (nothing is instrumented)
+* `--exclude "[coverlet.*]Coverlet.Core.Coverage"` => Excludes the Coverage class in the `Coverlet.Core` namespace belonging to any assembly that matches `coverlet.*` (e.g `coverlet.core`)
+* `--exclude "[*]Coverlet.Core.Instrumentation.*"` => Excludes all types belonging to `Coverlet.Core.Instrumentation` namespace in any assembly
+* `--exclude "[coverlet.*.tests?]*"` => Excludes all types in any assembly starting with `coverlet.` and ending with `.test` or `.tests` (the `?` makes the `s` optional)
+* `--exclude "[coverlet.*]*" --exclude "[*]Coverlet.Core*"` => Excludes assemblies matching `coverlet.*` and excludes all types belonging to the `Coverlet.Core` namespace in any assembly
```bash
coverlet --target --targetargs --exclude "[coverlet.*]Coverlet.Core.Coverage"
@@ -219,9 +224,10 @@ coverlet --target --targetargs --exclude "[cove
Coverlet goes a step in the other direction by also letting you explicitly set what can be included using the `--include` option.
Examples
- - `--include "[*]*"` => Includes all types in all assemblies (everything is instrumented)
- - `--include "[coverlet.*]Coverlet.Core.Coverage"` => Includes the Coverage class in the `Coverlet.Core` namespace belonging to any assembly that matches `coverlet.*` (e.g `coverlet.core`)
- - `--include "[coverlet.*.tests?]*"` => Includes all types in any assembly starting with `coverlet.` and ending with `.test` or `.tests` (the `?` makes the `s` optional)
+
+* `--include "[*]*"` => Includes all types in all assemblies (everything is instrumented)
+* `--include "[coverlet.*]Coverlet.Core.Coverage"` => Includes the Coverage class in the `Coverlet.Core` namespace belonging to any assembly that matches `coverlet.*` (e.g `coverlet.core`)
+* `--include "[coverlet.*.tests?]*"` => Includes all types in any assembly starting with `coverlet.` and ending with `.test` or `.tests` (the `?` makes the `s` optional)
Both `--exclude` and `--include` options can be used together but `--exclude` takes precedence. You can specify the `--exclude` and `--include` options multiple times to allow for multiple filter expressions.
diff --git a/Documentation/KnownIssues.md b/Documentation/KnownIssues.md
index 0b5b842ec..07d17df34 100644
--- a/Documentation/KnownIssues.md
+++ b/Documentation/KnownIssues.md
@@ -2,7 +2,7 @@
## VSTest stops process execution early
-*Affected drivers*: msbuild (`dotnet test`) , dotnet tool(if you're using ` --targetargs "test ... --no-build"`)
+*Affected drivers*: msbuild (`dotnet test`) , dotnet tool(if you're using `--targetargs "test ... --no-build"`)
*Symptoms:*
@@ -12,7 +12,7 @@
`warning : [coverlet] Hits file:'C:\Users\REDACTED\AppData\Local\Temp\testApp_ac32258b-fd4a-4bb4-824c-a79061e97c31' not found for module: 'testApp'`
-* zero coverage result (often only on CI but not on local)
+* zero coverage result (often only on CI but not on local)
```bash
Calculating coverage result...
@@ -37,7 +37,7 @@
+---------+------+--------+--------+
```
-The issue is related to VSTest platform https://github.com/microsoft/vstest/issues/1900#issuecomment-457488472
+The issue is related to VSTest platform
> However if testhost doesn't shut down within 100ms (as the execution is completed, we expect it to shutdown fast). vstest.console forcefully kills the process.
@@ -46,7 +46,7 @@ This happen also if there are other "piece of code" during testing that slow dow
*Solution:*
-The only way to get around this issue is to use collectors integration https://github.com/coverlet-coverage/coverlet#vstest-integration-preferred-due-to-known-issue-supports-only-net-core-application. With the collector, we're injected in test host through a in-proc collector that communicates with the VSTest platform so we can signal when we end our work.
+The only way to get around this issue is to use collectors integration . With the collector, we're injected in test host through a in-proc collector that communicates with the VSTest platform so we can signal when we end our work.
## Upgrade `coverlet.collector` to version > 1.0.0
@@ -54,7 +54,7 @@ The only way to get around this issue is to use collectors integration https://g
*Symptoms:* The same as "known issue 1".
-There is a bug inside the VSTest platform: https://github.com/microsoft/vstest/issues/2205.
+There is a bug inside the VSTest platform: .
If you upgrade the collector package with a version greater than 1.0.0, in-proc collector won't be loaded so you could incur "known issue number 1" and get zero coverage result
@@ -62,36 +62,38 @@ If you upgrade the collector package with a version greater than 1.0.0, in-proc
1) Reference `Microsoft.NET.Test.Sdk` with version *greater than* 16.4.0
-```xml
-
- ...
-
- ...
-
-```
-2) You can pass custom *coverage.runsettings* file like this
-```xml
-
-
-
-
-
-
- cobertura
-
-
-
-
-
-
-
-
-
-
-```
+ ```xml
+
+ ...
+
+ ...
+
+ ```
+
+1) You can pass custom *coverage.runsettings* file like this
+
+ ```xml
+
+
+
+
+
+
+ cobertura
+
+
+
+
+
+
+
+
+
+
+ ```
And pass it to command line
@@ -103,11 +105,11 @@ dotnet test --settings coverage.runsettings
*Affected drivers*: all drivers that support `/p:UseSourceLink=true`
-*Symptoms:* some tool like SonarSource doesn't work well see https://github.com/coverlet-coverage/coverlet/issues/482
+*Symptoms:* some tool like SonarSource doesn't work well see
`Nerdbank.GitVersioning` generates a version file on the fly but this file is not part of user solution and it's not commited to repo so the generated remote source file reference does not exit, i.e.
-```
+```text
...
...
@@ -125,7 +127,7 @@ dotnet test --settings coverage.runsettings
*Symptoms:* during build/instrumentation you may get an exception like:
-```
+```text
[coverlet] Unable to instrument module: ..\UnitTests\bin\Debug\netcoreapp2.1\Core.Messaging.dll because : Failed to resolve assembly: 'Microsoft.Azure.ServiceBus, Version=3.4.0.0, Culture=neutral, PublicKeyToken=7e34167dcc6d6d8c' [..\UnitTests.csproj]
```
@@ -148,13 +150,13 @@ or by adding the property `` to the project file
```
-NB. This **DOESN'T ALWAYS WORK**, for example in case of the shared framework https://github.com/dotnet/cli/issues/12705#issuecomment-536686785
+NB. This **DOESN'T ALWAYS WORK**, for example in case of the shared framework
We can do nothing at the moment as this is a build behaviour out of our control.
-For .NET runtime version >= 3.0 the new default behavior is to copy all assets to the build output (CopyLocalLockFileAssemblies=true) https://github.com/dotnet/cli/issues/12705#issuecomment-535150372, unfortunately the issue could still arise.
+For .NET runtime version >= 3.0 the new default behavior is to copy all assets to the build output (CopyLocalLockFileAssemblies=true) , unfortunately the issue could still arise.
-In this case the only workaround at the moment is to *manually copy* missing dlls to the output folder: https://github.com/coverlet-coverage/coverlet/issues/560#issue-496440052
+In this case the only workaround at the moment is to *manually copy* missing dlls to the output folder:
> The only reliable way to work around this problem is to drop the DLL in the unit tests project's bin\Release\netcoreapp2.2 directory.
@@ -164,7 +166,7 @@ In this case the only workaround at the moment is to *manually copy* missing dll
*Symptoms:* Running coverage on .NET Framework runtime(i.e. .NET 4.6.1) and get error like:
-```
+```text
Failed Tests.MinMax.Min_AsyncSelector_Int32_4
Error Message:
System.TypeInitializationException : The type initializer for 'Tests.AsyncEnumerableTests' threw an exception.
@@ -184,7 +186,7 @@ NB. Workaround doesn't work if test method itself explicitly creates an appdomai
*Symptoms:* You are getting following result when running Coverlet within CI/CD pipeline:
-```
+```text
+--------+------+--------+--------+
| Module | Line | Branch | Method |
+--------+------+--------+--------+
@@ -229,5 +231,5 @@ C:\Users\REDACTED\.nuget\packages\coverlet.msbuild\3.2.0\build\coverlet.msbuild.
The XML code coverage report is too large for the coverlet to parse.
*Potential Solutions:*
-* Reduce noise from auto generated code, for example excluding your EntityFrameworkCore Migrations namespace or automatically generated typed Http Clients. See [Excluding From Coverage](./MSBuildIntegration.md#excluding-from-coverage) for more information on ignoring namespaces from code coverage.
+* Reduce noise from auto generated code, for example excluding your EntityFrameworkCore Migrations namespace or automatically generated typed Http Clients. See [Excluding From Coverage](./MSBuildIntegration.md#excluding-from-coverage) for more information on ignoring namespaces from code coverage.
diff --git a/Documentation/MSBuildIntegration.md b/Documentation/MSBuildIntegration.md
index a937665be..a097462e9 100644
--- a/Documentation/MSBuildIntegration.md
+++ b/Documentation/MSBuildIntegration.md
@@ -4,7 +4,8 @@ In this mode, Coverlet doesn't require any additional setup other than including
If a property takes multiple comma-separated values please note that [you will have to add escaped quotes around the string](https://github.com/Microsoft/msbuild/issues/2999#issuecomment-366078677) like this: `/p:Exclude=\"[coverlet.*]*,[*]Coverlet.Core*\"`, `/p:Include=\"[coverlet.*]*,[*]Coverlet.Core*\"`, or `/p:CoverletOutputFormat=\"json,opencover\"`.
-To achieve same behavior above using **powershell** you need to use the verbatim argument marker `--%` like this:
+To achieve same behavior above using **powershell** you need to use the verbatim argument marker `--%` like this:
+
```powershell
dotnet test /p:CollectCoverage=true --% /p:CoverletOutputFormat=\"opencover,lcov\"
```
@@ -103,7 +104,7 @@ The above command will automatically fail the build if the line, branch or metho
dotnet test /p:CollectCoverage=true /p:Threshold=80 /p:ThresholdType=line
```
-You can specify multiple values for `ThresholdType` by separating them with commas. Valid values include `line`, `branch` and `method`.
+You can specify multiple values for `ThresholdType` by separating them with commas. Valid values include `line`, `branch` and `method`.
You can do the same for `Threshold` as well.
```bash
@@ -137,8 +138,9 @@ dotnet test /p:CollectCoverage=true /p:ExcludeByAttribute="Obsolete,GeneratedCod
### Source Files
You can also ignore specific source files from code coverage using the `ExcludeByFile` property
- - Use single or multiple paths (separate by comma)
- - Use file path or directory path with globbing (e.g `dir1/*.cs`)
+
+* Use single or multiple paths (separate by comma)
+* Use file path or directory path with globbing (e.g `dir1/*.cs`)
```bash
dotnet test /p:CollectCoverage=true /p:ExcludeByFile=\"**/dir1/class1.cs,**/dir2/*.cs,**/dir3/**/*.cs\"
@@ -151,15 +153,17 @@ Coverlet gives the ability to have fine grained control over what gets excluded
Syntax: `/p:Exclude=[Assembly-Filter]Type-Filter`
Wildcards
-- `*` => matches zero or more characters
-- `?` => the prefixed character is optional
+
+* `*` => matches zero or more characters
+* `?` => the prefixed character is optional
Examples
- - `/p:Exclude="[*]*"` => Excludes all types in all assemblies (nothing is instrumented)
- - `/p:Exclude="[coverlet.*]Coverlet.Core.Coverage"` => Excludes the Coverage class in the `Coverlet.Core` namespace belonging to any assembly that matches `coverlet.*` (e.g `coverlet.core`)
- - `/p:Exclude="[*]Coverlet.Core.Instrumentation.*"` => Excludes all types belonging to `Coverlet.Core.Instrumentation` namespace in any assembly
- - `/p:Exclude="[coverlet.*.tests?]*"` => Excludes all types in any assembly starting with `coverlet.` and ending with `.test` or `.tests` (the `?` makes the `s` optional)
- - `/p:Exclude=\"[coverlet.*]*,[*]Coverlet.Core*\"` => Excludes assemblies matching `coverlet.*` and excludes all types belonging to the `Coverlet.Core` namespace in any assembly
+
+* `/p:Exclude="[*]*"` => Excludes all types in all assemblies (nothing is instrumented)
+* `/p:Exclude="[coverlet.*]Coverlet.Core.Coverage"` => Excludes the Coverage class in the `Coverlet.Core` namespace belonging to any assembly that matches `coverlet.*` (e.g `coverlet.core`)
+* `/p:Exclude="[*]Coverlet.Core.Instrumentation.*"` => Excludes all types belonging to `Coverlet.Core.Instrumentation` namespace in any assembly
+* `/p:Exclude="[coverlet.*.tests?]*"` => Excludes all types in any assembly starting with `coverlet.` and ending with `.test` or `.tests` (the `?` makes the `s` optional)
+* `/p:Exclude=\"[coverlet.*]*,[*]Coverlet.Core*\"` => Excludes assemblies matching `coverlet.*` and excludes all types belonging to the `Coverlet.Core` namespace in any assembly
```bash
dotnet test /p:CollectCoverage=true /p:Exclude="[coverlet.*]Coverlet.Core.Coverage"
@@ -168,20 +172,21 @@ dotnet test /p:CollectCoverage=true /p:Exclude="[coverlet.*]Coverlet.Core.Covera
Coverlet goes a step in the other direction by also letting you explicitly set what can be included using the `Include` property.
Examples
- - `/p:Include="[*]*"` => Includes all types in all assemblies (everything is instrumented)
- - `/p:Include="[coverlet.*]Coverlet.Core.Coverage"` => Includes the Coverage class in the `Coverlet.Core` namespace belonging to any assembly that matches `coverlet.*` (e.g `coverlet.core`)
- - `/p:Include="[coverlet.*.tests?]*"` => Includes all types in any assembly starting with `coverlet.` and ending with `.test` or `.tests` (the `?` makes the `s` optional)
+
+* `/p:Include="[*]*"` => Includes all types in all assemblies (everything is instrumented)
+* `/p:Include="[coverlet.*]Coverlet.Core.Coverage"` => Includes the Coverage class in the `Coverlet.Core` namespace belonging to any assembly that matches `coverlet.*` (e.g `coverlet.core`)
+* `/p:Include="[coverlet.*.tests?]*"` => Includes all types in any assembly starting with `coverlet.` and ending with `.test` or `.tests` (the `?` makes the `s` optional)
Both `Exclude` and `Include` properties can be used together but `Exclude` takes precedence. You can specify multiple filter expressions by separting them with a comma (`,`).
You can also include coverage of the test assembly itself by setting `/p:IncludeTestAssembly` to `true`.
-### Skip auto-implemented properties
+### Skip auto-implemented properties
-Neither track nor record auto-implemented properties.
+Neither track nor record auto-implemented properties.
Syntax: `/p:SkipAutoProps=true`
-### Instrument module wihtout local sources file.
+### Instrument module wihtout local sources file
Syntax: `/p:InstrumentModulesWithoutLocalSources=true`
@@ -200,7 +205,7 @@ To exclude or include multiple assemblies when using Powershell scripts or creat
Azure DevOps builds do not require double quotes to be unescaped:
-```
+```shell
dotnet test --configuration $(buildConfiguration) --no-build /p:CollectCoverage=true /p:CoverletOutputFormat=cobertura /p:CoverletOutput=$(Build.SourcesDirectory)/TestResults/Coverage/ /p:Exclude="[MyAppName.DebugHost]*%2c[MyAppNamet.WebHost]*%2c[MyAppName.App]*"
```
@@ -223,16 +228,17 @@ Coverlet supports [SourceLink](https://github.com/dotnet/sourcelink) custom debu
## Deterministic build
-Take a look at [documentation](DeterministicBuild.md) for further informations.
-To generate deterministc report the parameter is:
-```
+Take a look at [documentation](DeterministicBuild.md) for further information.
+To generate deterministic report the parameter is:
+
+```shell
/p:DeterministicReport=true
```
## Exclude assemblies without sources from coverage
The heuristic coverlet uses to determine if an assembly is a third-party dependency is based on the matching of the assembly`s source documents and the corresponding source files.
-This parameter has three different values to control the automatic assembly exclusion.
+This parameter has three different values to control the automatic assembly exclusion.
| Parameter | Description |
|-----------|-------------|
@@ -241,6 +247,7 @@ This parameter has three different values to control the automatic assembly excl
| None | No assembly is excluded. |
Here is an example of how to specifiy the parameter:
-```
+
+```shell
/p:ExcludeAssembliesWithoutSources="MissingAny"
-```
\ No newline at end of file
+```
diff --git a/Documentation/ReleasePlan.md b/Documentation/ReleasePlan.md
index 84f09223b..1adceaa6e 100644
--- a/Documentation/ReleasePlan.md
+++ b/Documentation/ReleasePlan.md
@@ -2,9 +2,9 @@
## Versioning strategy
-Coverlet is versioned with Semantic Versioning [2.0.0](https://semver.org/#semantic-versioning-200) that states:
+Coverlet is versioned with Semantic Versioning [6.0.0](https://semver.org/#semantic-versioning-200) that states:
-```
+```text
Given a version number MAJOR.MINOR.PATCH, increment the:
MAJOR version when you make incompatible API changes,
@@ -13,32 +13,31 @@ PATCH version when you make backwards-compatible bug fixes.
Additional labels for pre-release and build metadata are available as extensions to the MAJOR.MINOR.PATCH format.
```
-We release 3 components as NuGet packages:
+We release 3 components as NuGet packages:
-**coverlet.msbuild.nupkg**
-**coverlet.console.nupkg**
-**coverlet.collector.nupkg**
+**coverlet.msbuild.nupkg**
+**coverlet.console.nupkg**
+**coverlet.collector.nupkg**
### Current versions
| Package | Version |
|:----------------------|:--------|
-|**coverlet.msbuild** | 6.0.0 |
+|**coverlet.msbuild** | 6.0.0 |
|**coverlet.console** | 6.0.0 |
|**coverlet.collector** | 6.0.0 |
-
| Release Date | coverlet.msbuild | coverlet.console | coverlet.collector| commit hash | notes |
| :-----------------|:-----------------|:------------------|:------------------|:-----------------------------------------|:-------------------------------|
-| 05 May 2023 | 6.0.0 | 6.0.0 | 6.0.0 | 3ad4fa1d5cd7ffe206c0cb9dc805ee6ca5a7b550 | Version aligned with github one|
-| 29 Oct 2022 | 3.2.0 | 3.2.0 | 3.2.0 | e2c9d84a84a9d2d240ac15feb70f9198c6f8e173 | |
-| 06 Feb 2022 | 3.1.2 | 3.1.2 | 3.1.2 | e335b1a8025e49e2f2de6b40ef12ec9d3ed11ceb | Fix CoreLib coverage issues |
-| 30 Jan 2022 | 3.1.1 | 3.1.1 | 3.1.1 | e4278c06faba63122a870df15a1a1b934f6bc81d | |
-| 19 July 2021 | 3.1.0 | 3.1.0 | 3.1.0 | 5a0ecc1e92fd754e2439dc3e4c828ff7386aa1a7 | Support for determistic build |
-| 21 February 2021 | 3.0.3 | 3.0.3 | 3.0.3 | adfabfd58de0aabe263e7d2080324e0b8541071e | Fix regressions |
-| 24 January 2021 | 3.0.2 | 3.0.2 | 3.0.2 | ed918515492193fd154b60270d440c40fa30fee9 | Fix regressions |
-| 16 January 2021 | 3.0.1 | 3.0.1 | 3.0.1 | 1b45fd89245369ae94407e7a77bdfee112042486 | Fix severe coverage regression |
-| 09 January 2021 | 3.0.0 | 3.0.0 | 3.0.0 | 1e77f9d2183a320e8991bfc296460e793301931f | Align versions numbers |
+| 05 May 2023 | 6.0.0 | 6.0.0 | 6.0.0 | 3ad4fa1d5cd7ffe206c0cb9dc805ee6ca5a7b550 | Version aligned with github one|
+| 29 Oct 2022 | 3.2.0 | 3.2.0 | 3.2.0 | e2c9d84a84a9d2d240ac15feb70f9198c6f8e173 | |
+| 06 Feb 2022 | 3.1.2 | 3.1.2 | 3.1.2 | e335b1a8025e49e2f2de6b40ef12ec9d3ed11ceb | Fix CoreLib coverage issues |
+| 30 Jan 2022 | 3.1.1 | 3.1.1 | 3.1.1 | e4278c06faba63122a870df15a1a1b934f6bc81d | |
+| 19 July 2021 | 3.1.0 | 3.1.0 | 3.1.0 | 5a0ecc1e92fd754e2439dc3e4c828ff7386aa1a7 | Support for determistic build |
+| 21 February 2021 | 3.0.3 | 3.0.3 | 3.0.3 | adfabfd58de0aabe263e7d2080324e0b8541071e | Fix regressions |
+| 24 January 2021 | 3.0.2 | 3.0.2 | 3.0.2 | ed918515492193fd154b60270d440c40fa30fee9 | Fix regressions |
+| 16 January 2021 | 3.0.1 | 3.0.1 | 3.0.1 | 1b45fd89245369ae94407e7a77bdfee112042486 | Fix severe coverage regression |
+| 09 January 2021 | 3.0.0 | 3.0.0 | 3.0.0 | 1e77f9d2183a320e8991bfc296460e793301931f | Align versions numbers |
| 30 May 2020 | 2.9.0 | 1.7.2 | 1.3.0 | 83a38d45b3f9c231d705bfed849efbf41b3aaa86 | deterministic build support |
| 04 April 2020 | 2.8.1 | 1.7.1 | 1.2.1 | 3f81828821d07d756e02a4105b2533cedf0b543c | |
| 03 January 2019 | 2.8.0 | 1.7.0 | 1.2.0 | 72a688f1c47fa92059540d5fbb1c4b0b4bf0dc8c | |
@@ -47,80 +46,81 @@ We release 3 components as NuGet packages:
| 06 June 2019 | 2.6.2 | 1.5.2 | 1.0.0 | 3e7eac9df094c22335711a298d359890aed582e8 | first collector release |
To get the list of commits between two version use git command
+
```bash
git log --oneline hashbefore currenthash
```
-# How to manually compare latest release with nightly build
-Before creating a new release it makes sense to test the new release against a benchmark repository. This can help to determine bugs that haven't been found
-by the unit/integration tests. Therefore, coverage of the latest release is compared with our nightly build.
+## How to manually compare latest release with nightly build
-In the following example the benchmark repository refit (https://github.com/reactiveui/refit) is used which already uses coverlet for coverage.
+Before creating a new release it makes sense to test the new release against a benchmark repository. This can help to determine bugs that haven't been found
+by the unit/integration tests. Therefore, coverage of the latest release is compared with our nightly build.
-1. Clone the benchmark repository (https://github.com/reactiveui/refit)
-
-2. Check if latest coverlet version is used by the project, otherwise add coverlet to the project (https://github.com/coverlet-coverage/coverlet#installation).
+In the following example the benchmark repository refit () is used which already uses coverlet for coverage.
+1. Clone the benchmark repository ()
+2. Check if latest coverlet version is used by the project, otherwise add coverlet to the project ().
3. Create coverage report for latest coverlet version:
-```
-dotnet test --collect:"XPlat Code Coverage"
-```
+
+ ```shell
+ dotnet test --collect:"XPlat Code Coverage"
+ ```
4. Update the test projects with the latest nightly build version of coverlet
-(https://github.com/coverlet-coverage/coverlet/blob/master/Documentation/ConsumeNightlyBuild.md).
+().
5. Create coverage report for nightly build version by rerunning the tests:
-```
-dotnet test --collect:"XPlat Code Coverage"
-```
-6. Check for differences in the coverage reports.
+ ```shell
+ dotnet test --collect:"XPlat Code Coverage"
+ ```
+6. Check for differences in the coverage reports.
-# How to manually release packages to nuget.org
+## How to manually release packages to nuget.org
This is the steps to release new packages to nuget.org
1. Update projects version in file `version.json` in root of repo (remove `-preview.{height}` and adjust version)
-Do a PR and merge to master.
+ Do a PR and merge to master.
2. Clone repo, **remember to build packages from master and not from your fork or metadata links will point to your forked repo.** . Run `git log -5` from repo root to verify last commit.
3. From new cloned, aligned and versions updated repo root run pack command
- ```
- dotnet pack -c release /p:TF_BUILD=true /p:PublicRelease=true
- ...
- coverlet.console -> D:\git\coverlet\src\coverlet.console\bin\Release\netcoreapp2.2\coverlet.console.dll
- coverlet.console -> D:\git\coverlet\src\coverlet.console\bin\Release\netcoreapp2.2\publish\
- Successfully created package 'D:\git\coverlet\bin\Release\Packages\coverlet.msbuild.2.8.1.nupkg'.
- Successfully created package 'D:\git\coverlet\bin\Release\Packages\coverlet.msbuild.2.8.1.snupkg'.
- Successfully created package 'D:\git\coverlet\bin\Release\Packages\coverlet.console.1.7.1.nupkg'.
- Successfully created package 'D:\git\coverlet\bin\Release\Packages\coverlet.console.1.7.1.snupkg'.
- Successfully created package 'D:\git\coverlet\bin\Release\Packages\coverlet.collector.1.2.1.nupkg'.
- Successfully created package 'D:\git\coverlet\bin\Release\Packages\coverlet.collector.1.2.1.snupkg'.
- ```
-
-4. Sign the packages using SignClient tool https://www.nuget.org/packages/SignClient
-
- ```powershell
- ❯ SignClient "Sign" `
- >> --baseDirectory "REPO ROOT DIRECTORY\bin" `
- >> --input "**/*.nupkg" `
- >> --config "ROOT REPO DIRECTORY\eng\signclient.json" `
- >> --user "USER" `
- >> --secret "SECRET" `
- >> --name "Coverlet" `
- >> --description "Coverlet" `
- >> --descriptionUrl "https://github.com/coverlet-coverage/coverlet"
- ```
+ ```shell
+ dotnet pack -c release /p:TF_BUILD=true /p:PublicRelease=true
+ ...
+ coverlet.console -> D:\git\coverlet\src\coverlet.console\bin\Release\net6.0\coverlet.console.dll
+ coverlet.console -> D:\git\coverlet\src\coverlet.console\bin\Release\net6.0\publish\
+ Successfully created package 'D:\git\coverlet\bin\Release\Packages\coverlet.collector.6.0.1-preview.6.g918cd179e0.nupkg'.
+ Successfully created package 'D:\git\coverlet\bin\Release\Packages\coverlet.collector.6.0.1-preview.6.g918cd179e0.snupkg'.
+ Successfully created package 'D:\git\coverlet\bin\Release\Packages\coverlet.msbuild.6.0.1-preview.6.g918cd179e0.nupkg'.
+ Successfully created package 'D:\git\coverlet\bin\Release\Packages\coverlet.msbuild.6.0.1-preview.6.g918cd179e0.snupkg'.
+ Successfully created package 'D:\git\coverlet\bin\Release\Packages\coverlet.console.6.0.1-preview.6.g918cd179e0.nupkg'.
+ Successfully created package 'D:\git\coverlet\bin\Release\Packages\coverlet.console.6.0.1-preview.6.g918cd179e0.snupkg'.
+ ```
+
+4. Sign the packages using SignClient tool
+
+ ```powershell
+ ❯ SignClient "Sign" `
+ >> --baseDirectory "REPO ROOT DIRECTORY\bin" `
+ >> --input "**/*.nupkg" `
+ >> --config "ROOT REPO DIRECTORY\eng\signclient.json" `
+ >> --user "USER" `
+ >> --secret "SECRET" `
+ >> --name "Coverlet" `
+ >> --description "Coverlet" `
+ >> --descriptionUrl "https://github.com/coverlet-coverage/coverlet"
+ ```
5. Upload *.nupkg files to Nuget.org site. **Check all metadata(url links, deterministic build etc...) before "Submit"**
6. **On your fork**:
- * Align to master
- * Bump version by one (fix part) and re-add `-preview.{height}`
- * Create release on repo https://github.com/coverlet-coverage/coverlet/releases
- * Update the [Release Plan](https://github.com/coverlet-coverage/coverlet/blob/master/Documentation/ReleasePlan.md)(this document) and [ChangeLog](https://github.com/coverlet-coverage/coverlet/blob/master/Documentation/Changelog.md)
- * Do PR and merge
+ * Align to master
+ * Bump version by one (fix part) and re-add `-preview.{height}`
+ * Create release on repo
+ * Update the [Release Plan](https://github.com/coverlet-coverage/coverlet/blob/master/Documentation/ReleasePlan.md)(this document) and [ChangeLog](https://github.com/coverlet-coverage/coverlet/blob/master/Documentation/Changelog.md)
+ * Do PR and merge
diff --git a/Documentation/Roadmap.md b/Documentation/Roadmap.md
index a7ef5117b..6415247af 100644
--- a/Documentation/Roadmap.md
+++ b/Documentation/Roadmap.md
@@ -1,30 +1,30 @@
# Roadmap
-This document describes the roadmap for coverlet showing priorities.
-Maintain coverlet means like any other project two things, answer/resolve soon as possible new issues that are blocking our users an second improve product with new features and enhancements in different areas.
+This document describes the roadmap for coverlet showing priorities.
+Maintain coverlet means like any other project two things, answer/resolve soon as possible new issues that are blocking our users an second improve product with new features and enhancements in different areas.
All coverlet issues are labeled and categorized to better support this activites.
-As soon as an issue is open is labeled with `untriaged` if not immediately solvable(we need to do some debugging/PoC to understand where is the issue).
-After triage a final correct label is applied and will be taken into account depending on priority order.
+As soon as an issue is open is labeled with `untriaged` if not immediately solvable(we need to do some debugging/PoC to understand where is the issue).
+After triage a final correct label is applied and will be taken into account depending on priority order.
We use `needs more info` if we're waiting for answers.
Default priority order "should" be:
1) Bugs: we should fix bugs as soon as possible and for first bugs related to coverage because this is the goal of coverlet.
-Coverage bugs: https://github.com/coverlet-coverage/coverlet/issues?q=is%3Aissue+is%3Aopen+label%3Abug+label%3Atenet-coverage
-Other bugs: https://github.com/coverlet-coverage/coverlet/issues?q=is%3Aissue+is%3Aopen+label%3Abug
+ Coverage bugs:
+ Other bugs:
2) New features: analyze and add new features, we have three drivers so features could be related to one of these.
-Feature requests: https://github.com/coverlet-coverage/coverlet/issues?q=is%3Aissue+is%3Aopen+label%3Afeature-request
+ Feature requests:
3) Performance: we never worked on performance aspect of coverlet, it makes sense for a "new project with some hope", but today coverlet is the facto the dotnet coverage tool, so we HAVE TO approach this aspect.
-Performance issues: https://github.com/coverlet-coverage/coverlet/issues?q=is%3Aissue+is%3Aopen+label%3Atenet-performance
+Performance issues:
-Some new features have got a `Discussion` label if we don't have and agreement yet on semantics.
-Discussions: https://github.com/coverlet-coverage/coverlet/issues?q=is%3Aissue+is%3Aopen+label%3Adiscussion
+Some new features have got a `Discussion` label if we don't have and agreement yet on semantics.
+Discussions:
## New features roadmap
@@ -32,16 +32,14 @@ This is the list of features we should develop soon as possible:
### High priority
-- Allow merge reports solution wide on all flavours https://github.com/coverlet-coverage/coverlet/issues/662 https://github.com/coverlet-coverage/coverlet/issues/357
+- Allow merge reports solution wide on all flavours
-- Some perf improvements https://github.com/coverlet-coverage/coverlet/issues/836
+- Some perf improvements
### Low priority
-- Rethink hits reports strategy https://github.com/coverlet-coverage/coverlet/issues/808
+- Rethink hits reports strategy
## Maintainers discussion channel
[As maintainers we should try to find a way to keep in synch, we could use a chat where we can "take note" of progress and if possible answer to questions/doubt, I know this is OSS, but it's hard keep project at high level without "more ideas".]
-
-
diff --git a/Documentation/Troubleshooting.md b/Documentation/Troubleshooting.md
index f5df25ac8..9592b4af7 100644
--- a/Documentation/Troubleshooting.md
+++ b/Documentation/Troubleshooting.md
@@ -4,39 +4,40 @@
1) Generate verbose log
-```
-dotnet test test\coverlet.core.tests\coverlet.core.tests.csproj -c debug /p:CollectCoverage=true /p:CoverletOutputFormat=opencover /p:Include=[coverlet.*]* -verbosity:diagnostic -bl:msbuild.binlog -noconsolelogger
-```
+ ```shell
+ dotnet test test\coverlet.core.tests\coverlet.core.tests.csproj -c debug /p:CollectCoverage=true /p:CoverletOutputFormat=opencover /p:Include=[coverlet.*]* -verbosity:diagnostic -bl:msbuild.binlog -noconsolelogger
+ ```
-2) Download http://msbuildlog.com/
+2) Download
3) Open `msbuild.binlog` generated and search for '[coverlet]' logs
-
-
+
+ 
## Collectors integration
-```
+```shell
dotnet test --collect:"XPlat Code Coverage" --settings runsettings --diag:log.txt
```
You'll get logs file in same folder similar to
-```
+```text
log.datacollector.19-09-12_14-55-17_64755_5.txt
log.host.19-09-12_14-55-18_82700_6.txt
log.txt
```
+
Search inside with filter '[coverlet]'
## Coverlet Global Tool
-```
+```shell
coverlet "C:\git\coverlet\test\coverlet.core.tests\bin\Debug\netcoreapp2.0\coverlet.core.tests.dll" --target "dotnet" --targetargs "test C:\git\coverlet\test\coverlet.core.tests --no-build" --verbosity detailed
```
Sample output
-```
+```text
...
Instrumented module: 'C:\git\coverlet\test\coverlet.core.tests\bin\Debug\netcoreapp2.0\coverlet.core.dll'
Instrumented module: 'C:\git\coverlet\test\coverlet.core.tests\bin\Debug\netcoreapp2.0\xunit.runner.reporters.netcoreapp10.dll'
@@ -80,116 +81,120 @@ Hits file:'C:\Users\Marco\AppData\Local\Temp\coverlet.core_703263e9-21f0-4d1c-9c
## Use local build (no collectors)
-Sometimes is useful test local updated source to fix issue.
+Sometimes is useful test local updated source to fix issue.
You can "load" your local build using simple switch:
* build repo
-```
-D:\git\coverlet (fixjsonserializerbug -> origin)
-λ dotnet build
-Microsoft (R) Build Engine version 16.1.76+g14b0a930a7 for .NET Core
-Copyright (C) Microsoft Corporation. All rights reserved.
-
- Restore completed in 52.23 ms for D:\git\coverlet\test\coverlet.testsubject\coverlet.testsubject.csproj.
- Restore completed in 58.97 ms for D:\git\coverlet\src\coverlet.console\coverlet.console.csproj.
- Restore completed in 59 ms for D:\git\coverlet\src\coverlet.core\coverlet.core.csproj.
- Restore completed in 59.17 ms for D:\git\coverlet\src\coverlet.msbuild.tasks\coverlet.msbuild.tasks.csproj.
- Restore completed in 59.26 ms for D:\git\coverlet\src\coverlet.collector\coverlet.collector.csproj.
- Restore completed in 60.1 ms for D:\git\coverlet\test\coverlet.collector.tests\coverlet.collector.tests.csproj.
- Restore completed in 60.42 ms for D:\git\coverlet\test\coverlet.core.performancetest\coverlet.core.performancetest.csproj.
- Restore completed in 60.47 ms for D:\git\coverlet\test\coverlet.core.tests\coverlet.core.tests.csproj.
- Restore completed in 22.85 ms for D:\git\coverlet\test\coverlet.core.tests\coverlet.core.tests.csproj.
- coverlet.testsubject -> D:\git\coverlet\test\coverlet.testsubject\bin\Debug\netcoreapp2.0\coverlet.testsubject.dll
- coverlet.core -> D:\git\coverlet\src\coverlet.core\bin\Debug\netstandard2.0\coverlet.core.dll
- coverlet.msbuild.tasks -> D:\git\coverlet\src\coverlet.msbuild.tasks\bin\Debug\netstandard2.0\coverlet.msbuild.tasks.dll
- coverlet.collector -> D:\git\coverlet\src\coverlet.collector\bin\Debug\netcoreapp2.0\coverlet.collector.dll
- coverlet.console -> D:\git\coverlet\src\coverlet.console\bin\Debug\netcoreapp2.2\coverlet.console.dll
- coverlet.core.performancetest -> D:\git\coverlet\test\coverlet.core.performancetest\bin\Debug\netcoreapp2.0\coverlet.core.performancetest.dll
- coverlet.core.tests -> D:\git\coverlet\test\coverlet.core.tests\bin\Debug\netcoreapp2.0\coverlet.core.tests.dll
- coverlet.collector.tests -> D:\git\coverlet\test\coverlet.collector.tests\bin\Debug\netcoreapp2.2\coverlet.collector.tests.dll
-
-Build succeeded.
- 0 Warning(s)
- 0 Error(s)
-
-Time Elapsed 00:00:07.42
-
-D:\git\coverlet (fixjsonserializerbug -> origin)
-```
+ ```text
+ D:\git\coverlet (fixjsonserializerbug -> origin)
+ λ dotnet build
+ Microsoft (R) Build Engine version 16.1.76+g14b0a930a7 for .NET Core
+ Copyright (C) Microsoft Corporation. All rights reserved.
+
+ Restore completed in 52.23 ms for D:\git\coverlet\test\coverlet.testsubject\coverlet.testsubject.csproj.
+ Restore completed in 58.97 ms for D:\git\coverlet\src\coverlet.console\coverlet.console.csproj.
+ Restore completed in 59 ms for D:\git\coverlet\src\coverlet.core\coverlet.core.csproj.
+ Restore completed in 59.17 ms for D:\git\coverlet\src\coverlet.msbuild.tasks\coverlet.msbuild.tasks.csproj.
+ Restore completed in 59.26 ms for D:\git\coverlet\src\coverlet.collector\coverlet.collector.csproj.
+ Restore completed in 60.1 ms for D:\git\coverlet\test\coverlet.collector.tests\coverlet.collector.tests.csproj.
+ Restore completed in 60.42 ms for D:\git\coverlet\test\coverlet.core.performancetest\coverlet.core.performancetest.csproj.
+ Restore completed in 60.47 ms for D:\git\coverlet\test\coverlet.core.tests\coverlet.core.tests.csproj.
+ Restore completed in 22.85 ms for D:\git\coverlet\test\coverlet.core.tests\coverlet.core.tests.csproj.
+ coverlet.testsubject -> D:\git\coverlet\test\coverlet.testsubject\bin\Debug\netcoreapp2.0\coverlet.testsubject.dll
+ coverlet.core -> D:\git\coverlet\src\coverlet.core\bin\Debug\netstandard2.0\coverlet.core.dll
+ coverlet.msbuild.tasks -> D:\git\coverlet\src\coverlet.msbuild.tasks\bin\Debug\netstandard2.0\coverlet.msbuild.tasks.dll
+ coverlet.collector -> D:\git\coverlet\src\coverlet.collector\bin\Debug\netcoreapp2.0\coverlet.collector.dll
+ coverlet.console -> D:\git\coverlet\src\coverlet.console\bin\Debug\netcoreapp2.2\coverlet.console.dll
+ coverlet.core.performancetest -> D:\git\coverlet\test\coverlet.core.performancetest\bin\Debug\netcoreapp2.0\coverlet.core.performancetest.dll
+ coverlet.core.tests -> D:\git\coverlet\test\coverlet.core.tests\bin\Debug\netcoreapp2.0\coverlet.core.tests.dll
+ coverlet.collector.tests -> D:\git\coverlet\test\coverlet.collector.tests\bin\Debug\netcoreapp2.2\coverlet.collector.tests.dll
+
+ Build succeeded.
+ 0 Warning(s)
+ 0 Error(s)
+
+ Time Elapsed 00:00:07.42
+
+ D:\git\coverlet (fixjsonserializerbug -> origin)
+ ```
* Go to repro project and run
-```
-D:\git\Cake.Codecov\Source\Cake.Codecov.Tests (develop -> origin)
-λ dotnet test /p:CollectCoverage=true /p:Exclude="[xunit.*]*" /p:CoverletToolsPath=D:\git\coverlet\src\coverlet.msbuild.tasks\bin\Debug\netstandard2.0\
-Test run for D:\git\Cake.Codecov\Source\Cake.Codecov.Tests\bin\Debug\netcoreapp2.0\Cake.Codecov.Tests.dll(.NETCoreApp,Version=v2.0)
-...
-```
+ ```text
+ D:\git\Cake.Codecov\Source\Cake.Codecov.Tests (develop -> origin)
+ λ dotnet test /p:CollectCoverage=true /p:Exclude="[xunit.*]*" /p:CoverletToolsPath=D:\git\coverlet\src\coverlet.msbuild.tasks\bin\Debug\netstandard2.0\
+ Test run for D:\git\Cake.Codecov\Source\Cake.Codecov.Tests\bin\Debug\netcoreapp2.0\Cake.Codecov.Tests.dll(.NETCoreApp,Version=v2.0)
+ ...
+ ```
In this way you can add `Debug.Launch()` inside coverlet source and debug.
-## Use local collectors build
+## Use local collectors build
To use/debug local collectors build we need to tell to our project to restore and use our local build nuget package.
1) Build local package
-```
-C:\git\coverlet\src\coverlet.collector (master -> origin)
-λ dotnet pack
-Microsoft (R) Build Engine version 16.2.32702+c4012a063 for .NET Core
-Copyright (C) Microsoft Corporation. All rights reserved.
-
- Restore completed in 50,28 ms for C:\git\coverlet\src\coverlet.collector\coverlet.collector.csproj.
- Restore completed in 50,28 ms for C:\git\coverlet\src\coverlet.core\coverlet.core.csproj.
- coverlet.core -> C:\git\coverlet\src\coverlet.core\bin\Debug\netstandard2.0\coverlet.core.dll
- coverlet.collector -> C:\git\coverlet\src\coverlet.collector\bin\Debug\netcoreapp2.0\coverlet.collector.dll
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.collector.1.0.67.nupkg'.
- Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.collector.1.0.67.snupkg'.
-```
+ ```text
+ C:\git\coverlet\src\coverlet.collector (master -> origin)
+ λ dotnet pack
+ Microsoft (R) Build Engine version 16.2.32702+c4012a063 for .NET Core
+ Copyright (C) Microsoft Corporation. All rights reserved.
+
+ Restore completed in 50,28 ms for C:\git\coverlet\src\coverlet.collector\coverlet.collector.csproj.
+ Restore completed in 50,28 ms for C:\git\coverlet\src\coverlet.core\coverlet.core.csproj.
+ coverlet.core -> C:\git\coverlet\src\coverlet.core\bin\Debug\netstandard2.0\coverlet.core.dll
+ coverlet.collector -> C:\git\coverlet\src\coverlet.collector\bin\Debug\netcoreapp2.0\coverlet.collector.dll
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.collector.1.0.67.nupkg'.
+ Successfully created package 'C:\git\coverlet\bin\Debug\Packages\coverlet.collector.1.0.67.snupkg'.
+ ```
+
2) Add new `NuGet.Config` file on your test project/solution
-```
-
-
-
-
-
-
-
-
-
-
-
-```
+
+ ```xml
+
+
+
+
+
+
+
+
+
+
+
+ ```
+
3) Update nuget package in our test project
-```xml
-
-
-
- netcoreapp2.2
- false
-
-
-
-
-
-
- <-- My local package version
-
-
-
-
-
-
-
-```
+
+ ```xml
+
+
+
+ netcoreapp2.2
+ false
+
+
+
+
+
+
+ <-- My local package version
+
+
+
+
+
+
+
+ ```
4) Run test command
-```
- dotnet test XUnitTestProject1\ --collect:"XPlat Code Coverage"
-```
+ ```shell
+ dotnet test XUnitTestProject1\ --collect:"XPlat Code Coverage"
+ ```
You can also attach/debug your code adding some line of code on collectors i.e.
@@ -208,15 +213,15 @@ Fire attach
System.Diagnostics.Debugger.Launch();
```
-If you want debug in-process collector, you need to set VSTEST_HOST_DEBUG(https://github.com/microsoft/vstest/issues/2158) environment variable
+If you want debug in-process collector, you need to set [VSTEST_HOST_DEBUG](https://github.com/microsoft/vstest/issues/2158) environment variable
-```
+```shell
set VSTEST_HOST_DEBUG=1
```
Test host will wait for debugger
-```
+```text
Starting test execution, please wait...
Logging Vstest Diagnostics in file: C:\git\coverletissue\collectorlog\XUnitTestProject1\log.txt
Host debugging is enabled. Please attach debugger to testhost process to continue.
@@ -231,7 +236,7 @@ Coverlet works thanks to ModuleTracker that is injected during instrumentation f
We can collect logs from trackers through an enviroment variable
-```
+```shell
set COVERLET_ENABLETRACKERLOG=1
```
@@ -241,7 +246,7 @@ When enabled, tracking event will be collected in a log file near to module loca
You can live attach and debug msbuild tasks with `COVERLET_MSBUILD_INSTRUMENTATIONTASK_DEBUG` env variable
-```
+```shell
set COVERLET_MSBUILD_INSTRUMENTATIONTASK_DEBUG=1
```
@@ -249,14 +254,14 @@ You can live attach and debug msbuild tasks with `COVERLET_MSBUILD_INSTRUMENTATI
You can live attach and debug collectors with `COVERLET_DATACOLLECTOR_OUTOFPROC_DEBUG` and `COVERLET_DATACOLLECTOR_INPROC_DEBUG` env variable
-```
+```shell
set COVERLET_DATACOLLECTOR_OUTOFPROC_DEBUG=1
set COVERLET_DATACOLLECTOR_INPROC_DEBUG=1
```
-You will be asked to attach a debugger through UI popup.
+You will be asked to attach a debugger through UI popup.
To enable exceptions log for in-process data collectors
-```
+```shell
set COVERLET_DATACOLLECTOR_INPROC_EXCEPTIONLOG_ENABLED=1
```
diff --git a/Documentation/VSTestIntegration.md b/Documentation/VSTestIntegration.md
index 4cc67383d..93018d5f0 100644
--- a/Documentation/VSTestIntegration.md
+++ b/Documentation/VSTestIntegration.md
@@ -2,28 +2,25 @@
**Supported runtime versions**:
-Before version `3.0.0`
-- .NET Core >= 2.0
-- .NET Framework not fully supported(only out of process collector, could suffer of [known issue](KnownIssues.md#1-vstest-stops-process-execution-earlydotnet-test))
+Since version `6.0.0`
-Since version `3.0.0`
-- .NET Core >= 2.0
-- .NET Framework >= 4.6.1
+* .NET Core >= 6.0
+* .NET Framework >= 4.6.2
-As explained in quick start section, to use collectors you need to run *SDK v2.2.401* or newer and your project file must reference `coverlet.collector.dll` and a minimum version of `Microsoft.NET.Test.Sdk`.
+As explained in quick start section, to use collectors you need to run *SDK v6.0.100* (LTS) or newer and your project file must reference `coverlet.collector` and a minimum version of `Microsoft.NET.Test.Sdk`.
A sample project file looks like:
```xml
- netcoreapp3.0;netcoreapp2.1;net46
+ net6.0;net48
-
-
+
+
-
+ allruntime; build; native; contentfiles; analyzers; buildtransitive
@@ -37,13 +34,13 @@ The reference to `coverlet.collector` package is included by default with xunit
With correct reference in place you can run coverage through default dotnet test CLI verbs:
-```
+```shell
dotnet test --collect:"XPlat Code Coverage"
```
or
-```
+```text
dotnet publish
...
... -> C:\project\bin\Debug\netcoreapp3.0\testdll.dll
@@ -56,7 +53,7 @@ As you can see in case of `vstest` verb you **must** publish project before.
At the end of tests you'll find the coverage file data under default VSTest platform directory `TestResults`
-```
+```text
Attachments:
C:\git\coverlet\Documentation\Examples\VSTest\HelloWorld\XUnitTestProject1\TestResults\bc5e983b-d7a8-4f17-8c0a-8a8831a4a891\coverage.cobertura.xml
Test Run Successful.
@@ -66,29 +63,31 @@ Total tests: 1
```
You can change the position of files using standard `dotnet test` switch `[-r|--results-directory]`
-
-*NB: By design VSTest platform will create your file under a random named folder(guid string) so if you need stable path to load file to some gui report system(i.e. coveralls, codecov, reportgenerator etc..) that doesn't support glob patterns or hierarchical search, you'll need to manually move resulting file to a predictable folder*
+>*NB: By design VSTest platform will create your file under a random named folder(guid string) so if you need stable path to load file to some gui report system(i.e. coveralls, codecov, reportgenerator etc..) that doesn't support glob patterns or hierarchical search, you'll need to manually move resulting file to a predictable folder*
## Coverlet options supported by VSTest integration
-At the moment VSTest integration doesn't support all features of msbuild and .NET tool, for instance show result on console, report merging and threshold validation.
-We're working to fill the gaps.
-*PS: if you don't have any other way to merge reports(for instance your report generator doesn't support multi coverage file) you can for the moment exploit a trick reported by one of our contributor Daniel Paz(@p4p3) https://github.com/tonerdo/coverlet/pull/225#issuecomment-573896446*
+:warning:At the moment VSTest integration **doesn't support all features** of msbuild and .NET tool, for instance show result on console, report merging and threshold validation.
+We're working to fill the gaps.
+>*PS: if you don't have any other way to merge reports(for instance your report generator doesn't support multi coverage file) you can for the moment exploit a trick reported by one of our contributor Daniel Paz(@p4p3) *
### Default option (if you don't specify a runsettings file)
Without specifying a runsettings file and calling coverlet by just the name of the collector, the result of the generated coverage output is by default in cobertura format.
-```
+
+```shell
dotnet test --collect:"XPlat Code Coverage"
```
The output format of the coverage report can also be changed without a runsettings file by specifying it in a parameter. The supported formats are lcov, opencover, cobertura, teamcity, json (default coverlet proprietary format).
-```
+
+```shell
dotnet test --collect:"XPlat Code Coverage;Format=json"
```
It is even possible to specify the coverage output in multiple formats.
-```
+
+```shell
dotnet test --collect:"XPlat Code Coverage;Format=json,lcov,cobertura"
```
@@ -98,12 +97,12 @@ These are a list of options that are supported by coverlet. These can be specifi
| Option | Summary |
|:-------------------------|:----------------------------------------------------------------------------------------------------------------------------------------------------------------|
-| Format | Coverage output format. These are either cobertura, json, lcov, opencover or teamcity as well as combinations of these formats. |
-| Exclude | Exclude from code coverage analysing using filter expressions. |
-| ExcludeByFile | Ignore specific source files from code coverage. |
-| Include | Explicitly set what to include in code coverage analysis using filter expressions. |
+| Format | Coverage output format. These are either cobertura, json, lcov, opencover or teamcity as well as combinations of these formats. |
+| Exclude | Exclude from code coverage analysing using filter expressions. |
+| ExcludeByFile | Ignore specific source files from code coverage. |
+| Include | Explicitly set what to include in code coverage analysis using filter expressions. |
| IncludeDirectory | Explicitly set which directories to include in code coverage analysis. |
-| SingleHit | Specifies whether to limit code coverage hit reporting to a single hit for each location. |
+| SingleHit | Specifies whether to limit code coverage hit reporting to a single hit for each location. |
| UseSourceLink | Specifies whether to use SourceLink URIs in place of file system paths. |
| IncludeTestAssembly | Include coverage of the test assembly. |
| SkipAutoProps | Neither track nor record auto-implemented properties. |
@@ -113,14 +112,14 @@ These are a list of options that are supported by coverlet. These can be specifi
How to specify these options via runsettings?
-```
+```xml
- json,cobertura,lcov,teamcity,opencover
+ json,cobertura,lcov,teamcity,opencover[coverlet.*.tests?]*,[*]Coverlet.Core*[coverlet.*]*,[*]Coverlet.Core*Obsolete,GeneratedCodeAttribute,CompilerGeneratedAttribute
@@ -138,13 +137,13 @@ How to specify these options via runsettings?
```
+
Filtering details are present on [msbuild guide](MSBuildIntegration.md#excluding-from-coverage).
This runsettings file can easily be provided using command line option as given :
-1. `dotnet test --collect:"XPlat Code Coverage" --settings coverlet.runsettings`
-
-2. `dotnet vstest C:\project\bin\Debug\netcoreapp3.0\publish\testdll.dll --collect:"XPlat Code Coverage" --settings coverlet.runsettings`
+* `dotnet test --collect:"XPlat Code Coverage" --settings coverlet.runsettings`
+* `dotnet vstest C:\project\bin\Debug\netcoreapp3.0\publish\testdll.dll --collect:"XPlat Code Coverage" --settings coverlet.runsettings`
Take a look at our [`HelloWorld`](Examples/VSTest/HelloWorld/HowTo.md) sample.
@@ -154,20 +153,20 @@ You can avoid passing a `runsettings` file to `dotnet test` driver by using the
For instance if you want to set the `Format` element as a runsettings option you can use this syntax:
-```
+```shell
dotnet test --collect:"XPlat Code Coverage" -- DataCollectionRunSettings.DataCollectors.DataCollector.Configuration.Format=json,cobertura,lcov,teamcity,opencover
```
-Take a look here for further information: https://github.com/microsoft/vstest-docs/blob/master/docs/RunSettingsArguments.md
+Take a look here for further information:
## How it works
-Coverlet integration is implemented with the help of [datacollectors](https://github.com/Microsoft/vstest-docs/blob/master/docs/extensions/datacollector.md).
+Coverlet integration is implemented with the help of [datacollectors](https://github.com/Microsoft/vstest-docs/blob/master/docs/extensions/datacollector.md).
When we specify `--collect:"XPlat Code Coverage"` VSTest platform tries to load coverlet collectors inside `coverlet.collector.dll`
1. Out-of-proc Datacollector: The outproc collector run in a separate process(datacollector.exe/datacollector.dll) than the process in which tests are being executed(testhost*.exe/testhost.dll). This datacollector is responsible for calling into Coverlet APIs for instrumenting dlls, collecting coverage results and sending the coverage output file back to test platform.
-2. In-proc Datacollector: The in-proc collector is loaded in the testhost process executing the tests. This collector will be needed to remove the dependency on the process exit handler to flush the hit files and avoid to hit this [serious known issue](KnownIssues.md#1-vstest-stops-process-execution-earlydotnet-test)
+1. In-proc Datacollector: The in-proc collector is loaded in the testhost process executing the tests. This collector will be needed to remove the dependency on the process exit handler to flush the hit files and avoid to hit this [serious known issue](KnownIssues.md#1-vstest-stops-process-execution-earlydotnet-test)
## Known Issues
diff --git a/README.md b/README.md
index c05a6ec66..3863b4a81 100644
--- a/README.md
+++ b/README.md
@@ -1,16 +1,16 @@
# Coverlet
-[](https://dev.azure.com/tonerdo/coverlet/_build/latest?definitionId=5&branchName=master) [](https://github.com/coverlet-coverage/coverlet/blob/master/LICENSE)
+[](https://dev.azure.com/tonerdo/coverlet/_build/latest?definitionId=5&branchName=master) [](https://github.com/coverlet-coverage/coverlet/blob/master/LICENSE)
| Driver | Current version | Downloads |
|---|---|---|
-| coverlet.collector | [](https://www.nuget.org/packages/coverlet.collector/) | [](https://www.nuget.org/packages/coverlet.collector/)
+| coverlet.collector | [](https://www.nuget.org/packages/coverlet.collector/) | [](https://www.nuget.org/packages/coverlet.collector/)
| coverlet.msbuild | [](https://www.nuget.org/packages/coverlet.msbuild/) | [](https://www.nuget.org/packages/coverlet.msbuild/) |
| coverlet.console | [](https://www.nuget.org/packages/coverlet.console/) | [](https://www.nuget.org/packages/coverlet.console/) |
Coverlet is a cross platform code coverage framework for .NET, with support for line, branch and method coverage. It works with .NET Framework on Windows and .NET Core on all supported platforms.
-**Coverlet documentation reflect the current repository state of the features, not the released ones.**
+**Coverlet documentation reflect the current repository state of the features, not the released ones.**
**Check the [changelog](Documentation/Changelog.md) to understand if the documented feature you want to use has been officially released.**
# Main contents
@@ -28,14 +28,13 @@ Coverlet is a cross platform code coverage framework for .NET, with support for
## Quick Start
-Coverlet can be used through three different *drivers*
+Coverlet can be used through three different *drivers*
* VSTest engine integration
* MSBuild task integration
* As a .NET Global tool (supports standalone integration tests)
-Coverlet supports only SDK-style projects https://docs.microsoft.com/en-us/visualstudio/msbuild/how-to-use-project-sdk?view=vs-2019
-
+Coverlet supports only SDK-style projects https://docs.microsoft.com/en-us/visualstudio/msbuild/how-to-use-project-sdk?view=vs-2019
### VSTest Integration (preferred due to [known issue](https://github.com/coverlet-coverage/coverlet/blob/master/Documentation/KnownIssues.md#1-vstest-stops-process-execution-earlydotnet-test))
@@ -57,10 +56,10 @@ After the above command is run, a `coverage.cobertura.xml` file containing the r
See [documentation](Documentation/VSTestIntegration.md) for advanced usage.
#### Requirements
-* _You need to be running .NET Core SDK v2.2.401 or newer_
-* _You need to reference version 16.5.0 and above of Microsoft.NET.Test.Sdk_
+* _You need to be running .NET 6.0 SDK v6.0.316 or newer_
+* _You need to reference version 17.5.0 and above of Microsoft.NET.Test.Sdk_
```
-
+
```
### MSBuild Integration (suffers of possible [known issue](https://github.com/coverlet-coverage/coverlet/blob/master/Documentation/KnownIssues.md#1-vstest-stops-process-execution-earlydotnet-test))
@@ -69,7 +68,7 @@ See [documentation](Documentation/VSTestIntegration.md) for advanced usage.
```bash
dotnet add package coverlet.msbuild
```
-N.B. You **MUST** add package only to test projects
+N.B. You **MUST** add package only to test projects
### Usage
@@ -111,7 +110,7 @@ See [documentation](Documentation/GlobalTool.md) for advanced usage.
#### Requirements
.NET global tools rely on a .NET Core runtime installed on your machine https://docs.microsoft.com/en-us/dotnet/core/tools/global-tools#what-could-go-wrong
-.NET Coverlet global tool requires _.NET Core 2.2 and above_
+.NET Coverlet global tool requires _.NET Core 2.2 and above_
## How It Works
@@ -131,14 +130,14 @@ Coverlet generates code coverage information by going through the following proc
## Deterministic build support
-Coverlet supports coverage for deterministic builds. The solution at the moment is not optimal and need a workaround.
+Coverlet supports coverage for deterministic builds. The solution at the moment is not optimal and need a workaround.
Take a look at [documentation](Documentation/DeterministicBuild.md).
## Are you in trouble with some feature? Check on [examples](Documentation/Examples.md)!
## Known Issues
-Unfortunately we have some known issues, check it [here](Documentation/KnownIssues.md)
+Unfortunately we have some known issues, check it [here](Documentation/KnownIssues.md)
## Cake Add-In
@@ -166,12 +165,11 @@ If you find a bug or have a feature request, please report them at this reposito
## Coverlet Team
-Author and owner
-* [Toni Solarin-Sodara](https://github.com/tonerdo)
+Author and owner
+* [Toni Solarin-Sodara](https://github.com/tonerdo)
Co-maintainers
-
* [David Müller](https://github.com/daveMueller)
* [Bert](https://github.com/Bertk)
* [Peter Liljenberg](https://github.com/petli)
@@ -190,6 +188,6 @@ Part of the code is based on work done by OpenCover team https://github.com/Open
## License
-This project is licensed under the MIT license. See the [LICENSE](LICENSE) file for more info.
-
+This project is licensed under the MIT license. See the [LICENSE](LICENSE) file for more info.
+
## Supported by the [.NET Foundation](https://dotnetfoundation.org/)
diff --git a/coverlet.sln b/coverlet.sln
index 311b59387..c3392e38d 100644
--- a/coverlet.sln
+++ b/coverlet.sln
@@ -34,6 +34,7 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution
DeterministicBuild.targets = DeterministicBuild.targets
Directory.Build.props = Directory.Build.props
Directory.Build.targets = Directory.Build.targets
+ Directory.Packages.props = Directory.Packages.props
global.json = global.json
EndProjectSection
EndProject
@@ -53,8 +54,6 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Build", "Build", "{9A8B19D4
test\Directory.Build.targets = test\Directory.Build.targets
EndProjectSection
EndProject
-Project("{778DAE3C-4631-46EA-AA77-85C1314464D9}") = "coverlet.tests.projectsample.vbmynamespace", "test\coverlet.tests.projectsample.vbmynamespace\coverlet.tests.projectsample.vbmynamespace.vbproj", "{C9B7DC34-3E04-4F20-AED4-73791AF8020D}"
-EndProject
Project("{6EC3EE1D-3C4E-46DD-8F32-0CC8E7565705}") = "coverlet.tests.projectsample.fsharp", "test\coverlet.tests.projectsample.fsharp\coverlet.tests.projectsample.fsharp.fsproj", "{1CBF6966-2A67-4D2C-8598-D174B83072F4}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "coverlet.tests.projectsample.netframework", "test\coverlet.tests.projectsample.netframework\coverlet.tests.projectsample.netframework.csproj", "{E69D68C9-78ED-4076-A14B-D07295A4B2A5}"
@@ -65,9 +64,9 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "coverlet.tests.projectsampl
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "coverlet.tests.projectsample.wpf6", "test\coverlet.tests.projectsample.wpf6\coverlet.tests.projectsample.wpf6.csproj", "{988A5FF0-4326-4F5B-9F05-CB165543A555}"
EndProject
-Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "coverlet.tests.projectsample.aspmvcrazor", "test\coverlet.tests.projectsample.aspmvcrazor\coverlet.tests.projectsample.aspmvcrazor.csproj", "{6ACF69B1-C01F-44A4-8F8E-2501884238D4}"
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "coverlet.tests.projectsample.aspmvcrazor", "test\coverlet.tests.projectsample.aspmvcrazor\coverlet.tests.projectsample.aspmvcrazor.csproj", "{6ACF69B1-C01F-44A4-8F8E-2501884238D4}"
EndProject
-Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "coverlet.tests.projectsample.aspmvcrazor.tests", "test\coverlet.tests.projectsample.aspmvcrazor.tests\coverlet.tests.projectsample.aspmvcrazor.tests.csproj", "{F508CCDD-5BC8-4AB6-97B3-D37498813C41}"
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "coverlet.tests.projectsample.aspmvcrazor.tests", "test\coverlet.tests.projectsample.aspmvcrazor.tests\coverlet.tests.projectsample.aspmvcrazor.tests.csproj", "{F508CCDD-5BC8-4AB6-97B3-D37498813C41}"
ProjectSection(ProjectDependencies) = postProject
{31084026-D563-4B91-BE71-174C4270CCF4} = {31084026-D563-4B91-BE71-174C4270CCF4}
{6ACF69B1-C01F-44A4-8F8E-2501884238D4} = {6ACF69B1-C01F-44A4-8F8E-2501884238D4}
@@ -135,10 +134,6 @@ Global
{F8199E19-FA9A-4559-9101-CAD7028121B4}.Debug|Any CPU.Build.0 = Debug|Any CPU
{F8199E19-FA9A-4559-9101-CAD7028121B4}.Release|Any CPU.ActiveCfg = Release|Any CPU
{F8199E19-FA9A-4559-9101-CAD7028121B4}.Release|Any CPU.Build.0 = Release|Any CPU
- {C9B7DC34-3E04-4F20-AED4-73791AF8020D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
- {C9B7DC34-3E04-4F20-AED4-73791AF8020D}.Debug|Any CPU.Build.0 = Debug|Any CPU
- {C9B7DC34-3E04-4F20-AED4-73791AF8020D}.Release|Any CPU.ActiveCfg = Release|Any CPU
- {C9B7DC34-3E04-4F20-AED4-73791AF8020D}.Release|Any CPU.Build.0 = Release|Any CPU
{1CBF6966-2A67-4D2C-8598-D174B83072F4}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{1CBF6966-2A67-4D2C-8598-D174B83072F4}.Debug|Any CPU.Build.0 = Debug|Any CPU
{1CBF6966-2A67-4D2C-8598-D174B83072F4}.Release|Any CPU.ActiveCfg = Release|Any CPU
@@ -187,7 +182,6 @@ Global
{5FF404AD-7C0B-465A-A1E9-558CDC642B0C} = {2FEBDE1B-83E3-445B-B9F8-5644B0E0E134}
{F8199E19-FA9A-4559-9101-CAD7028121B4} = {2FEBDE1B-83E3-445B-B9F8-5644B0E0E134}
{9A8B19D4-4A24-4217-AEFE-159B68F029A1} = {2FEBDE1B-83E3-445B-B9F8-5644B0E0E134}
- {C9B7DC34-3E04-4F20-AED4-73791AF8020D} = {2FEBDE1B-83E3-445B-B9F8-5644B0E0E134}
{1CBF6966-2A67-4D2C-8598-D174B83072F4} = {2FEBDE1B-83E3-445B-B9F8-5644B0E0E134}
{E69D68C9-78ED-4076-A14B-D07295A4B2A5} = {2FEBDE1B-83E3-445B-B9F8-5644B0E0E134}
{1C3CA3F8-DF8C-433F-8A56-69102D2BBDF6} = {2FEBDE1B-83E3-445B-B9F8-5644B0E0E134}
diff --git a/eng/azure-pipelines-nightly.yml b/eng/azure-pipelines-nightly.yml
index 502f6065a..60dc036fc 100644
--- a/eng/azure-pipelines-nightly.yml
+++ b/eng/azure-pipelines-nightly.yml
@@ -1,26 +1,16 @@
pool:
- vmImage: 'windows-2019'
+ vmImage: 'windows-latest'
steps:
- task: UseDotNet@2
inputs:
- version: 3.1.404
- displayName: Install .NET Core SDK 3.1.404
+ version: 6.0.413
+ displayName: Install .NET Core SDK 6.0.413
- task: UseDotNet@2
inputs:
- version: 5.0.401
- displayName: Install .NET Core SDK 5.0.401
-
-- task: UseDotNet@2
- inputs:
- version: 6.0.408
- displayName: Install .NET Core SDK 6.0.408
-
-- task: UseDotNet@2
- inputs:
- version: 7.0.203
- displayName: Install .NET Core SDK 7.0.203
+ version: 7.0.400
+ displayName: Install .NET Core SDK 7.0.400
- task: NuGetAuthenticate@0
displayName: Authenticate with NuGet feeds
diff --git a/eng/build.yml b/eng/build.yml
index e4db0b0a6..b2e3a8f34 100644
--- a/eng/build.yml
+++ b/eng/build.yml
@@ -1,23 +1,13 @@
steps:
- task: UseDotNet@2
inputs:
- version: 3.1.404
- displayName: Install .NET Core SDK 3.1.404
+ version: 6.0.413
+ displayName: Install .NET Core SDK 6.0.413
- task: UseDotNet@2
inputs:
- version: 5.0.401
- displayName: Install .NET Core SDK 5.0.401
-
-- task: UseDotNet@2
- inputs:
- version: 6.0.408
- displayName: Install .NET Core SDK 6.0.408
-
-- task: UseDotNet@2
- inputs:
- version: 7.0.203
- displayName: Install .NET Core SDK 7.0.203
+ version: 7.0.400
+ displayName: Install .NET Core SDK 7.0.400
- script: dotnet restore
displayName: Restore packages
@@ -34,3 +24,11 @@ steps:
command: test
arguments: -c $(BuildConfiguration) --no-build /p:CollectCoverage=true /p:CoverletOutputFormat=opencover /p:Include="[coverlet.collector]*%2c[coverlet.core]*%2c[coverlet.msbuild.tasks]*" /p:Exclude="[coverlet.core.tests.samples.netstandard]*%2c[coverlet.tests.xunit.extensions]*"
testRunTitle: $(Agent.JobName)
+
+- template: publish-coverlet-result-files.yml
+
+#- template: publish-coverage-results.yml
+# parameters:
+# reports: $(Build.SourcesDirectory)/**/coverage.opencover.xml
+# condition: and(succeeded(), eq(variables['_BuildConfig'], 'Debug'))
+# assemblyfilters: '-xunit*;+Coverlet.Core.*;+Coverlet.Collector.*'
diff --git a/eng/publish-coverage-results.yml b/eng/publish-coverage-results.yml
new file mode 100644
index 000000000..41f34a089
--- /dev/null
+++ b/eng/publish-coverage-results.yml
@@ -0,0 +1,32 @@
+# File: publish-coverage-results.yml
+# uses reportgenerator task to create a code coverage report and aggregates available cobertura XML files. The results are publishes as a build artifact.
+
+parameters:
+ condition: 'succeeded()'
+ reports: ''
+ assemblyfilters: '-xunit*'
+ breakBuild: false
+
+steps:
+- task: reportgenerator@5
+ displayName: ReportGenerator
+ condition: ${{parameters.condition}}
+ inputs:
+ reports: ${{parameters.reports}}
+ targetdir: $(Build.SourcesDirectory)/artifacts/CoverageReport
+ reporttypes: Html;HtmlInline_AzurePipelines_Dark;Cobertura
+ verbosity: 'Verbose'
+ assemblyfilters: ${{parameters.assemblyfilters}}
+
+- publish: '$(Build.SourcesDirectory)/artifacts/CoverageReport'
+ displayName: 'Publish CoverageReport Artifact'
+ artifact: CoverageResults_$(Agent.Os)_$(BuildConfiguration)
+ condition: ${{parameters.condition}}
+
+- task: PublishCodeCoverageResults@1
+ displayName: 'Publish code coverage'
+ condition: ${{parameters.condition}}
+ inputs:
+ codeCoverageTool: Cobertura
+ summaryFileLocation: '$(Build.SourcesDirectory)/artifacts/CoverageReport/Cobertura.xml'
+ failIfCoverageEmpty: ${{parameters.breakBuild}}
diff --git a/eng/publish-coverlet-result-files.yml b/eng/publish-coverlet-result-files.yml
new file mode 100644
index 000000000..5f781e96b
--- /dev/null
+++ b/eng/publish-coverlet-result-files.yml
@@ -0,0 +1,35 @@
+steps:
+- task: Powershell@2
+ displayName: Prepare coverage files to Upload
+ inputs:
+ targetType: inline
+ pwsh: true
+ script: |
+ New-Item -ItemType Directory "$(Build.SourcesDirectory)/artifacts/TestLogs/"
+ function Copy-FileKeepPath {
+ param (
+ $Filter,$FileToCopy,$Destination,$StartIndex
+ )
+ Get-ChildItem -Path $FileToCopy -Filter $Filter -Recurse -File | ForEach-Object {
+ $fileName = $_.FullName
+ $newDestination=Join-Path -Path $Destination -ChildPath $fileName.Substring($StartIndex)
+ $folder=Split-Path -Path $newDestination -Parent
+ if (!(Test-Path -Path $folder)) {New-Item $folder -Type Directory -Force -Verbose}
+ Copy-Item -Path $fileName -Destination $newDestination -Recurse -Force -Verbose
+ }
+ }
+ $logfiles = "coverage.opencover.xml", "coverage.cobertura.xml", "coverage.json", "log.txt", "log.datacollector.*.txt", "log.host.*.txt"
+ foreach ($logfile in $logfiles ) {
+ Copy-FileKeepPath -FileToCopy "$(Build.SourcesDirectory)/test/*" -des "$(Build.SourcesDirectory)/artifacts/TestLogs/" -filter $logfile -startIndex "$(Build.SourcesDirectory)/test/coverlet.integration.tests/bin/".Length
+ }
+
+ continueOnError: true
+ condition: always()
+
+- task: PublishPipelineArtifact@1
+ displayName: Publish coverage logs
+ continueOnError: true
+ condition: always()
+ inputs:
+ path: artifacts/TestLogs
+ artifactName: TestLogs_$(Agent.Os)_$(BuildConfiguration)
diff --git a/global.json b/global.json
index ccc54128c..06ce1b485 100644
--- a/global.json
+++ b/global.json
@@ -1,6 +1,5 @@
{
"sdk": {
- "version": "6.0.410",
- "rollForward": "latestMajor"
+ "version": "7.0.400"
}
}
diff --git a/src/coverlet.collector/build/netstandard1.0/coverlet.collector.targets b/src/coverlet.collector/build/netstandard2.0/coverlet.collector.targets
similarity index 98%
rename from src/coverlet.collector/build/netstandard1.0/coverlet.collector.targets
rename to src/coverlet.collector/build/netstandard2.0/coverlet.collector.targets
index 7bd7b28e7..8c189b6ab 100644
--- a/src/coverlet.collector/build/netstandard1.0/coverlet.collector.targets
+++ b/src/coverlet.collector/build/netstandard2.0/coverlet.collector.targets
@@ -26,7 +26,7 @@ WARNING: DO NOT MODIFY this file unless you are knowledgeable about MSBuild and
<_CoverletSdkNETCoreSdkVersion>$(NETCoreSdkVersion)
<_CoverletSdkNETCoreSdkVersion Condition="$(_CoverletSdkNETCoreSdkVersion.Contains('-'))">$(_CoverletSdkNETCoreSdkVersion.Split('-')[0])
- <_CoverletSdkMinVersionWithDependencyTarget>3.1.300
+ <_CoverletSdkMinVersionWithDependencyTarget>6.0.100
<_CoverletSourceRootTargetName>CoverletGetPathMap
<_CoverletSourceRootTargetName Condition="'$([System.Version]::Parse($(_CoverletSdkNETCoreSdkVersion)).CompareTo($([System.Version]::Parse($(_CoverletSdkMinVersionWithDependencyTarget)))))' >= '0' ">InitializeSourceRootMappedPaths
diff --git a/src/coverlet.collector/coverlet.collector.csproj b/src/coverlet.collector/coverlet.collector.csproj
index bdae19ae6..1459d5e69 100644
--- a/src/coverlet.collector/coverlet.collector.csproj
+++ b/src/coverlet.collector/coverlet.collector.csproj
@@ -5,10 +5,10 @@
truetruefalse
-
true
@@ -29,6 +29,8 @@
falseCoverlet is a cross platform code coverage library for .NET, with support for line, branch and method coverage.coverage testing unit-test lcov opencover quality
+ VSTestIntegration.md
+ https://github.com/coverlet-coverage/coverlet/blob/master/Documentation/Changelog.mdgit
@@ -39,6 +41,9 @@
+
+ true
+
@@ -79,9 +84,9 @@
-
-
-
+
+
+
diff --git a/src/coverlet.core/coverlet.core.csproj b/src/coverlet.core/coverlet.core.csproj
index 34b6b5777..2a84b0b92 100644
--- a/src/coverlet.core/coverlet.core.csproj
+++ b/src/coverlet.core/coverlet.core.csproj
@@ -7,12 +7,13 @@
-
-
-
+
+
+
+
diff --git a/src/coverlet.msbuild.tasks/coverlet.msbuild.targets b/src/coverlet.msbuild.tasks/coverlet.msbuild.targets
index ed288de59..6a12b2fc3 100644
--- a/src/coverlet.msbuild.tasks/coverlet.msbuild.targets
+++ b/src/coverlet.msbuild.tasks/coverlet.msbuild.targets
@@ -6,7 +6,7 @@
<_CoverletSdkNETCoreSdkVersion>$(NETCoreSdkVersion)
<_CoverletSdkNETCoreSdkVersion Condition="$(_CoverletSdkNETCoreSdkVersion.Contains('-'))">$(_CoverletSdkNETCoreSdkVersion.Split('-')[0])
- <_CoverletSdkMinVersionWithDependencyTarget>3.1.300
+ <_CoverletSdkMinVersionWithDependencyTarget>6.0.100
<_CoverletSourceRootTargetName>CoverletGetPathMap
<_CoverletSourceRootTargetName Condition="'$([System.Version]::Parse($(_CoverletSdkNETCoreSdkVersion)).CompareTo($([System.Version]::Parse($(_CoverletSdkMinVersionWithDependencyTarget)))))' >= '0' ">InitializeSourceRootMappedPaths
diff --git a/src/coverlet.msbuild.tasks/coverlet.msbuild.tasks.csproj b/src/coverlet.msbuild.tasks/coverlet.msbuild.tasks.csproj
index 0dbef0361..74fc19631 100644
--- a/src/coverlet.msbuild.tasks/coverlet.msbuild.tasks.csproj
+++ b/src/coverlet.msbuild.tasks/coverlet.msbuild.tasks.csproj
@@ -8,10 +8,10 @@
$(TargetsForTfmSpecificContentInPackage);PackBuildOutputsbuildfalse
-
true
@@ -30,6 +30,8 @@
trueCoverlet is a cross platform code coverage library for .NET, with support for line, branch and method coverage.coverage testing unit-test lcov opencover quality
+ MSBuildIntegration.md
+ https://github.com/coverlet-coverage/coverlet/blob/master/Documentation/Changelog.mdgit
@@ -48,10 +50,14 @@
+
+
+ true
+
diff --git a/test/coverlet.core.tests.samples.netstandard/coverlet.core.tests.samples.netstandard.csproj b/test/coverlet.core.tests.samples.netstandard/coverlet.core.tests.samples.netstandard.csproj
index 783e0d0c3..9f753d759 100644
--- a/test/coverlet.core.tests.samples.netstandard/coverlet.core.tests.samples.netstandard.csproj
+++ b/test/coverlet.core.tests.samples.netstandard/coverlet.core.tests.samples.netstandard.csproj
@@ -6,7 +6,7 @@
-
+
diff --git a/test/coverlet.core.tests/Helpers/InstrumentationHelperTests.cs b/test/coverlet.core.tests/Helpers/InstrumentationHelperTests.cs
index 71d88bfb8..3ea04b5b3 100644
--- a/test/coverlet.core.tests/Helpers/InstrumentationHelperTests.cs
+++ b/test/coverlet.core.tests/Helpers/InstrumentationHelperTests.cs
@@ -36,7 +36,7 @@ public void TestGetDependenciesWithTestAssembly()
[Fact]
public void EmbeddedPortablePDPHasLocalSource_NoDocumentsExist_ReturnsFalse()
{
- var fileSystem = new Mock {CallBase = true};
+ var fileSystem = new Mock { CallBase = true };
fileSystem.Setup(x => x.Exists(It.IsAny())).Returns(false);
var instrumentationHelper =
@@ -70,7 +70,7 @@ public void EmbeddedPortablePDPHasLocalSource_FirstDocumentDoesNotExist_ReturnsE
var instrumentationHelper =
new InstrumentationHelper(new ProcessExitHandler(), new RetryHelper(), fileSystem.Object, new Mock().Object, new SourceRootTranslator(typeof(InstrumentationHelperTests).Assembly.Location, new Mock().Object, new FileSystem(), new AssemblyAdapter()));
- Assert.Equal(result, instrumentationHelper.PortablePdbHasLocalSource(typeof(InstrumentationHelperTests).Assembly.Location, (AssemblySearchType) assemblySearchType));
+ Assert.Equal(result, instrumentationHelper.PortablePdbHasLocalSource(typeof(InstrumentationHelperTests).Assembly.Location, (AssemblySearchType)assemblySearchType));
}
[Fact]
diff --git a/test/coverlet.core.tests/Instrumentation/InstrumenterTests.cs b/test/coverlet.core.tests/Instrumentation/InstrumenterTests.cs
index ef5065f55..2060da38d 100644
--- a/test/coverlet.core.tests/Instrumentation/InstrumenterTests.cs
+++ b/test/coverlet.core.tests/Instrumentation/InstrumenterTests.cs
@@ -1,4 +1,4 @@
-// Copyright (c) Toni Solarin-Sodara
+// Copyright (c) Toni Solarin-Sodara
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
using System;
@@ -7,363 +7,361 @@
using System.Linq;
using System.Reflection;
using System.Runtime.InteropServices;
-using Coverlet.Core.Helpers;
using Coverlet.Core.Abstractions;
+using Coverlet.Core.Helpers;
using Coverlet.Core.Samples.Tests;
using Coverlet.Core.Symbols;
-using Coverlet.Tests.Xunit.Extensions;
+using Coverlet.Core.Tests;
using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.CSharp;
using Microsoft.CodeAnalysis.Emit;
+using Microsoft.VisualStudio.TestPlatform;
using Mono.Cecil;
using Moq;
using Xunit;
-using Microsoft.Extensions.DependencyModel;
-using Microsoft.VisualStudio.TestPlatform;
-using Coverlet.Core.Tests;
namespace Coverlet.Core.Instrumentation.Tests
{
- public class InstrumenterTests : IDisposable
- {
- private readonly Mock _mockLogger = new();
- private Action _disposeAction;
+ public class InstrumenterTests : IDisposable
+ {
+ private readonly Mock _mockLogger = new();
+ private Action _disposeAction;
- public void Dispose()
- {
- _disposeAction?.Invoke();
- }
+ public void Dispose()
+ {
+ _disposeAction?.Invoke();
+ }
- [Fact]
- public void TestCoreLibInstrumentation()
- {
- DirectoryInfo directory = Directory.CreateDirectory(Path.Combine(Directory.GetCurrentDirectory(), nameof(TestCoreLibInstrumentation)));
- string[] files = new[]
- {
+ [Fact]
+ public void TestCoreLibInstrumentation()
+ {
+ DirectoryInfo directory = Directory.CreateDirectory(Path.Combine(Directory.GetCurrentDirectory(), nameof(TestCoreLibInstrumentation)));
+ string[] files = new[]
+ {
"System.Private.CoreLib.dll",
"System.Private.CoreLib.pdb"
};
- foreach (string file in files)
- {
- File.Copy(Path.Combine(Directory.GetCurrentDirectory(), "TestAssets", file), Path.Combine(directory.FullName, file), overwrite: true);
- }
+ foreach (string file in files)
+ {
+ File.Copy(Path.Combine(Directory.GetCurrentDirectory(), "TestAssets", file), Path.Combine(directory.FullName, file), overwrite: true);
+ }
- var partialMockFileSystem = new Mock();
- partialMockFileSystem.CallBase = true;
- partialMockFileSystem.Setup(fs => fs.OpenRead(It.IsAny())).Returns((string path) =>
- {
- if (Path.GetFileName(path.Replace(@"\", @"/")) == files[1])
- {
- return File.OpenRead(Path.Combine(Path.Combine(Directory.GetCurrentDirectory(), "TestAssets"), files[1]));
- }
- else
- {
- return File.OpenRead(path);
- }
- });
- partialMockFileSystem.Setup(fs => fs.Exists(It.IsAny())).Returns((string path) =>
- {
- if (Path.GetFileName(path.Replace(@"\", @"/")) == files[1])
- {
- return File.Exists(Path.Combine(Path.Combine(Directory.GetCurrentDirectory(), "TestAssets"), files[1]));
- }
- else
- {
- if (path.Contains(@":\git\runtime"))
- {
- return true;
- }
- else
- {
- return File.Exists(path);
- }
- }
- });
- var sourceRootTranslator = new SourceRootTranslator(_mockLogger.Object, new FileSystem());
- var parameters = new CoverageParameters();
- var instrumentationHelper =
- new InstrumentationHelper(new ProcessExitHandler(), new RetryHelper(), partialMockFileSystem.Object, _mockLogger.Object, sourceRootTranslator);
- var instrumenter = new Instrumenter(Path.Combine(directory.FullName, files[0]), "_coverlet_instrumented", parameters, _mockLogger.Object, instrumentationHelper, partialMockFileSystem.Object, sourceRootTranslator, new CecilSymbolHelper());
-
- Assert.True(instrumenter.CanInstrument());
- InstrumenterResult result = instrumenter.Instrument();
- Assert.NotNull(result);
- Assert.Equal(1052, result.Documents.Count);
- foreach ((string docName, Document _) in result.Documents)
- {
- Assert.False(docName.EndsWith(@"System.Private.CoreLib\src\System\Threading\Interlocked.cs"));
- }
- directory.Delete(true);
+ var partialMockFileSystem = new Mock();
+ partialMockFileSystem.CallBase = true;
+ partialMockFileSystem.Setup(fs => fs.OpenRead(It.IsAny())).Returns((string path) =>
+ {
+ if (Path.GetFileName(path.Replace(@"\", @"/")) == files[1])
+ {
+ return File.OpenRead(Path.Combine(Path.Combine(Directory.GetCurrentDirectory(), "TestAssets"), files[1]));
}
-
- [Theory]
- [InlineData(true)]
- [InlineData(false)]
- public void TestInstrument(bool singleHit)
+ else
{
- InstrumenterTest instrumenterTest = CreateInstrumentor(singleHit: singleHit);
-
- InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
-
- Assert.Equal(Path.GetFileNameWithoutExtension(instrumenterTest.Module), result.Module);
- Assert.Equal(instrumenterTest.Module, result.ModulePath);
-
- instrumenterTest.Directory.Delete(true);
+ return File.OpenRead(path);
}
-
- [Theory]
- [InlineData(true)]
- [InlineData(false)]
- public void TestInstrumentCoreLib(bool singleHit)
+ });
+ partialMockFileSystem.Setup(fs => fs.Exists(It.IsAny())).Returns((string path) =>
+ {
+ if (Path.GetFileName(path.Replace(@"\", @"/")) == files[1])
{
- InstrumenterTest instrumenterTest = CreateInstrumentor(fakeCoreLibModule: true, singleHit: singleHit);
-
- InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
-
- Assert.Equal(Path.GetFileNameWithoutExtension(instrumenterTest.Module), result.Module);
- Assert.Equal(instrumenterTest.Module, result.ModulePath);
-
- instrumenterTest.Directory.Delete(true);
+ return File.Exists(Path.Combine(Path.Combine(Directory.GetCurrentDirectory(), "TestAssets"), files[1]));
}
-
- [Theory]
- [InlineData(typeof(ClassExcludedByCodeAnalysisCodeCoverageAttr))]
- [InlineData(typeof(ClassExcludedByCoverletCodeCoverageAttr))]
- public void TestInstrument_ClassesWithExcludeAttributeAreExcluded(Type excludedType)
+ else
{
- InstrumenterTest instrumenterTest = CreateInstrumentor();
- InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
+ if (path.Contains(@":\git\runtime"))
+ {
+ return true;
+ }
+ else
+ {
+ return File.Exists(path);
+ }
+ }
+ });
+ var sourceRootTranslator = new SourceRootTranslator(_mockLogger.Object, new FileSystem());
+ var parameters = new CoverageParameters();
+ var instrumentationHelper =
+ new InstrumentationHelper(new ProcessExitHandler(), new RetryHelper(), partialMockFileSystem.Object, _mockLogger.Object, sourceRootTranslator);
+ var instrumenter = new Instrumenter(Path.Combine(directory.FullName, files[0]), "_coverlet_instrumented", parameters, _mockLogger.Object, instrumentationHelper, partialMockFileSystem.Object, sourceRootTranslator, new CecilSymbolHelper());
+
+ Assert.True(instrumenter.CanInstrument());
+ InstrumenterResult result = instrumenter.Instrument();
+ Assert.NotNull(result);
+ Assert.Equal(1052, result.Documents.Count);
+ foreach ((string docName, Document _) in result.Documents)
+ {
+ Assert.False(docName.EndsWith(@"System.Private.CoreLib\src\System\Threading\Interlocked.cs"));
+ }
+ directory.Delete(true);
+ }
- Document doc = result.Documents.Values.FirstOrDefault(d => Path.GetFileName(d.Path) == "Samples.cs");
- Assert.NotNull(doc);
+ [Theory]
+ [InlineData(true)]
+ [InlineData(false)]
+ public void TestInstrument(bool singleHit)
+ {
+ InstrumenterTest instrumenterTest = CreateInstrumentor(singleHit: singleHit);
- bool found = doc.Lines.Values.Any(l => l.Class == excludedType.FullName);
- Assert.False(found, "Class decorated with with exclude attribute should be excluded");
+ InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
- instrumenterTest.Directory.Delete(true);
- }
+ Assert.Equal(Path.GetFileNameWithoutExtension(instrumenterTest.Module), result.Module);
+ Assert.Equal(instrumenterTest.Module, result.ModulePath);
- [Theory]
- [InlineData(typeof(ClassExcludedByAttrWithoutAttributeNameSuffix), nameof(TestSDKAutoGeneratedCode))]
- public void TestInstrument_ClassesWithExcludeAttributeWithoutAttributeNameSuffixAreExcluded(Type excludedType, string excludedAttribute)
- {
- InstrumenterTest instrumenterTest = CreateInstrumentor(attributesToIgnore: new string[] { excludedAttribute });
- InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
+ instrumenterTest.Directory.Delete(true);
+ }
- Document doc = result.Documents.Values.FirstOrDefault(d => Path.GetFileName(d.Path) == "Samples.cs");
- Assert.NotNull(doc);
+ [Theory]
+ [InlineData(true)]
+ [InlineData(false)]
+ public void TestInstrumentCoreLib(bool singleHit)
+ {
+ InstrumenterTest instrumenterTest = CreateInstrumentor(fakeCoreLibModule: true, singleHit: singleHit);
- bool found = doc.Lines.Values.Any(l => l.Class == excludedType.FullName);
- Assert.False(found, "Class decorated with with exclude attribute should be excluded");
+ InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
- instrumenterTest.Directory.Delete(true);
- }
+ Assert.Equal(Path.GetFileNameWithoutExtension(instrumenterTest.Module), result.Module);
+ Assert.Equal(instrumenterTest.Module, result.ModulePath);
- [Theory]
- [InlineData(nameof(ObsoleteAttribute))]
- [InlineData("Obsolete")]
- [InlineData(nameof(TestSDKAutoGeneratedCode))]
- public void TestInstrument_ClassesWithCustomExcludeAttributeAreExcluded(string excludedAttribute)
- {
- InstrumenterTest instrumenterTest = CreateInstrumentor(attributesToIgnore: new string[] { excludedAttribute });
- InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
+ instrumenterTest.Directory.Delete(true);
+ }
- Document doc = result.Documents.Values.FirstOrDefault(d => Path.GetFileName(d.Path) == "Samples.cs");
- Assert.NotNull(doc);
-#pragma warning disable CS0612 // Type or member is obsolete
- bool found = doc.Lines.Values.Any(l => l.Class.Equals(nameof(ClassExcludedByObsoleteAttr)));
-#pragma warning restore CS0612 // Type or member is obsolete
- Assert.False(found, "Class decorated with with exclude attribute should be excluded");
+ [Theory]
+ [InlineData(typeof(ClassExcludedByCodeAnalysisCodeCoverageAttr))]
+ [InlineData(typeof(ClassExcludedByCoverletCodeCoverageAttr))]
+ public void TestInstrument_ClassesWithExcludeAttributeAreExcluded(Type excludedType)
+ {
+ InstrumenterTest instrumenterTest = CreateInstrumentor();
+ InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
- instrumenterTest.Directory.Delete(true);
- }
+ Document doc = result.Documents.Values.FirstOrDefault(d => Path.GetFileName(d.Path) == "Samples.cs");
+ Assert.NotNull(doc);
- [Theory]
- [InlineData(nameof(ObsoleteAttribute), "ClassWithMethodExcludedByObsoleteAttr")]
- [InlineData("Obsolete", "ClassWithMethodExcludedByObsoleteAttr")]
- [InlineData(nameof(TestSDKAutoGeneratedCode), "ClassExcludedByAttrWithoutAttributeNameSuffix")]
- public void TestInstrument_ClassesWithMethodWithCustomExcludeAttributeAreExcluded(string excludedAttribute, string testClassName)
- {
- InstrumenterTest instrumenterTest = CreateInstrumentor(attributesToIgnore: new string[] { excludedAttribute });
- InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
+ bool found = doc.Lines.Values.Any(l => l.Class == excludedType.FullName);
+ Assert.False(found, "Class decorated with with exclude attribute should be excluded");
- Document doc = result.Documents.Values.FirstOrDefault(d => Path.GetFileName(d.Path) == "Samples.cs");
- Assert.NotNull(doc);
- bool found = doc.Lines.Values.Any(l => l.Method.Equals($"System.String Coverlet.Core.Samples.Tests.{testClassName}::Method(System.String)"));
- Assert.False(found, "Method decorated with with exclude attribute should be excluded");
+ instrumenterTest.Directory.Delete(true);
+ }
- instrumenterTest.Directory.Delete(true);
- }
+ [Theory]
+ [InlineData(typeof(ClassExcludedByAttrWithoutAttributeNameSuffix), nameof(TestSDKAutoGeneratedCode))]
+ public void TestInstrument_ClassesWithExcludeAttributeWithoutAttributeNameSuffixAreExcluded(Type excludedType, string excludedAttribute)
+ {
+ InstrumenterTest instrumenterTest = CreateInstrumentor(attributesToIgnore: new string[] { excludedAttribute });
+ InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
- [Theory]
- [InlineData(nameof(ObsoleteAttribute), "ClassWithMethodExcludedByObsoleteAttr")]
- [InlineData("Obsolete", "ClassWithMethodExcludedByObsoleteAttr")]
- [InlineData(nameof(TestSDKAutoGeneratedCode), "ClassExcludedByAttrWithoutAttributeNameSuffix")]
- public void TestInstrument_ClassesWithPropertyWithCustomExcludeAttributeAreExcluded(string excludedAttribute, string testClassName)
- {
- InstrumenterTest instrumenterTest = CreateInstrumentor(attributesToIgnore: new string[] { excludedAttribute });
- InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
+ Document doc = result.Documents.Values.FirstOrDefault(d => Path.GetFileName(d.Path) == "Samples.cs");
+ Assert.NotNull(doc);
- Document doc = result.Documents.Values.FirstOrDefault(d => Path.GetFileName(d.Path) == "Samples.cs");
- Assert.NotNull(doc);
- bool getFound = doc.Lines.Values.Any(l => l.Method.Equals($"System.String Coverlet.Core.Samples.Tests.{testClassName}::get_Property()"));
- Assert.False(getFound, "Property getter decorated with with exclude attribute should be excluded");
+ bool found = doc.Lines.Values.Any(l => l.Class == excludedType.FullName);
+ Assert.False(found, "Class decorated with with exclude attribute should be excluded");
- bool setFound = doc.Lines.Values.Any(l => l.Method.Equals($"System.String Coverlet.Core.Samples.Tests.{testClassName}::set_Property()"));
- Assert.False(setFound, "Property setter decorated with with exclude attribute should be excluded");
+ instrumenterTest.Directory.Delete(true);
+ }
- instrumenterTest.Directory.Delete(true);
- }
+ [Theory]
+ [InlineData(nameof(ObsoleteAttribute))]
+ [InlineData("Obsolete")]
+ [InlineData(nameof(TestSDKAutoGeneratedCode))]
+ public void TestInstrument_ClassesWithCustomExcludeAttributeAreExcluded(string excludedAttribute)
+ {
+ InstrumenterTest instrumenterTest = CreateInstrumentor(attributesToIgnore: new string[] { excludedAttribute });
+ InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
- private InstrumenterTest CreateInstrumentor(bool fakeCoreLibModule = false, string[] attributesToIgnore = null, string[] excludedFiles = null, bool singleHit = false)
- {
- string module = GetType().Assembly.Location;
- string pdb = Path.Combine(Path.GetDirectoryName(module), Path.GetFileNameWithoutExtension(module) + ".pdb");
- string identifier = Guid.NewGuid().ToString();
+ Document doc = result.Documents.Values.FirstOrDefault(d => Path.GetFileName(d.Path) == "Samples.cs");
+ Assert.NotNull(doc);
+#pragma warning disable CS0612 // Type or member is obsolete
+ bool found = doc.Lines.Values.Any(l => l.Class.Equals(nameof(ClassExcludedByObsoleteAttr)));
+#pragma warning restore CS0612 // Type or member is obsolete
+ Assert.False(found, "Class decorated with with exclude attribute should be excluded");
- DirectoryInfo directory = Directory.CreateDirectory(Path.Combine(Path.GetTempPath(), identifier));
+ instrumenterTest.Directory.Delete(true);
+ }
- string destModule, destPdb;
- if (fakeCoreLibModule)
- {
- destModule = "System.Private.CoreLib.dll";
- destPdb = "System.Private.CoreLib.pdb";
- }
- else
- {
- destModule = Path.GetFileName(module);
- destPdb = Path.GetFileName(pdb);
- }
+ [Theory]
+ [InlineData(nameof(ObsoleteAttribute), "ClassWithMethodExcludedByObsoleteAttr")]
+ [InlineData("Obsolete", "ClassWithMethodExcludedByObsoleteAttr")]
+ [InlineData(nameof(TestSDKAutoGeneratedCode), "ClassExcludedByAttrWithoutAttributeNameSuffix")]
+ public void TestInstrument_ClassesWithMethodWithCustomExcludeAttributeAreExcluded(string excludedAttribute, string testClassName)
+ {
+ InstrumenterTest instrumenterTest = CreateInstrumentor(attributesToIgnore: new string[] { excludedAttribute });
+ InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
- File.Copy(module, Path.Combine(directory.FullName, destModule), true);
- File.Copy(pdb, Path.Combine(directory.FullName, destPdb), true);
+ Document doc = result.Documents.Values.FirstOrDefault(d => Path.GetFileName(d.Path) == "Samples.cs");
+ Assert.NotNull(doc);
+ bool found = doc.Lines.Values.Any(l => l.Method.Equals($"System.String Coverlet.Core.Samples.Tests.{testClassName}::Method(System.String)"));
+ Assert.False(found, "Method decorated with with exclude attribute should be excluded");
- var instrumentationHelper =
- new InstrumentationHelper(new ProcessExitHandler(), new RetryHelper(), new FileSystem(), new Mock().Object, new SourceRootTranslator(new Mock().Object, new FileSystem()));
+ instrumenterTest.Directory.Delete(true);
+ }
- module = Path.Combine(directory.FullName, destModule);
- CoverageParameters parameters = new()
- {
- ExcludeAttributes = attributesToIgnore,
- DoesNotReturnAttributes = new string[] { "DoesNotReturnAttribute" }
- };
- var instrumenter = new Instrumenter(module, identifier, parameters, _mockLogger.Object, instrumentationHelper, new FileSystem(), new SourceRootTranslator(_mockLogger.Object, new FileSystem()), new CecilSymbolHelper());
- return new InstrumenterTest
- {
- Instrumenter = instrumenter,
- Module = module,
- Identifier = identifier,
- Directory = directory
- };
- }
+ [Theory]
+ [InlineData(nameof(ObsoleteAttribute), "ClassWithMethodExcludedByObsoleteAttr")]
+ [InlineData("Obsolete", "ClassWithMethodExcludedByObsoleteAttr")]
+ [InlineData(nameof(TestSDKAutoGeneratedCode), "ClassExcludedByAttrWithoutAttributeNameSuffix")]
+ public void TestInstrument_ClassesWithPropertyWithCustomExcludeAttributeAreExcluded(string excludedAttribute, string testClassName)
+ {
+ InstrumenterTest instrumenterTest = CreateInstrumentor(attributesToIgnore: new string[] { excludedAttribute });
+ InstrumenterResult result = instrumenterTest.Instrumenter.Instrument();
- class InstrumenterTest
- {
- public Instrumenter Instrumenter { get; set; }
+ Document doc = result.Documents.Values.FirstOrDefault(d => Path.GetFileName(d.Path) == "Samples.cs");
+ Assert.NotNull(doc);
+ bool getFound = doc.Lines.Values.Any(l => l.Method.Equals($"System.String Coverlet.Core.Samples.Tests.{testClassName}::get_Property()"));
+ Assert.False(getFound, "Property getter decorated with with exclude attribute should be excluded");
- public string Module { get; set; }
+ bool setFound = doc.Lines.Values.Any(l => l.Method.Equals($"System.String Coverlet.Core.Samples.Tests.{testClassName}::set_Property()"));
+ Assert.False(setFound, "Property setter decorated with with exclude attribute should be excluded");
- public string Identifier { get; set; }
+ instrumenterTest.Directory.Delete(true);
+ }
- public DirectoryInfo Directory { get; set; }
- }
+ private InstrumenterTest CreateInstrumentor(bool fakeCoreLibModule = false, string[] attributesToIgnore = null, string[] excludedFiles = null, bool singleHit = false)
+ {
+ string module = GetType().Assembly.Location;
+ string pdb = Path.Combine(Path.GetDirectoryName(module), Path.GetFileNameWithoutExtension(module) + ".pdb");
+ string identifier = Guid.NewGuid().ToString();
+
+ DirectoryInfo directory = Directory.CreateDirectory(Path.Combine(Path.GetTempPath(), identifier));
+
+ string destModule, destPdb;
+ if (fakeCoreLibModule)
+ {
+ destModule = "System.Private.CoreLib.dll";
+ destPdb = "System.Private.CoreLib.pdb";
+ }
+ else
+ {
+ destModule = Path.GetFileName(module);
+ destPdb = Path.GetFileName(pdb);
+ }
+
+ File.Copy(module, Path.Combine(directory.FullName, destModule), true);
+ File.Copy(pdb, Path.Combine(directory.FullName, destPdb), true);
+
+ var instrumentationHelper =
+ new InstrumentationHelper(new ProcessExitHandler(), new RetryHelper(), new FileSystem(), new Mock().Object, new SourceRootTranslator(new Mock().Object, new FileSystem()));
+
+ module = Path.Combine(directory.FullName, destModule);
+ CoverageParameters parameters = new()
+ {
+ ExcludeAttributes = attributesToIgnore,
+ DoesNotReturnAttributes = new string[] { "DoesNotReturnAttribute" }
+ };
+ var instrumenter = new Instrumenter(module, identifier, parameters, _mockLogger.Object, instrumentationHelper, new FileSystem(), new SourceRootTranslator(_mockLogger.Object, new FileSystem()), new CecilSymbolHelper());
+ return new InstrumenterTest
+ {
+ Instrumenter = instrumenter,
+ Module = module,
+ Identifier = identifier,
+ Directory = directory
+ };
+ }
- [Fact]
- public void TestInstrument_NetStandardAwareAssemblyResolver_FromRuntime()
- {
- var netstandardResolver = new NetstandardAwareAssemblyResolver(null, _mockLogger.Object);
+ class InstrumenterTest
+ {
+ public Instrumenter Instrumenter { get; set; }
- // We ask for "official" netstandard.dll implementation with know MS public key cc7b13ffcd2ddd51 same in all runtime
- AssemblyDefinition resolved = netstandardResolver.Resolve(AssemblyNameReference.Parse("netstandard, Version=0.0.0.0, Culture=neutral, PublicKeyToken=cc7b13ffcd2ddd51"));
- Assert.NotNull(resolved);
+ public string Module { get; set; }
- // We check that netstandard.dll was resolved from runtime folder, where System.Object is
- Assert.Equal(Path.Combine(Path.GetDirectoryName(typeof(object).Assembly.Location), "netstandard.dll"), resolved.MainModule.FileName);
- }
+ public string Identifier { get; set; }
- [Fact]
- public void TestInstrument_NetStandardAwareAssemblyResolver_FromFolder()
- {
- // Someone could create a custom dll named netstandard.dll we need to be sure that not
- // conflicts with "official" resolution
-
- // We create dummy netstandard.dll
- var compilation = CSharpCompilation.Create(
- "netstandard",
- new[] { CSharpSyntaxTree.ParseText("") },
- new[] { MetadataReference.CreateFromFile(typeof(object).Assembly.Location) },
- new CSharpCompilationOptions(OutputKind.DynamicallyLinkedLibrary));
-
- Assembly newAssemlby;
- using (var dllStream = new MemoryStream())
- {
- EmitResult emitResult = compilation.Emit(dllStream);
- Assert.True(emitResult.Success);
- newAssemlby = Assembly.Load(dllStream.ToArray());
- // remove if exists
- File.Delete("netstandard.dll");
- File.WriteAllBytes("netstandard.dll", dllStream.ToArray());
- }
+ public DirectoryInfo Directory { get; set; }
+ }
- var netstandardResolver = new NetstandardAwareAssemblyResolver(newAssemlby.Location, _mockLogger.Object);
- AssemblyDefinition resolved = netstandardResolver.Resolve(AssemblyNameReference.Parse(newAssemlby.FullName));
+ [Fact]
+ public void TestInstrument_NetStandardAwareAssemblyResolver_FromRuntime()
+ {
+ var netstandardResolver = new NetstandardAwareAssemblyResolver(null, _mockLogger.Object);
- // We check if final netstandard.dll resolved is local folder one and not "official" netstandard.dll
- Assert.Equal(Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), "netstandard.dll"), Path.GetFullPath(resolved.MainModule.FileName));
- }
+ // We ask for "official" netstandard.dll implementation with know MS public key cc7b13ffcd2ddd51 same in all runtime
+ AssemblyDefinition resolved = netstandardResolver.Resolve(AssemblyNameReference.Parse("netstandard, Version=0.0.0.0, Culture=neutral, PublicKeyToken=cc7b13ffcd2ddd51"));
+ Assert.NotNull(resolved);
- public static IEnumerable
diff --git a/test/coverlet.integration.tests/Collectors.cs b/test/coverlet.integration.tests/Collectors.cs
index 262f29d58..05d261c3b 100644
--- a/test/coverlet.integration.tests/Collectors.cs
+++ b/test/coverlet.integration.tests/Collectors.cs
@@ -8,120 +8,120 @@
namespace Coverlet.Integration.Tests
{
- public class TestSDK_16_2_0 : Collectors
+ public class TestSDK_17_5_0 : Collectors
+ {
+ public TestSDK_17_5_0()
{
- public TestSDK_16_2_0()
- {
- TestSDKVersion = "16.2.0";
- }
-
- private protected override void AssertCollectorsInjection(ClonedTemplateProject clonedTemplateProject)
- {
- // Check out/in process collectors injection
- Assert.Contains("[coverlet]", File.ReadAllText(clonedTemplateProject.GetFiles("log.datacollector.*.txt").Single()));
-
- // There is a bug in this SDK version https://github.com/microsoft/vstest/pull/2221
- // in-proc coverlet.collector.dll collector with version != 1.0.0.0 won't be loaded
- // Assert.Contains("[coverlet]", File.ReadAllText(clonedTemplateProject.GetFiles("log.host.*.txt").Single()));
- }
+ TestSDKVersion = "17.5.0";
}
- public class TestSDK_16_5_0 : Collectors
+ private protected override void AssertCollectorsInjection(ClonedTemplateProject clonedTemplateProject)
{
- public TestSDK_16_5_0()
- {
- TestSDKVersion = "16.5.0";
- }
+ // Check out/in process collectors injection
+ Assert.Contains("[coverlet]", File.ReadAllText(clonedTemplateProject.GetFiles("log.datacollector.*.txt").Single()));
+
+ // There is a bug in this SDK version https://github.com/microsoft/vstest/pull/2221
+ // in-proc coverlet.collector.dll collector with version != 1.0.0.0 won't be loaded
+ // Assert.Contains("[coverlet]", File.ReadAllText(clonedTemplateProject.GetFiles("log.host.*.txt").Single()));
+ }
+ }
+
+ public class TestSDK_17_6_0 : Collectors
+ {
+ public TestSDK_17_6_0()
+ {
+ TestSDKVersion = "17.6.0";
+ }
+ }
+
+ public class TestSDK_Preview : Collectors
+ {
+ public TestSDK_Preview()
+ {
+ TestSDKVersion = "17.7.0-preview-23364-03";
+ }
+ }
+
+ public abstract class Collectors : BaseTest
+ {
+ private readonly string _buildConfiguration;
+
+ public Collectors()
+ {
+ _buildConfiguration = GetAssemblyBuildConfiguration().ToString();
+ }
+
+ protected string? TestSDKVersion { get; set; }
+
+ private ClonedTemplateProject PrepareTemplateProject()
+ {
+ if (TestSDKVersion is null)
+ {
+ throw new ArgumentNullException("Invalid TestSDKVersion");
+ }
+
+ ClonedTemplateProject clonedTemplateProject = CloneTemplateProject(testSDKVersion: TestSDKVersion);
+ UpdateNugeConfigtWithLocalPackageFolder(clonedTemplateProject.ProjectRootPath!);
+ AddCoverletCollectosRef(clonedTemplateProject.ProjectRootPath!);
+ return clonedTemplateProject;
+ }
+
+ private protected virtual void AssertCollectorsInjection(ClonedTemplateProject clonedTemplateProject)
+ {
+ // Check out/in process collectors injection
+ Assert.Contains("[coverlet]Initializing CoverletCoverageDataCollector with configuration:", File.ReadAllText(clonedTemplateProject.GetFiles("log.datacollector.*.txt").Single()));
+ Assert.Contains("[coverlet]Initialize CoverletInProcDataCollector", File.ReadAllText(clonedTemplateProject.GetFiles("log.host.*.txt").Single()));
+ }
+
+ [Fact]
+ public void TestVsTest_Test()
+ {
+ using ClonedTemplateProject clonedTemplateProject = PrepareTemplateProject();
+ Assert.True(DotnetCli($"test -c {_buildConfiguration} \"{clonedTemplateProject.ProjectRootPath}\" --collect:\"XPlat Code Coverage\" --diag:{Path.Combine(clonedTemplateProject.ProjectRootPath, "log.txt")}", out string standardOutput, out string standardError, clonedTemplateProject.ProjectRootPath!), standardOutput);
+ // We don't have any result to check because tests and code to instrument are in same assembly so we need to pass
+ // IncludeTestAssembly=true we do it in other test
+ Assert.Contains("Passed!", standardOutput);
+ AssertCollectorsInjection(clonedTemplateProject);
+ }
+
+ [Fact]
+ public void TestVsTest_Test_Settings()
+ {
+ using ClonedTemplateProject clonedTemplateProject = PrepareTemplateProject();
+ string runSettingsPath = AddCollectorRunsettingsFile(clonedTemplateProject.ProjectRootPath!);
+ Assert.True(DotnetCli($"test -c {_buildConfiguration} \"{clonedTemplateProject.ProjectRootPath}\" --collect:\"XPlat Code Coverage\" --settings \"{runSettingsPath}\" --diag:{Path.Combine(clonedTemplateProject.ProjectRootPath, "log.txt")}", out string standardOutput, out string standardError), standardOutput);
+ Assert.Contains("Passed!", standardOutput);
+ AssertCoverage(clonedTemplateProject);
+ AssertCollectorsInjection(clonedTemplateProject);
}
- public class TestSDK_Preview : Collectors
+ [Fact]
+ public void TestVsTest_VsTest()
{
- public TestSDK_Preview()
- {
- TestSDKVersion = "16.5.0-preview-20200203-01";
- }
+ using ClonedTemplateProject clonedTemplateProject = PrepareTemplateProject();
+ string runSettingsPath = AddCollectorRunsettingsFile(clonedTemplateProject.ProjectRootPath!);
+ Assert.True(DotnetCli($"publish -c {_buildConfiguration} {clonedTemplateProject.ProjectRootPath}", out string standardOutput, out string standardError), standardOutput);
+ string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => f.Contains("publish"));
+ Assert.NotNull(publishedTestFile);
+ Assert.True(DotnetCli($"vstest \"{publishedTestFile}\" --collect:\"XPlat Code Coverage\" --diag:{Path.Combine(clonedTemplateProject.ProjectRootPath, "log.txt")}", out standardOutput, out standardError), standardOutput);
+ // We don't have any result to check because tests and code to instrument are in same assembly so we need to pass
+ // IncludeTestAssembly=true we do it in other test
+ Assert.Contains("Passed!", standardOutput);
+ AssertCollectorsInjection(clonedTemplateProject);
}
- public abstract class Collectors : BaseTest
+ [Fact]
+ public void TestVsTest_VsTest_Settings()
{
- private readonly string _buildConfiguration;
-
- public Collectors()
- {
- _buildConfiguration = GetAssemblyBuildConfiguration().ToString();
- }
-
- protected string? TestSDKVersion { get; set; }
-
- private ClonedTemplateProject PrepareTemplateProject()
- {
- if (TestSDKVersion is null)
- {
- throw new ArgumentNullException("Invalid TestSDKVersion");
- }
-
- ClonedTemplateProject clonedTemplateProject = CloneTemplateProject(testSDKVersion: TestSDKVersion);
- UpdateNugeConfigtWithLocalPackageFolder(clonedTemplateProject.ProjectRootPath!);
- AddCoverletCollectosRef(clonedTemplateProject.ProjectRootPath!);
- return clonedTemplateProject;
- }
-
- private protected virtual void AssertCollectorsInjection(ClonedTemplateProject clonedTemplateProject)
- {
- // Check out/in process collectors injection
- Assert.Contains("[coverlet]Initializing CoverletCoverageDataCollector with configuration:", File.ReadAllText(clonedTemplateProject.GetFiles("log.datacollector.*.txt").Single()));
- Assert.Contains("[coverlet]Initialize CoverletInProcDataCollector", File.ReadAllText(clonedTemplateProject.GetFiles("log.host.*.txt").Single()));
- }
-
- [Fact]
- public void TestVsTest_Test()
- {
- using ClonedTemplateProject clonedTemplateProject = PrepareTemplateProject();
- Assert.True(DotnetCli($"test -c {_buildConfiguration} \"{clonedTemplateProject.ProjectRootPath}\" --collect:\"XPlat Code Coverage\" --diag:{Path.Combine(clonedTemplateProject.ProjectRootPath, "log.txt")}", out string standardOutput, out string standardError, clonedTemplateProject.ProjectRootPath!), standardOutput);
- // We don't have any result to check because tests and code to instrument are in same assembly so we need to pass
- // IncludeTestAssembly=true we do it in other test
- Assert.Contains("Passed!", standardOutput);
- AssertCollectorsInjection(clonedTemplateProject);
- }
-
- [Fact]
- public void TestVsTest_Test_Settings()
- {
- using ClonedTemplateProject clonedTemplateProject = PrepareTemplateProject();
- string runSettingsPath = AddCollectorRunsettingsFile(clonedTemplateProject.ProjectRootPath!);
- Assert.True(DotnetCli($"test -c {_buildConfiguration} \"{clonedTemplateProject.ProjectRootPath}\" --collect:\"XPlat Code Coverage\" --settings \"{runSettingsPath}\" --diag:{Path.Combine(clonedTemplateProject.ProjectRootPath, "log.txt")}", out string standardOutput, out string standardError), standardOutput);
- Assert.Contains("Passed!", standardOutput);
- AssertCoverage(clonedTemplateProject);
- AssertCollectorsInjection(clonedTemplateProject);
- }
-
- [Fact]
- public void TestVsTest_VsTest()
- {
- using ClonedTemplateProject clonedTemplateProject = PrepareTemplateProject();
- string runSettingsPath = AddCollectorRunsettingsFile(clonedTemplateProject.ProjectRootPath!);
- Assert.True(DotnetCli($"publish -c {_buildConfiguration} {clonedTemplateProject.ProjectRootPath}", out string standardOutput, out string standardError), standardOutput);
- string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => f.Contains("publish"));
- Assert.NotNull(publishedTestFile);
- Assert.True(DotnetCli($"vstest \"{publishedTestFile}\" --collect:\"XPlat Code Coverage\" --diag:{Path.Combine(clonedTemplateProject.ProjectRootPath, "log.txt")}", out standardOutput, out standardError), standardOutput);
- // We don't have any result to check because tests and code to instrument are in same assembly so we need to pass
- // IncludeTestAssembly=true we do it in other test
- Assert.Contains("Passed!", standardOutput);
- AssertCollectorsInjection(clonedTemplateProject);
- }
-
- [Fact]
- public void TestVsTest_VsTest_Settings()
- {
- using ClonedTemplateProject clonedTemplateProject = PrepareTemplateProject();
- string runSettingsPath = AddCollectorRunsettingsFile(clonedTemplateProject.ProjectRootPath!);
- Assert.True(DotnetCli($"publish -c {_buildConfiguration} \"{clonedTemplateProject.ProjectRootPath}\"", out string standardOutput, out string standardError), standardOutput);
- string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => f.Contains("publish"));
- Assert.NotNull(publishedTestFile);
- Assert.True(DotnetCli($"vstest \"{publishedTestFile}\" --collect:\"XPlat Code Coverage\" --ResultsDirectory:\"{clonedTemplateProject.ProjectRootPath}\" /settings:\"{runSettingsPath}\" --diag:{Path.Combine(clonedTemplateProject.ProjectRootPath, "log.txt")}", out standardOutput, out standardError), standardOutput);
- Assert.Contains("Passed!", standardOutput);
- AssertCoverage(clonedTemplateProject);
- AssertCollectorsInjection(clonedTemplateProject);
- }
+ using ClonedTemplateProject clonedTemplateProject = PrepareTemplateProject();
+ string runSettingsPath = AddCollectorRunsettingsFile(clonedTemplateProject.ProjectRootPath!);
+ Assert.True(DotnetCli($"publish -c {_buildConfiguration} \"{clonedTemplateProject.ProjectRootPath}\"", out string standardOutput, out string standardError), standardOutput);
+ string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => f.Contains("publish"));
+ Assert.NotNull(publishedTestFile);
+ Assert.True(DotnetCli($"vstest \"{publishedTestFile}\" --collect:\"XPlat Code Coverage\" --ResultsDirectory:\"{clonedTemplateProject.ProjectRootPath}\" /settings:\"{runSettingsPath}\" --diag:{Path.Combine(clonedTemplateProject.ProjectRootPath, "log.txt")}", out standardOutput, out standardError), standardOutput);
+ Assert.Contains("Passed!", standardOutput);
+ AssertCoverage(clonedTemplateProject);
+ AssertCollectorsInjection(clonedTemplateProject);
}
+ }
}
diff --git a/test/coverlet.integration.tests/DeterministicBuild.cs b/test/coverlet.integration.tests/DeterministicBuild.cs
index 2607b5e8e..7affdd1d3 100644
--- a/test/coverlet.integration.tests/DeterministicBuild.cs
+++ b/test/coverlet.integration.tests/DeterministicBuild.cs
@@ -88,7 +88,7 @@ public void Msbuild()
Assert.True(File.Exists(Path.Combine(_testProjectPath, "coverage.json")));
AssertCoverage(standardOutput);
- // Process exits hang on clean seem that process doesn't close, maybe some mbuild node reuse? btw manually tested
+ // Process exits hang on clean seem that process doesn't close, maybe some msbuild node reuse? btw manually tested
// DotnetCli("clean", out standardOutput, out standardError, _fixture.TestProjectPath);
// Assert.False(File.Exists(sourceRootMappingFilePath));
RunCommand("git", "clean -fdx", out _, out _, _testProjectPath);
@@ -112,7 +112,7 @@ public void Msbuild_SourceLink()
Assert.Contains("raw.githubusercontent.com", File.ReadAllText(Path.Combine(_testProjectPath, "coverage.json")));
AssertCoverage(standardOutput, checkDeterministicReport: false);
- // Process exits hang on clean seem that process doesn't close, maybe some mbuild node reuse? btw manually tested
+ // Process exits hang on clean seem that process doesn't close, maybe some msbuild node reuse? btw manually tested
// DotnetCli("clean", out standardOutput, out standardError, _fixture.TestProjectPath);
// Assert.False(File.Exists(sourceRootMappingFilePath));
RunCommand("git", "clean -fdx", out _, out _, _testProjectPath);
@@ -140,7 +140,7 @@ public void Collectors()
Assert.Contains("[coverlet]Initialize CoverletInProcDataCollector", File.ReadAllText(Directory.GetFiles(_testProjectPath, "log.host.*.txt").Single()));
Assert.Contains("[coverlet]Mapping resolved", dataCollectorLogContent);
- // Process exits hang on clean seem that process doesn't close, maybe some mbuild node reuse? btw manually tested
+ // Process exits hang on clean seem that process doesn't close, maybe some msbuild node reuse? btw manually tested
// DotnetCli("clean", out standardOutput, out standardError, _fixture.TestProjectPath);
// Assert.False(File.Exists(sourceRootMappingFilePath));
RunCommand("git", "clean -fdx", out _, out _, _testProjectPath);
@@ -169,7 +169,7 @@ public void Collectors_SourceLink()
Assert.Contains("[coverlet]Initialize CoverletInProcDataCollector", File.ReadAllText(Directory.GetFiles(_testProjectPath, "log.host.*.txt").Single()));
Assert.Contains("[coverlet]Mapping resolved", dataCollectorLogContent);
- // Process exits hang on clean seem that process doesn't close, maybe some mbuild node reuse? btw manually tested
+ // Process exits hang on clean seem that process doesn't close, maybe some msbuild node reuse? btw manually tested
// DotnetCli("clean", out standardOutput, out standardError, _fixture.TestProjectPath);
// Assert.False(File.Exists(sourceRootMappingFilePath));
RunCommand("git", "clean -fdx", out _, out _, _testProjectPath);
diff --git a/test/coverlet.integration.tests/DotnetTool.cs b/test/coverlet.integration.tests/DotnetTool.cs
index 8c87e33da..d2fd80fdf 100644
--- a/test/coverlet.integration.tests/DotnetTool.cs
+++ b/test/coverlet.integration.tests/DotnetTool.cs
@@ -1,97 +1,97 @@
// Copyright (c) Toni Solarin-Sodara
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
-using Coverlet.Tests.Xunit.Extensions;
using System.IO;
using System.Linq;
+using Coverlet.Tests.Xunit.Extensions;
using Xunit;
namespace Coverlet.Integration.Tests
{
- public class DotnetGlobalTools : BaseTest
+ public class DotnetGlobalTools : BaseTest
+ {
+ private string InstallTool(string projectPath)
{
- private string InstallTool(string projectPath)
- {
- _ = DotnetCli($"tool install coverlet.console --version {GetPackageVersion("*console*.nupkg")} --tool-path \"{Path.Combine(projectPath, "coverletTool")}\"", out string standardOutput, out _, projectPath);
- Assert.Contains("was successfully installed.", standardOutput);
- return Path.Combine(projectPath, "coverletTool", "coverlet");
- }
+ _ = DotnetCli($"tool install coverlet.console --version {GetPackageVersion("*console*.nupkg")} --tool-path \"{Path.Combine(projectPath, "coverletTool")}\"", out string standardOutput, out _, projectPath);
+ Assert.Contains("was successfully installed.", standardOutput);
+ return Path.Combine(projectPath, "coverletTool", "coverlet");
+ }
- [Fact]
- public void DotnetTool()
- {
- using ClonedTemplateProject clonedTemplateProject = CloneTemplateProject();
- UpdateNugeConfigtWithLocalPackageFolder(clonedTemplateProject.ProjectRootPath!);
- string coverletToolCommandPath = InstallTool(clonedTemplateProject.ProjectRootPath!);
- DotnetCli($"build {clonedTemplateProject.ProjectRootPath}", out string standardOutput, out string standardError);
- string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => !f.Contains("obj") && !f.Contains("ref"));
- RunCommand(coverletToolCommandPath, $"\"{publishedTestFile}\" --target \"dotnet\" --targetargs \"test {Path.Combine(clonedTemplateProject.ProjectRootPath, ClonedTemplateProject.ProjectFileName)} --no-build\" --include-test-assembly --output \"{clonedTemplateProject.ProjectRootPath}\"{Path.DirectorySeparatorChar}", out standardOutput, out standardError);
- Assert.Contains("Passed!", standardOutput);
- AssertCoverage(clonedTemplateProject, standardOutput: standardOutput);
- }
+ [Fact]
+ public void DotnetTool()
+ {
+ using ClonedTemplateProject clonedTemplateProject = CloneTemplateProject();
+ UpdateNugeConfigtWithLocalPackageFolder(clonedTemplateProject.ProjectRootPath!);
+ string coverletToolCommandPath = InstallTool(clonedTemplateProject.ProjectRootPath!);
+ DotnetCli($"build {clonedTemplateProject.ProjectRootPath}", out string standardOutput, out string standardError);
+ string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => !f.Contains("obj") && !f.Contains("ref"));
+ RunCommand(coverletToolCommandPath, $"\"{publishedTestFile}\" --target \"dotnet\" --targetargs \"test {Path.Combine(clonedTemplateProject.ProjectRootPath, ClonedTemplateProject.ProjectFileName)} --no-build\" --include-test-assembly --output \"{clonedTemplateProject.ProjectRootPath}\"{Path.DirectorySeparatorChar}", out standardOutput, out standardError);
+ Assert.Contains("Passed!", standardOutput);
+ AssertCoverage(clonedTemplateProject, standardOutput: standardOutput);
+ }
- [Fact]
- public void StandAlone()
- {
- using ClonedTemplateProject clonedTemplateProject = CloneTemplateProject();
- UpdateNugeConfigtWithLocalPackageFolder(clonedTemplateProject.ProjectRootPath!);
- string coverletToolCommandPath = InstallTool(clonedTemplateProject.ProjectRootPath!);
- DotnetCli($"build {clonedTemplateProject.ProjectRootPath}", out string standardOutput, out string standardError);
- string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => !f.Contains("obj") && !f.Contains("ref"));
- RunCommand(coverletToolCommandPath, $"\"{Path.GetDirectoryName(publishedTestFile)}\" --target \"dotnet\" --targetargs \"{publishedTestFile}\" --output \"{clonedTemplateProject.ProjectRootPath}\"{Path.DirectorySeparatorChar}", out standardOutput, out standardError);
- Assert.Contains("Hello World!", standardOutput);
- AssertCoverage(clonedTemplateProject, standardOutput: standardOutput);
- }
+ [Fact]
+ public void StandAlone()
+ {
+ using ClonedTemplateProject clonedTemplateProject = CloneTemplateProject();
+ UpdateNugeConfigtWithLocalPackageFolder(clonedTemplateProject.ProjectRootPath!);
+ string coverletToolCommandPath = InstallTool(clonedTemplateProject.ProjectRootPath!);
+ DotnetCli($"build {clonedTemplateProject.ProjectRootPath}", out string standardOutput, out string standardError);
+ string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => !f.Contains("obj") && !f.Contains("ref"));
+ RunCommand(coverletToolCommandPath, $"\"{Path.GetDirectoryName(publishedTestFile)}\" --target \"dotnet\" --targetargs \"{publishedTestFile}\" --output \"{clonedTemplateProject.ProjectRootPath}\"{Path.DirectorySeparatorChar}", out standardOutput, out standardError);
+ Assert.Contains("Hello World!", standardOutput);
+ AssertCoverage(clonedTemplateProject, standardOutput: standardOutput);
+ }
- [ConditionalFact]
- [SkipOnOS(OS.Linux)]
- [SkipOnOS(OS.MacOS)]
- public void StandAloneThreshold()
- {
- using ClonedTemplateProject clonedTemplateProject = CloneTemplateProject();
- UpdateNugeConfigtWithLocalPackageFolder(clonedTemplateProject.ProjectRootPath!);
- string coverletToolCommandPath = InstallTool(clonedTemplateProject.ProjectRootPath!);
- DotnetCli($"build {clonedTemplateProject.ProjectRootPath}", out string standardOutput, out string standardError);
- string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => !f.Contains("obj") && !f.Contains("ref"));
- Assert.False( RunCommand(coverletToolCommandPath, $"\"{Path.GetDirectoryName(publishedTestFile)}\" --target \"dotnet\" --targetargs \"{publishedTestFile}\" --threshold 80 --output \"{clonedTemplateProject.ProjectRootPath}\"\\", out standardOutput, out standardError));
- Assert.Contains("Hello World!", standardOutput);
- AssertCoverage(clonedTemplateProject, standardOutput: standardOutput);
- Assert.Contains("The minimum line coverage is below the specified 80", standardOutput);
- Assert.Contains("The minimum method coverage is below the specified 80", standardOutput);
- }
+ [ConditionalFact]
+ [SkipOnOS(OS.Linux)]
+ [SkipOnOS(OS.MacOS)]
+ public void StandAloneThreshold()
+ {
+ using ClonedTemplateProject clonedTemplateProject = CloneTemplateProject();
+ UpdateNugeConfigtWithLocalPackageFolder(clonedTemplateProject.ProjectRootPath!);
+ string coverletToolCommandPath = InstallTool(clonedTemplateProject.ProjectRootPath!);
+ DotnetCli($"build {clonedTemplateProject.ProjectRootPath}", out string standardOutput, out string standardError);
+ string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => !f.Contains("obj") && !f.Contains("ref"));
+ Assert.False(RunCommand(coverletToolCommandPath, $"\"{Path.GetDirectoryName(publishedTestFile)}\" --target \"dotnet\" --targetargs \"{publishedTestFile}\" --threshold 80 --output \"{clonedTemplateProject.ProjectRootPath}\"\\", out standardOutput, out standardError));
+ Assert.Contains("Hello World!", standardOutput);
+ AssertCoverage(clonedTemplateProject, standardOutput: standardOutput);
+ Assert.Contains("The minimum line coverage is below the specified 80", standardOutput);
+ Assert.Contains("The minimum method coverage is below the specified 80", standardOutput);
+ }
- [ConditionalFact]
- [SkipOnOS(OS.Linux)]
- [SkipOnOS(OS.MacOS)]
- public void StandAloneThresholdLine()
- {
- using ClonedTemplateProject clonedTemplateProject = CloneTemplateProject();
- UpdateNugeConfigtWithLocalPackageFolder(clonedTemplateProject.ProjectRootPath!);
- string coverletToolCommandPath = InstallTool(clonedTemplateProject.ProjectRootPath!);
- DotnetCli($"build {clonedTemplateProject.ProjectRootPath}", out string standardOutput, out string standardError);
- string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => !f.Contains("obj") && !f.Contains("ref"));
- Assert.False(RunCommand(coverletToolCommandPath, $"\"{Path.GetDirectoryName(publishedTestFile)}\" --target \"dotnet\" --targetargs \"{publishedTestFile}\" --threshold 80 --threshold-type line --output \"{clonedTemplateProject.ProjectRootPath}\"\\", out standardOutput, out standardError));
- Assert.Contains("Hello World!", standardOutput);
- AssertCoverage(clonedTemplateProject, standardOutput: standardOutput);
- Assert.Contains("The minimum line coverage is below the specified 80", standardOutput);
- Assert.DoesNotContain("The minimum method coverage is below the specified 80", standardOutput);
- }
+ [ConditionalFact]
+ [SkipOnOS(OS.Linux)]
+ [SkipOnOS(OS.MacOS)]
+ public void StandAloneThresholdLine()
+ {
+ using ClonedTemplateProject clonedTemplateProject = CloneTemplateProject();
+ UpdateNugeConfigtWithLocalPackageFolder(clonedTemplateProject.ProjectRootPath!);
+ string coverletToolCommandPath = InstallTool(clonedTemplateProject.ProjectRootPath!);
+ DotnetCli($"build {clonedTemplateProject.ProjectRootPath}", out string standardOutput, out string standardError);
+ string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => !f.Contains("obj") && !f.Contains("ref"));
+ Assert.False(RunCommand(coverletToolCommandPath, $"\"{Path.GetDirectoryName(publishedTestFile)}\" --target \"dotnet\" --targetargs \"{publishedTestFile}\" --threshold 80 --threshold-type line --output \"{clonedTemplateProject.ProjectRootPath}\"\\", out standardOutput, out standardError));
+ Assert.Contains("Hello World!", standardOutput);
+ AssertCoverage(clonedTemplateProject, standardOutput: standardOutput);
+ Assert.Contains("The minimum line coverage is below the specified 80", standardOutput);
+ Assert.DoesNotContain("The minimum method coverage is below the specified 80", standardOutput);
+ }
- [ConditionalFact]
- [SkipOnOS(OS.Linux)]
- [SkipOnOS(OS.MacOS)]
- public void StandAloneThresholdLineAndMethod ()
- {
- using ClonedTemplateProject clonedTemplateProject = CloneTemplateProject();
- UpdateNugeConfigtWithLocalPackageFolder(clonedTemplateProject.ProjectRootPath!);
- string coverletToolCommandPath = InstallTool(clonedTemplateProject.ProjectRootPath!);
- DotnetCli($"build {clonedTemplateProject.ProjectRootPath}", out string standardOutput, out string standardError);
- string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => !f.Contains("obj") && !f.Contains("ref"));
- Assert.False(RunCommand(coverletToolCommandPath, $"\"{Path.GetDirectoryName(publishedTestFile)}\" --target \"dotnet\" --targetargs \"{publishedTestFile}\" --threshold 80 --threshold-type line --threshold-type method --output \"{clonedTemplateProject.ProjectRootPath}\"\\", out standardOutput, out standardError));
- Assert.Contains("Hello World!", standardOutput);
- AssertCoverage(clonedTemplateProject, standardOutput: standardOutput);
- Assert.Contains("The minimum line coverage is below the specified 80", standardOutput);
- Assert.Contains("The minimum method coverage is below the specified 80", standardOutput);
- }
+ [ConditionalFact]
+ [SkipOnOS(OS.Linux)]
+ [SkipOnOS(OS.MacOS)]
+ public void StandAloneThresholdLineAndMethod()
+ {
+ using ClonedTemplateProject clonedTemplateProject = CloneTemplateProject();
+ UpdateNugeConfigtWithLocalPackageFolder(clonedTemplateProject.ProjectRootPath!);
+ string coverletToolCommandPath = InstallTool(clonedTemplateProject.ProjectRootPath!);
+ DotnetCli($"build {clonedTemplateProject.ProjectRootPath}", out string standardOutput, out string standardError);
+ string publishedTestFile = clonedTemplateProject.GetFiles("*" + ClonedTemplateProject.AssemblyName + ".dll").Single(f => !f.Contains("obj") && !f.Contains("ref"));
+ Assert.False(RunCommand(coverletToolCommandPath, $"\"{Path.GetDirectoryName(publishedTestFile)}\" --target \"dotnet\" --targetargs \"{publishedTestFile}\" --threshold 80 --threshold-type line --threshold-type method --output \"{clonedTemplateProject.ProjectRootPath}\"\\", out standardOutput, out standardError));
+ Assert.Contains("Hello World!", standardOutput);
+ AssertCoverage(clonedTemplateProject, standardOutput: standardOutput);
+ Assert.Contains("The minimum line coverage is below the specified 80", standardOutput);
+ Assert.Contains("The minimum method coverage is below the specified 80", standardOutput);
}
+ }
}
diff --git a/test/coverlet.integration.tests/coverlet.integration.tests.csproj b/test/coverlet.integration.tests/coverlet.integration.tests.csproj
index 2f0b3bacc..cda721792 100644
--- a/test/coverlet.integration.tests/coverlet.integration.tests.csproj
+++ b/test/coverlet.integration.tests/coverlet.integration.tests.csproj
@@ -4,14 +4,15 @@
net6.0falseenable
+ false
-
-
-
-
-
+
+
+
+
+
diff --git a/test/coverlet.tests.projectsample.fsharp/coverlet.tests.projectsample.fsharp.fsproj b/test/coverlet.tests.projectsample.fsharp/coverlet.tests.projectsample.fsharp.fsproj
index cd7a95969..14224c9a0 100644
--- a/test/coverlet.tests.projectsample.fsharp/coverlet.tests.projectsample.fsharp.fsproj
+++ b/test/coverlet.tests.projectsample.fsharp/coverlet.tests.projectsample.fsharp.fsproj
@@ -5,6 +5,7 @@
truefalsefalse
+ false
diff --git a/test/coverlet.tests.projectsample.netframework/coverlet.tests.projectsample.netframework.csproj b/test/coverlet.tests.projectsample.netframework/coverlet.tests.projectsample.netframework.csproj
index 822b965de..d34a33ca5 100644
--- a/test/coverlet.tests.projectsample.netframework/coverlet.tests.projectsample.netframework.csproj
+++ b/test/coverlet.tests.projectsample.netframework/coverlet.tests.projectsample.netframework.csproj
@@ -7,7 +7,7 @@
-
+ all
diff --git a/test/coverlet.tests.remoteexecutor/coverlet.tests.remoteexecutor.csproj b/test/coverlet.tests.remoteexecutor/coverlet.tests.remoteexecutor.csproj
index 5167d6c7e..42c7c75d4 100644
--- a/test/coverlet.tests.remoteexecutor/coverlet.tests.remoteexecutor.csproj
+++ b/test/coverlet.tests.remoteexecutor/coverlet.tests.remoteexecutor.csproj
@@ -2,7 +2,7 @@
Exe
- netcoreapp3.1
+ net6.0Coverlet.Tests.RemoteExecutorfalsefalse
diff --git a/test/coverlet.tests.xunit.extensions/coverlet.tests.xunit.extensions.csproj b/test/coverlet.tests.xunit.extensions/coverlet.tests.xunit.extensions.csproj
index 3003d7511..71b02548a 100644
--- a/test/coverlet.tests.xunit.extensions/coverlet.tests.xunit.extensions.csproj
+++ b/test/coverlet.tests.xunit.extensions/coverlet.tests.xunit.extensions.csproj
@@ -4,9 +4,10 @@
netstandard2.0falsefalse
+ false
-
+