.NET Test Execution
Basic Test Commands
Run all tests in solution
dotnet test
Run tests in specific project
dotnet test tests/MyApp.Tests/MyApp.Tests.csproj
Run without build (faster if already built)
dotnet test --no-build
Run without restore
dotnet test --no-restore
Test Filtering
By Name
Filter by fully qualified name (contains)
dotnet test --filter "FullyQualifiedName~OrderService"
Filter by test name (exact match)
dotnet test --filter "Name=CreateOrder_ValidInput_ReturnsOrder"
Filter by display name
dotnet test --filter "DisplayName~Create Order"
By Category/Trait
Filter by trait (xUnit)
dotnet test --filter "Category=Unit" dotnet test --filter "Category!=Integration"
Multiple trait filters
dotnet test --filter "Category=Unit&Priority=High" dotnet test --filter "Category=Unit|Category=Integration"
By Class/Namespace
Filter by class name
dotnet test --filter "ClassName=OrderServiceTests"
Filter by namespace
dotnet test --filter "FullyQualifiedName~MyApp.Tests.Services"
Complex Filters
Combine with operators
& (and), | (or), ! (not), ~ (contains), = (equals)
Unit tests except slow ones
dotnet test --filter "Category=Unit&Category!=Slow"
All tests in namespace containing "Order"
dotnet test --filter "FullyQualifiedName~Order&Category!=Integration"
Test Output
Verbosity Levels
Quiet (minimal output)
dotnet test --verbosity quiet dotnet test -v q
Normal (default)
dotnet test --verbosity normal
Detailed (shows all test names)
dotnet test --verbosity detailed dotnet test -v d
Diagnostic (maximum output)
dotnet test --verbosity diagnostic
Logger Options
Console logger with verbosity
dotnet test --logger "console;verbosity=detailed"
TRX (Visual Studio Test Results)
dotnet test --logger trx
JUnit format (for CI systems)
dotnet test --logger "junit;LogFileName=results.xml"
HTML report
dotnet test --logger "html;LogFileName=results.html"
Multiple loggers
dotnet test --logger trx --logger "console;verbosity=detailed"
Results Directory
Specify results output directory
dotnet test --results-directory ./TestResults
Code Coverage
Collect Coverage
Basic coverage collection
dotnet test --collect:"XPlat Code Coverage"
With Coverlet
dotnet test /p:CollectCoverage=true
Coverlet with specific format
dotnet test /p:CollectCoverage=true /p:CoverletOutputFormat=cobertura
Multiple formats
dotnet test /p:CollectCoverage=true /p:CoverletOutputFormat="opencover,cobertura"
Coverage Thresholds
Fail if coverage below threshold
dotnet test /p:CollectCoverage=true /p:Threshold=80
Per-type thresholds
dotnet test /p:CollectCoverage=true /p:ThresholdType=line /p:Threshold=80
Coverage Reports
Install report generator
dotnet tool install -g dotnet-reportgenerator-globaltool
Generate HTML report
reportgenerator -reports:coverage.cobertura.xml -targetdir:coveragereport
Parallel Execution
Control parallelism
dotnet test --parallel
Limit parallel workers
dotnet test -- RunConfiguration.MaxCpuCount=4
Disable parallel execution
dotnet test -- RunConfiguration.DisableParallelization=true
Test Timeouts
Set test timeout (milliseconds)
dotnet test -- RunConfiguration.TestSessionTimeout=60000
// Per-test timeout (xUnit) [Fact(Timeout = 5000)] public void SlowTest() { }
// Per-test timeout (NUnit) [Test, Timeout(5000)] public void SlowTest() { }
Configuration Files
runsettings
<!-- test.runsettings --> <?xml version="1.0" encoding="utf-8"?> <RunSettings> <RunConfiguration> <MaxCpuCount>4</MaxCpuCount> <ResultsDirectory>./TestResults</ResultsDirectory> <TestSessionTimeout>600000</TestSessionTimeout> </RunConfiguration> <DataCollectionRunSettings> <DataCollectors> <DataCollector friendlyName="XPlat Code Coverage"> <Configuration> <Format>cobertura</Format> <Exclude>[].Migrations.*</Exclude> </Configuration> </DataCollector> </DataCollectors> </DataCollectionRunSettings> </RunSettings>
Use runsettings file
dotnet test --settings test.runsettings
Test Failure Analysis
Common Failure Patterns
Pattern Cause Fix
Assert.Equal failed Expected != Actual Check logic, verify test data
NullReferenceException Null not handled Add null checks, verify setup
TimeoutException Test too slow Optimize or increase timeout
ObjectDisposedException Using disposed object Fix lifetime management
InvalidOperationException Invalid state Check test setup/order
Debugging Failed Tests
Run single failing test with detailed output
dotnet test --filter "FullyQualifiedName~FailingTest" -v d
Enable blame mode to catch hangs
dotnet test --blame
Blame with hang detection
dotnet test --blame-hang --blame-hang-timeout 60s
Watch Mode
Run tests on file changes
dotnet watch test
Watch specific project
dotnet watch --project tests/MyApp.Tests test
Watch with filter
dotnet watch test --filter "Category=Unit"
CI/CD Integration
Exit Codes
Code Meaning
0 All tests passed
1 Tests failed
2 Command line error
CI Examples
Azure DevOps
- task: DotNetCoreCLI@2 inputs: command: test arguments: '--configuration Release --logger trx'
GitHub Actions
- run: dotnet test --configuration Release --logger "trx;LogFileName=test-results.trx"
See test-filtering.md for advanced filtering patterns.