Source: kevintsengtw/dotnet-testing-agent-skills (MIT). Ported into dotnet-agent-harness.
TUnit Advanced Applications: Data-Driven Testing, Dependency Injection, and Integration Testing
Applicable Scenarios
This skill covers TUnit advanced application techniques, from data-driven testing to dependency injection, from
execution control to ASP.NET Core integration testing practice.
Core Topics
- Data-driven testing advanced techniques (MethodDataSource, ClassDataSource, Matrix Tests)
- Properties attribute marking and test filtering
- Test lifecycle and dependency injection
- Execution control (Retry, Timeout, DisplayName)
- ASP.NET Core integration testing (WebApplicationFactory)
- Performance testing and load testing
- TUnit + Testcontainers complex infrastructure orchestration
- TUnit Engine Modes and troubleshooting
Data-Driven Testing Advanced Techniques
TUnit provides MethodDataSource, ClassDataSource, and Matrix Tests as three advanced data sources. MethodDataSource is
most flexible, supporting dynamic generation and external file loading; ClassDataSource is suitable for cross-test class
data sharing and AutoFixture integration; Matrix Tests automatically generates all parameter combinations (note: control
quantity to avoid explosive growth).
Full examples and comparison table please refer to
references/data-driven-testing.md
Properties Attribute Marking and Test Filtering
Basic Properties Usage
[Test]
[Property("Category", "Database")]
[Property("Priority", "High")]
public async Task DatabaseTest_HighPriority_ShouldBeFilterableByAttribute()
{
await Assert.That(true).IsTrue();
}
[Test]
[Property("Category", "Unit")]
[Property("Priority", "Medium")]
public async Task UnitTest_MediumPriority_BasicValidation()
{
await Assert.That(1 + 1).IsEqualTo(2);
}
[Test]
[Property("Category", "Integration")]
[Property("Priority", "Low")]
[Property("Environment", "Development")]
public async Task IntegrationTest_LowPriority_OnlyRunInDevEnvironment()
{
await Assert.That("Hello World").Contains("World");
}
```text
### Establishing Consistent Attribute Naming Conventions
```csharp
public static class TestProperties
{
// Test categories
public const string CATEGORY_UNIT = "Unit";
public const string CATEGORY_INTEGRATION = "Integration";
public const string CATEGORY_E2E = "E2E";
// Priority levels
public const string PRIORITY_CRITICAL = "Critical";
public const string PRIORITY_HIGH = "High";
public const string PRIORITY_MEDIUM = "Medium";
public const string PRIORITY_LOW = "Low";
// Environments
public const string ENV_DEVELOPMENT = "Development";
public const string ENV_STAGING = "Staging";
public const string ENV_PRODUCTION = "Production";
}
[Test]
[Property("Category", TestProperties.CATEGORY_UNIT)]
[Property("Priority", TestProperties.PRIORITY_HIGH)]
public async Task ExampleTest_UsingConstants_EnsuresConsistency()
{
await Assert.That(1 + 1).IsEqualTo(2);
}
```text
### TUnit Test Filtering Execution
TUnit uses `dotnet run` instead of `dotnet test`:
```bash
# Only run unit tests
dotnet run --treenode-filter "/*/*/*/*[Category=Unit]"
# Only run high priority tests
dotnet run --treenode-filter "/*/*/*/*[Priority=High]"
# Combined conditions: run high priority unit tests
dotnet run --treenode-filter "/*/*/*/*[(Category=Unit)&(Priority=High)]"
# OR condition: run unit tests or smoke tests
dotnet run --treenode-filter "/*/*/*/*[(Category=Unit)|(Suite=Smoke)]"
# Run tests for specific features
dotnet run --treenode-filter "/*/*/*/*[Feature=OrderProcessing]"
```text
### Filter Syntax Notes
- Path pattern `/*/*/*/*` represents Assembly/Namespace/Class/Method level
- Attribute names are case-sensitive
- Combined conditions must be properly enclosed in parentheses
---
## Test Lifecycle Management
TUnit provides complete lifecycle hooks: `[Before(Class)]` -> Constructor -> `[Before(Test)]` -> Test Method -> `[After(Test)]` -> Dispose -> `[After(Class)]`. Also has Assembly/TestSession level and `[BeforeEvery]`/`[AfterEvery]` global hooks. Constructor always executes first, BeforeClass/AfterClass each only executes once.
> Full attribute family and examples please refer to [references/lifecycle-management.md](references/lifecycle-management.md)
---
## Dependency Injection Patterns
### TUnit Dependency Injection Core Concepts
TUnit's dependency injection is built on Data Source Generators:
```csharp
public class MicrosoftDependencyInjectionDataSourceAttribute : DependencyInjectionDataSourceAttribute<IServiceScope>
{
private static readonly IServiceProvider ServiceProvider = CreateSharedServiceProvider();
public override IServiceScope CreateScope(DataGeneratorMetadata dataGeneratorMetadata)
{
return ServiceProvider.CreateScope();
}
public override object? Create(IServiceScope scope, Type type)
{
return scope.ServiceProvider.GetService(type);
}
private static IServiceProvider CreateSharedServiceProvider()
{
return new ServiceCollection()
.AddSingleton<IOrderRepository, MockOrderRepository>()
.AddSingleton<IDiscountCalculator, MockDiscountCalculator>()
.AddSingleton<IShippingCalculator, MockShippingCalculator>()
.AddSingleton<ILogger<OrderService>, MockLogger<OrderService>>()
.AddTransient<OrderService>()
.BuildServiceProvider();
}
}
```text
### Using TUnit Dependency Injection
```csharp
[MicrosoftDependencyInjectionDataSource]
public class DependencyInjectionTests(OrderService orderService)
{
[Test]
public async Task CreateOrder_UsingTUnitDependencyInjection_ShouldWorkCorrectly()
{
// Arrange - dependencies automatically injected through TUnit DI
var items = new List<OrderItem>
{
new() { ProductId = "PROD001", ProductName = "Test Product", UnitPrice = 100m, Quantity = 2 }
};
// Act
var order = await orderService.CreateOrderAsync("CUST001", CustomerLevel.VIP, items);
// Assert
await Assert.That(order).IsNotNull();
await Assert.That(order.CustomerId).IsEqualTo("CUST001");
await Assert.That(order.CustomerLevel).IsEqualTo(CustomerLevel.VIP);
}
[Test]
public async Task TUnitDependencyInjection_ValidateAutoInjection_ServiceShouldBeCorrectType()
{
await Assert.That(orderService).IsNotNull();
await Assert.That(orderService.GetType().Name).IsEqualTo("OrderService");
}
}
```text
### TUnit DI vs Manual Dependency Creation Comparison
| Feature | TUnit DI | Manual Dependency Creation |
| :------ | :------- | :------------------------- |
| **Setup Complexity** | Setup once, reuse | Manual creation needed for each test |
| **Maintainability** | Dependency changes only in one place | Need to modify all tests that use it |
| **Consistency** | Consistent with production code DI | May be inconsistent with actual application |
| **Test Readability** | Focus on test logic | Interfered by dependency creation code |
| **Scope Management** | Automatic service scope management | Need to manually manage object lifecycle |
| **Error Risk** | Framework guarantees correct injection | May miss or incorrectly create dependencies |
---
## Execution Control and Test Quality
- **`[Retry(n)]`**: Only for unstable tests caused by external dependencies (network, file locking), not for logic errors
- **`[Timeout(ms)]`**: Set reasonable upper limit for performance-sensitive tests, validate SLA with `Stopwatch`
- **`[DisplayName]`**: Supports `{0}` parameter interpolation, making test reports more business-language aligned
> Full examples (Retry/Timeout/DisplayName) please refer to [references/execution-control.md](references/execution-control.md)
---
## ASP.NET Core Integration Testing
Using `WebApplicationFactory<Program>` in TUnit for ASP.NET Core integration testing, managing lifecycle through `IDisposable` implementation. Covers API response validation, Content-Type header checking, and performance baseline and parallel load testing.
> Full WebApplicationFactory integration and load testing examples please refer to [references/aspnet-integration.md](references/aspnet-integration.md)
---
## TUnit + Testcontainers Infrastructure Orchestration
Using `[Before(Assembly)]` / `[After(Assembly)]` at Assembly level to manage multi-container orchestration for PostgreSQL, Redis, Kafka, combined with `NetworkBuilder` to create shared network. Containers only start once, significantly reducing startup time and resource consumption while maintaining data isolation between tests.
> Full multi-container orchestration and global sharing examples please refer to [references/tunit-testcontainers.md](references/tunit-testcontainers.md)
---
## TUnit Engine Modes
### Source Generation Mode (Default Mode)
```text
████████╗██╗ ██╗███╗ ██╗██╗████████╗
╚══██╔══╝██║ ██║████╗ ██║██║╚══██╔══╝
██║ ██║ ██║██╔██╗ ██║██║ ██║
██║ ██║ ██║██║╚██╗██║██║ ██║
██║ ╚██████╔╝██║ ╚████║██║ ██║
╚═╝ ╚═════╝ ╚═╝ ╚═══╝╚═╝ ╚═╝
Engine Mode: SourceGenerated
```text
### Features and Advantages
- **Compile-time generation**: All test discovery logic generated at compile time, no runtime reflection needed
- **Excellent performance**: Several times faster than reflection mode
- **Type safety**: Compile-time validation of test configuration and data sources
- **AOT compatible**: Fully supports Native AOT compilation
### Reflection Mode
```bash
# Enable reflection mode
dotnet run -- --reflection
# Or set environment variable
$env:TUNIT_EXECUTION_MODE = "reflection"
dotnet run
```text
### Applicable Scenarios
- Dynamic test discovery
- F# and VB.NET projects (automatically used)
- Certain reflection-dependent test patterns
### Native AOT Support
```xml
<PropertyGroup>
<PublishAot>true</PublishAot>
</PropertyGroup>
```text
```bash
dotnet publish -c Release
```text
---
## Common Issues and Troubleshooting
### Test Statistics Display Abnormal Issue
**Problem:** `Test Summary: Total: 0, Failed: 0, Success: 0`
### Solution Steps
1. **Ensure project file is correctly configured:**
```xml
<PropertyGroup>
<IsTestProject>true</IsTestProject>
</PropertyGroup>
```text
2. **Ensure GlobalUsings.cs is correct:**
```csharp
global using System;
global using System.Collections.Generic;
global using System.Linq;
global using System.Threading.Tasks;
global using TUnit.Core;
global using TUnit.Assertions;
global using TUnit.Assertions.Extensions;
```text
3. **Special configuration for integration tests:**
```csharp
// Add at the end of WebApi project's Program.cs
public partial class Program { } // Allow integration tests to access
```text
4. **Clean and rebuild:**
```bash
dotnet clean; dotnet build
dotnet test --verbosity normal
```text
### Source Generator Related Issues
### Issue: Test classes not discoverable
- **Solution**: Ensure project is fully rebuilt (`dotnet clean; dotnet build`)
### Issue: Strange errors at compile time
- **Solution**: Check if other Source Generator packages exist, consider updating to compatible versions
### Diagnostic Options
```ini
# .editorconfig
tunit.enable_verbose_diagnostics = true
```text
```xml
<PropertyGroup>
<TUnitEnableVerboseDiagnostics>true</TUnitEnableVerboseDiagnostics>
</PropertyGroup>
```text
---
## Practical Recommendations
### Data-Driven Testing Selection Strategy
- **MethodDataSource**: Suitable for dynamic data, complex objects, external file loading
- **ClassDataSource**: Suitable for shared data, AutoFixture integration, cross-test class reuse
- **Matrix Tests**: Suitable for combination testing, but control parameter quantity to avoid explosive growth
### Execution Control Best Practices
- **Retry**: Only for truly unstable external dependency tests
- **Timeout**: Set reasonable limits for performance-sensitive tests
- **DisplayName**: Make test reports more business-language aligned
### Integration Testing Strategy
- Use WebApplicationFactory for complete Web API testing
- Use TUnit + Testcontainers to build complex multi-service test environments
- Manage complex dependency relationships through attribute injection system
- Only test actually existing functionality, avoid testing non-existent endpoints
---
## Template Files
| File Name | Description |
| --------- | ----------- |
| [data-source-examples.cs](templates/data-source-examples.cs) | MethodDataSource, ClassDataSource examples |
| [matrix-tests-examples.cs](templates/matrix-tests-examples.cs) | Matrix Tests combination testing examples |
| [lifecycle-di-examples.cs](templates/lifecycle-di-examples.cs) | Lifecycle management and dependency injection examples |
| [execution-control-examples.cs](templates/execution-control-examples.cs) | Retry, Timeout, DisplayName examples |
| [aspnet-integration-tests.cs](templates/aspnet-integration-tests.cs) | ASP.NET Core integration testing examples |
| [testcontainers-examples.cs](templates/testcontainers-examples.cs) | Testcontainers infrastructure orchestration examples |
---
## Reference Resources
### Original Articles
This skill content is distilled from the "Old School Software Engineer's Testing Practice - 30 Day Challenge" article series:
- **Day 29 - TUnit Advanced Applications: Data-Driven Testing and Dependency Injection Deep Practice**
- Article: https://ithelp.ithome.com.tw/articles/10377970
- Sample code: https://github.com/kevintsengtw/30Days_in_Testing_Samples/tree/main/day29
- **Day 30 - TUnit Advanced Applications - Execution Control and Test Quality and ASP.NET Core Integration Testing**
- Article: https://ithelp.ithome.com.tw/articles/10378176
- Sample code: https://github.com/kevintsengtw/30Days_in_Testing_Samples/tree/main/day30
### TUnit Official Resources
- [TUnit Official Website](https://tunit.dev/)
- [TUnit GitHub Repository](https://github.com/thomhurst/TUnit)
### Advanced Feature Documentation
- [TUnit Method Data Source Documentation](https://tunit.dev/docs/test-authoring/method-data-source)
- [TUnit Class Data Source Documentation](https://tunit.dev/docs/test-authoring/class-data-source)
- [TUnit Matrix Tests Documentation](https://tunit.dev/docs/test-authoring/matrix-tests)
- [TUnit Properties Documentation](https://tunit.dev/docs/test-lifecycle/properties)
- [TUnit Dependency Injection Documentation](https://tunit.dev/docs/test-lifecycle/dependency-injection)
- [TUnit Retrying Documentation](https://tunit.dev/docs/execution/retrying)
- [TUnit Timeouts Documentation](https://tunit.dev/docs/execution/timeouts)
- [TUnit Engine Modes Documentation](https://tunit.dev/docs/execution/engine-modes)
- [TUnit ASP.NET Core Documentation](https://tunit.dev/docs/examples/aspnet)
- [TUnit Complex Test Infrastructure](https://tunit.dev/docs/examples/complex-test-infrastructure-orchestration)
### Testcontainers Related Resources
- [Testcontainers.NET Official Website](https://dotnet.testcontainers.org/)
- [Testcontainers.NET GitHub](https://github.com/testcontainers/testcontainers-dotnet)
1---2name: dotnet-testing-advanced-tunit-advanced3description: Complete guide for TUnit advanced applications. Use when using TUnit for data-driven testing, dependency injection, or integration testing. Covers MethodDataSource, ClassDataSource, Matrix Tests, Properties filtering. Includes Retry/Timeout control, WebApplicationFactory integration, Testcontainers multi-service orchestration. Keywords: TUnit advanced, TUnit advanced, MethodDataSource, ClassDataSource, Matrix Tests, MatrixDataSource, MicrosoftDependencyInjectionDataSource, Property, Retry, Timeout, data-driven testing, test filtering, WebApplicationFactory TUnit, multi-container orchestration4---5Source: kevintsengtw/dotnet-testing-agent-skills (MIT). Ported into dotnet-agent-harness.67# TUnit Advanced Applications: Data-Driven Testing, Dependency Injection, and Integration Testing89## Applicable Scenarios1011This skill covers TUnit advanced application techniques, from data-driven testing to dependency injection, from12execution control to ASP.NET Core integration testing practice.1314### Core Topics1516- Data-driven testing advanced techniques (MethodDataSource, ClassDataSource, Matrix Tests)17- Properties attribute marking and test filtering18- Test lifecycle and dependency injection19- Execution control (Retry, Timeout, DisplayName)20- ASP.NET Core integration testing (WebApplicationFactory)21- Performance testing and load testing22- TUnit + Testcontainers complex infrastructure orchestration23- TUnit Engine Modes and troubleshooting2425---2627## Data-Driven Testing Advanced Techniques2829TUnit provides MethodDataSource, ClassDataSource, and Matrix Tests as three advanced data sources. MethodDataSource is30most flexible, supporting dynamic generation and external file loading; ClassDataSource is suitable for cross-test class31data sharing and AutoFixture integration; Matrix Tests automatically generates all parameter combinations (note: control32quantity to avoid explosive growth).3334> Full examples and comparison table please refer to35> [references/data-driven-testing.md](references/data-driven-testing.md)3637---3839## Properties Attribute Marking and Test Filtering4041### Basic Properties Usage4243````csharp44[Test]45[Property("Category", "Database")]46[Property("Priority", "High")]47public async Task DatabaseTest_HighPriority_ShouldBeFilterableByAttribute()48{49 await Assert.That(true).IsTrue();50}5152[Test]53[Property("Category", "Unit")]54[Property("Priority", "Medium")]55public async Task UnitTest_MediumPriority_BasicValidation()56{57 await Assert.That(1 + 1).IsEqualTo(2);58}5960[Test]61[Property("Category", "Integration")]62[Property("Priority", "Low")]63[Property("Environment", "Development")]64public async Task IntegrationTest_LowPriority_OnlyRunInDevEnvironment()65{66 await Assert.That("Hello World").Contains("World");67}68```text6970### Establishing Consistent Attribute Naming Conventions7172```csharp73public static class TestProperties74{75 // Test categories76 public const string CATEGORY_UNIT = "Unit";77 public const string CATEGORY_INTEGRATION = "Integration";78 public const string CATEGORY_E2E = "E2E";7980 // Priority levels81 public const string PRIORITY_CRITICAL = "Critical";82 public const string PRIORITY_HIGH = "High";83 public const string PRIORITY_MEDIUM = "Medium";84 public const string PRIORITY_LOW = "Low";8586 // Environments87 public const string ENV_DEVELOPMENT = "Development";88 public const string ENV_STAGING = "Staging";89 public const string ENV_PRODUCTION = "Production";90}9192[Test]93[Property("Category", TestProperties.CATEGORY_UNIT)]94[Property("Priority", TestProperties.PRIORITY_HIGH)]95public async Task ExampleTest_UsingConstants_EnsuresConsistency()96{97 await Assert.That(1 + 1).IsEqualTo(2);98}99```text100101### TUnit Test Filtering Execution102103TUnit uses `dotnet run` instead of `dotnet test`:104105```bash106# Only run unit tests107dotnet run --treenode-filter "/*/*/*/*[Category=Unit]"108109# Only run high priority tests110dotnet run --treenode-filter "/*/*/*/*[Priority=High]"111112# Combined conditions: run high priority unit tests113dotnet run --treenode-filter "/*/*/*/*[(Category=Unit)&(Priority=High)]"114115# OR condition: run unit tests or smoke tests116dotnet run --treenode-filter "/*/*/*/*[(Category=Unit)|(Suite=Smoke)]"117118# Run tests for specific features119dotnet run --treenode-filter "/*/*/*/*[Feature=OrderProcessing]"120```text121122### Filter Syntax Notes123124- Path pattern `/*/*/*/*` represents Assembly/Namespace/Class/Method level125- Attribute names are case-sensitive126- Combined conditions must be properly enclosed in parentheses127128---129130## Test Lifecycle Management131132TUnit provides complete lifecycle hooks: `[Before(Class)]` -> Constructor -> `[Before(Test)]` -> Test Method -> `[After(Test)]` -> Dispose -> `[After(Class)]`. Also has Assembly/TestSession level and `[BeforeEvery]`/`[AfterEvery]` global hooks. Constructor always executes first, BeforeClass/AfterClass each only executes once.133134> Full attribute family and examples please refer to [references/lifecycle-management.md](references/lifecycle-management.md)135136---137138## Dependency Injection Patterns139140### TUnit Dependency Injection Core Concepts141142TUnit's dependency injection is built on Data Source Generators:143144```csharp145public class MicrosoftDependencyInjectionDataSourceAttribute : DependencyInjectionDataSourceAttribute<IServiceScope>146{147 private static readonly IServiceProvider ServiceProvider = CreateSharedServiceProvider();148149 public override IServiceScope CreateScope(DataGeneratorMetadata dataGeneratorMetadata)150 {151 return ServiceProvider.CreateScope();152 }153154 public override object? Create(IServiceScope scope, Type type)155 {156 return scope.ServiceProvider.GetService(type);157 }158159 private static IServiceProvider CreateSharedServiceProvider()160 {161 return new ServiceCollection()162 .AddSingleton<IOrderRepository, MockOrderRepository>()163 .AddSingleton<IDiscountCalculator, MockDiscountCalculator>()164 .AddSingleton<IShippingCalculator, MockShippingCalculator>()165 .AddSingleton<ILogger<OrderService>, MockLogger<OrderService>>()166 .AddTransient<OrderService>()167 .BuildServiceProvider();168 }169}170```text171172### Using TUnit Dependency Injection173174```csharp175[MicrosoftDependencyInjectionDataSource]176public class DependencyInjectionTests(OrderService orderService)177{178 [Test]179 public async Task CreateOrder_UsingTUnitDependencyInjection_ShouldWorkCorrectly()180 {181 // Arrange - dependencies automatically injected through TUnit DI182 var items = new List<OrderItem>183 {184 new() { ProductId = "PROD001", ProductName = "Test Product", UnitPrice = 100m, Quantity = 2 }185 };186187 // Act188 var order = await orderService.CreateOrderAsync("CUST001", CustomerLevel.VIP, items);189190 // Assert191 await Assert.That(order).IsNotNull();192 await Assert.That(order.CustomerId).IsEqualTo("CUST001");193 await Assert.That(order.CustomerLevel).IsEqualTo(CustomerLevel.VIP);194 }195196 [Test]197 public async Task TUnitDependencyInjection_ValidateAutoInjection_ServiceShouldBeCorrectType()198 {199 await Assert.That(orderService).IsNotNull();200 await Assert.That(orderService.GetType().Name).IsEqualTo("OrderService");201 }202}203```text204205### TUnit DI vs Manual Dependency Creation Comparison206207| Feature | TUnit DI | Manual Dependency Creation |208| :------ | :------- | :------------------------- |209| **Setup Complexity** | Setup once, reuse | Manual creation needed for each test |210| **Maintainability** | Dependency changes only in one place | Need to modify all tests that use it |211| **Consistency** | Consistent with production code DI | May be inconsistent with actual application |212| **Test Readability** | Focus on test logic | Interfered by dependency creation code |213| **Scope Management** | Automatic service scope management | Need to manually manage object lifecycle |214| **Error Risk** | Framework guarantees correct injection | May miss or incorrectly create dependencies |215216---217218## Execution Control and Test Quality219220- **`[Retry(n)]`**: Only for unstable tests caused by external dependencies (network, file locking), not for logic errors221- **`[Timeout(ms)]`**: Set reasonable upper limit for performance-sensitive tests, validate SLA with `Stopwatch`222- **`[DisplayName]`**: Supports `{0}` parameter interpolation, making test reports more business-language aligned223224> Full examples (Retry/Timeout/DisplayName) please refer to [references/execution-control.md](references/execution-control.md)225226---227228## ASP.NET Core Integration Testing229230Using `WebApplicationFactory<Program>` in TUnit for ASP.NET Core integration testing, managing lifecycle through `IDisposable` implementation. Covers API response validation, Content-Type header checking, and performance baseline and parallel load testing.231232> Full WebApplicationFactory integration and load testing examples please refer to [references/aspnet-integration.md](references/aspnet-integration.md)233234---235236## TUnit + Testcontainers Infrastructure Orchestration237238Using `[Before(Assembly)]` / `[After(Assembly)]` at Assembly level to manage multi-container orchestration for PostgreSQL, Redis, Kafka, combined with `NetworkBuilder` to create shared network. Containers only start once, significantly reducing startup time and resource consumption while maintaining data isolation between tests.239240> Full multi-container orchestration and global sharing examples please refer to [references/tunit-testcontainers.md](references/tunit-testcontainers.md)241242---243244## TUnit Engine Modes245246### Source Generation Mode (Default Mode)247248```text249████████╗██╗ ██╗███╗ ██╗██╗████████╗250╚══██╔══╝██║ ██║████╗ ██║██║╚══██╔══╝251 ██║ ██║ ██║██╔██╗ ██║██║ ██║252 ██║ ██║ ██║██║╚██╗██║██║ ██║253 ██║ ╚██████╔╝██║ ╚████║██║ ██║254 ╚═╝ ╚═════╝ ╚═╝ ╚═══╝╚═╝ ╚═╝255256 Engine Mode: SourceGenerated257```text258259### Features and Advantages260261- **Compile-time generation**: All test discovery logic generated at compile time, no runtime reflection needed262- **Excellent performance**: Several times faster than reflection mode263- **Type safety**: Compile-time validation of test configuration and data sources264- **AOT compatible**: Fully supports Native AOT compilation265266### Reflection Mode267268```bash269# Enable reflection mode270dotnet run -- --reflection271272# Or set environment variable273$env:TUNIT_EXECUTION_MODE = "reflection"274dotnet run275```text276277### Applicable Scenarios278279- Dynamic test discovery280- F# and VB.NET projects (automatically used)281- Certain reflection-dependent test patterns282283### Native AOT Support284285```xml286<PropertyGroup>287 <PublishAot>true</PublishAot>288</PropertyGroup>289```text290291```bash292dotnet publish -c Release293```text294295---296297## Common Issues and Troubleshooting298299### Test Statistics Display Abnormal Issue300301**Problem:** `Test Summary: Total: 0, Failed: 0, Success: 0`302303### Solution Steps3043051. **Ensure project file is correctly configured:**306307```xml308<PropertyGroup>309 <IsTestProject>true</IsTestProject>310</PropertyGroup>311```text3123132. **Ensure GlobalUsings.cs is correct:**314315```csharp316global using System;317global using System.Collections.Generic;318global using System.Linq;319global using System.Threading.Tasks;320global using TUnit.Core;321global using TUnit.Assertions;322global using TUnit.Assertions.Extensions;323```text3243253. **Special configuration for integration tests:**326327```csharp328// Add at the end of WebApi project's Program.cs329public partial class Program { } // Allow integration tests to access330```text3313324. **Clean and rebuild:**333334```bash335dotnet clean; dotnet build336dotnet test --verbosity normal337```text338339### Source Generator Related Issues340341### Issue: Test classes not discoverable342343- **Solution**: Ensure project is fully rebuilt (`dotnet clean; dotnet build`)344345### Issue: Strange errors at compile time346347- **Solution**: Check if other Source Generator packages exist, consider updating to compatible versions348349### Diagnostic Options350351```ini352# .editorconfig353tunit.enable_verbose_diagnostics = true354```text355356```xml357<PropertyGroup>358 <TUnitEnableVerboseDiagnostics>true</TUnitEnableVerboseDiagnostics>359</PropertyGroup>360```text361362---363364## Practical Recommendations365366### Data-Driven Testing Selection Strategy367368- **MethodDataSource**: Suitable for dynamic data, complex objects, external file loading369- **ClassDataSource**: Suitable for shared data, AutoFixture integration, cross-test class reuse370- **Matrix Tests**: Suitable for combination testing, but control parameter quantity to avoid explosive growth371372### Execution Control Best Practices373374- **Retry**: Only for truly unstable external dependency tests375- **Timeout**: Set reasonable limits for performance-sensitive tests376- **DisplayName**: Make test reports more business-language aligned377378### Integration Testing Strategy379380- Use WebApplicationFactory for complete Web API testing381- Use TUnit + Testcontainers to build complex multi-service test environments382- Manage complex dependency relationships through attribute injection system383- Only test actually existing functionality, avoid testing non-existent endpoints384385---386387## Template Files388389| File Name | Description |390| --------- | ----------- |391| [data-source-examples.cs](templates/data-source-examples.cs) | MethodDataSource, ClassDataSource examples |392| [matrix-tests-examples.cs](templates/matrix-tests-examples.cs) | Matrix Tests combination testing examples |393| [lifecycle-di-examples.cs](templates/lifecycle-di-examples.cs) | Lifecycle management and dependency injection examples |394| [execution-control-examples.cs](templates/execution-control-examples.cs) | Retry, Timeout, DisplayName examples |395| [aspnet-integration-tests.cs](templates/aspnet-integration-tests.cs) | ASP.NET Core integration testing examples |396| [testcontainers-examples.cs](templates/testcontainers-examples.cs) | Testcontainers infrastructure orchestration examples |397398---399400## Reference Resources401402### Original Articles403404This skill content is distilled from the "Old School Software Engineer's Testing Practice - 30 Day Challenge" article series:405406- **Day 29 - TUnit Advanced Applications: Data-Driven Testing and Dependency Injection Deep Practice**407 - Article: https://ithelp.ithome.com.tw/articles/10377970408 - Sample code: https://github.com/kevintsengtw/30Days_in_Testing_Samples/tree/main/day29409410- **Day 30 - TUnit Advanced Applications - Execution Control and Test Quality and ASP.NET Core Integration Testing**411 - Article: https://ithelp.ithome.com.tw/articles/10378176412 - Sample code: https://github.com/kevintsengtw/30Days_in_Testing_Samples/tree/main/day30413414### TUnit Official Resources415416- [TUnit Official Website](https://tunit.dev/)417- [TUnit GitHub Repository](https://github.com/thomhurst/TUnit)418419### Advanced Feature Documentation420421- [TUnit Method Data Source Documentation](https://tunit.dev/docs/test-authoring/method-data-source)422- [TUnit Class Data Source Documentation](https://tunit.dev/docs/test-authoring/class-data-source)423- [TUnit Matrix Tests Documentation](https://tunit.dev/docs/test-authoring/matrix-tests)424- [TUnit Properties Documentation](https://tunit.dev/docs/test-lifecycle/properties)425- [TUnit Dependency Injection Documentation](https://tunit.dev/docs/test-lifecycle/dependency-injection)426- [TUnit Retrying Documentation](https://tunit.dev/docs/execution/retrying)427- [TUnit Timeouts Documentation](https://tunit.dev/docs/execution/timeouts)428- [TUnit Engine Modes Documentation](https://tunit.dev/docs/execution/engine-modes)429- [TUnit ASP.NET Core Documentation](https://tunit.dev/docs/examples/aspnet)430- [TUnit Complex Test Infrastructure](https://tunit.dev/docs/examples/complex-test-infrastructure-orchestration)431432### Testcontainers Related Resources433434- [Testcontainers.NET Official Website](https://dotnet.testcontainers.org/)435- [Testcontainers.NET GitHub](https://github.com/testcontainers/testcontainers-dotnet)436````