Xunit.DependencyInjection.Logging
12.0.0
dotnet add package Xunit.DependencyInjection.Logging --version 12.0.0
NuGet\Install-Package Xunit.DependencyInjection.Logging -Version 12.0.0
<PackageReference Include="Xunit.DependencyInjection.Logging" Version="12.0.0" />
<PackageVersion Include="Xunit.DependencyInjection.Logging" Version="12.0.0" />
<PackageReference Include="Xunit.DependencyInjection.Logging" />
paket add Xunit.DependencyInjection.Logging --version 12.0.0
#r "nuget: Xunit.DependencyInjection.Logging, 12.0.0"
#:package Xunit.DependencyInjection.Logging@12.0.0
#addin nuget:?package=Xunit.DependencyInjection.Logging&version=12.0.0
#tool nuget:?package=Xunit.DependencyInjection.Logging&version=12.0.0
Xunit.DependencyInjection
Use Microsoft.Extensions.DependencyInjection to resolve xUnit test cases: constructor-inject services into your test classes instead of writing them by hand, and reuse the same Startup/host configuration you use in your application.
xUnit v2 users: please use the v2 branch.
Xunit.DependencyInjection.SkippableFactis obsolete on xunit.v3 and no longer needed.
Getting started
Install the NuGet package:
dotnet add package Xunit.DependencyInjection
dotnet add package xunit.v3 --version 4.0.0
xUnit v4 uses the
xunit.v3package. When upgrading, replace anyxunit.v3.mtp-v2reference withxunit.v3.
Add a Startup class to your test project and register your services in ConfigureServices:
namespace Your.Test.Project
{
public class Startup
{
public void ConfigureServices(IServiceCollection services)
{
services.AddTransient<IDependency, DependencyClass>();
}
}
}
Then inject IDependency into your test class constructor, exactly like you would with any other DI-enabled class:
public interface IDependency
{
int Value { get; }
}
internal class DependencyClass : IDependency
{
public int Value => 1;
}
public class MyAwesomeTests
{
private readonly IDependency _d;
public MyAwesomeTests(IDependency d) => _d = d;
[Fact]
public void AssertThatWeDoStuff()
{
Assert.Equal(1, _d.Value);
}
}
Xunit.DependencyInjectionbuilds on top of the generic host and fully supports its lifecycle, so you can use any feature the generic host offers, including (but not limited to)IHostedService.
Integrating with ASP.NET Core TestHost (3.0+)
With an ASP.NET Core Startup class
dotnet add package Microsoft.AspNetCore.TestHost
public class Startup
{
public void ConfigureHost(IHostBuilder hostBuilder) => hostBuilder
.ConfigureWebHost[Defaults](webHostBuilder => webHostBuilder
.UseTestServer(options => options.PreserveExecutionContext = true)
.UseStartup<AspNetCoreStartup>());
}
With Minimal APIs
If your web project uses Minimal APIs instead of an ASP.NET Core Startup class, install Xunit.DependencyInjection.AspNetCoreTesting:
dotnet add package Xunit.DependencyInjection.AspNetCoreTesting
public class Startup
{
public IHostBuilder CreateHostBuilder() => MinimalApiHostBuilderFactory.GetHostBuilder<Program>();
}
Your ASP.NET Core project may need to add
InternalsVisibleTofor the test project, or addpublic partial class Program { }at the end ofProgram.cs, so the test project can referenceProgram.See Xunit.DependencyInjection.Test.AspNetCore for a full example.
Startup configuration styles
Startup supports two configuration styles. The Configure method (see Initializing data on startup) is supported by both styles.
HostApplicationBuilder style
CreateHostApplicationBuildermethodIf this method is not found, the host falls back to
Host.CreateEmptyApplicationBuilder(new() { ApplicationName = assemblyName.Name }).public HostApplicationBuilder CreateHostApplicationBuilder([AssemblyName assemblyName]) { }ConfigureHostApplicationBuildermethod (presence of this method selects theHostApplicationBuilderstyle)public void ConfigureHostApplicationBuilder(IHostApplicationBuilder hostApplicationBuilder) { }BuildHostApplicationBuildermethodIf this method is not found, the host is built by simply calling
hostApplicationBuilder.Build().public IHost BuildHostApplicationBuilder(HostApplicationBuilder hostApplicationBuilder) { return hostApplicationBuilder.Build(); }
Startup/HostBuilder style
CreateHostBuildermethodpublic class Startup { public IHostBuilder CreateHostBuilder([AssemblyName assemblyName]) { } }ConfigureHostmethodpublic class Startup { public void ConfigureHost(IHostBuilder hostBuilder) { } }ConfigureServicesmethodpublic class Startup { public void ConfigureServices(IServiceCollection services[, HostBuilderContext context]) { } }BuildHostmethodIf this method is not found, the host is built by simply calling
hostBuilder.Build().public class Startup { public IHost BuildHost([IHostBuilder hostBuilder]) { return hostBuilder.Build(); } }
Method parameters wrapped in [...] above are optional.
How is Startup located?
Startup classes are looked up in the following order; the first match wins.
1. Startup declared on the test class
Apply [Startup(typeof(MyStartup))] on the test class.
2. Nested Startup
public class TestClass1
{
public class Startup
{
public void ConfigureServices(IServiceCollection services) { }
}
}
3. Closest Startup in the namespace hierarchy
If the test class's full name is A.B.C.TestClass, Startup is looked up in this order:
A.B.C.StartupA.B.StartupA.StartupStartup
4. Default Startup
A default
Startupwas required before 8.7.0, and is optional in some cases after 8.7.0. When it's required, add a startup class to your test project as shown above.
By default, Your.Test.Project.Startup, Your.Test.Project is used.
If you want to use a custom Startup, set XunitStartupAssembly and/or XunitStartupFullName in your project's PropertyGroup:
<Project>
<PropertyGroup>
<XunitStartupAssembly>Abc</XunitStartupAssembly>
<XunitStartupFullName>Xyz</XunitStartupFullName>
</PropertyGroup>
</Project>
| XunitStartupAssembly | XunitStartupFullName | Resulting Startup |
|---|---|---|
Your.Test.Project.Startup, Your.Test.Project |
||
Abc |
Abc.Startup, Abc |
|
Xyz |
Xyz, Your.Test.Project |
|
Abc |
Xyz |
Xyz, Abc |
Running tests in parallel
By default, xUnit runs tests from different test collections in parallel, while tests in the same class run sequentially. xUnit v4 supports three parallelization modes:
ParallelMode.None: Run all tests sequentially.ParallelMode.Collections(default): Run different test collections in parallel.ParallelMode.All: Run all tests in parallel, including tests in the same class.
Configure the mode with xUnit's assembly-level Parallelization attribute:
using Xunit.v3;
[assembly: Parallelization(MaxThreads = 2, Mode = ParallelMode.All)]
MaxThreads is optional; set it to limit the number of tests running concurrently. Remove the ParallelizationMode MSBuild property when upgrading, as it no longer controls parallelization.
If you register a custom
ITestCollectionOrderer, test collections run in the order it specifies, which can be slower than running without one.
To run tests in a class or method sequentially when using ParallelMode.All, decorate it with [DisableParallelization]. To prevent a test collection from running in parallel with other tests, use [CollectionDefinition(DisableParallelization = true)].
See xUnit's parallelization documentation for Parallelization.Algorithm and runner-specific configuration.
Thanks to Meziantou.Xunit.ParallelTestFramework for the inspiration.
Disabling Xunit.DependencyInjection
<Project>
<PropertyGroup>
<EnableXunitDependencyInjectionDefaultTestFrameworkAttribute>false</EnableXunitDependencyInjectionDefaultTestFrameworkAttribute>
</PropertyGroup>
</Project>
Injecting ITestOutputHelper
Inject ITestOutputHelperAccessor instead of ITestOutputHelper directly, since the actual instance is only available while a test is running:
internal class DependencyClass : IDependency
{
private readonly ITestOutputHelperAccessor _testOutputHelperAccessor;
public DependencyClass(ITestOutputHelperAccessor testOutputHelperAccessor)
{
_testOutputHelperAccessor = testOutputHelperAccessor;
}
}
Writing Microsoft.Extensions.Logging output to ITestOutputHelper
Install Xunit.DependencyInjection.Logging:
dotnet add package Xunit.DependencyInjection.Logging
The call chain must originate from the running test case; otherwise this feature won't work.
public class Startup
{
public void ConfigureServices(IServiceCollection services) => services
.AddLogging(lb => lb.AddXunitOutput());
}
Injecting IConfiguration or IHostEnvironment into Startup
public class Startup
{
public void ConfigureHost(IHostBuilder hostBuilder) => hostBuilder
.ConfigureServices((context, services) => { /* use context.Configuration / context.HostingEnvironment */ });
}
or
public class Startup
{
public void ConfigureServices(IServiceCollection services, HostBuilderContext context)
{
// use context.Configuration / context.HostingEnvironment
}
}
Customizing IConfiguration
public class Startup
{
public void ConfigureHost(IHostBuilder hostBuilder) => hostBuilder
.ConfigureHostConfiguration(builder => { })
.ConfigureAppConfiguration((context, builder) => { });
}
How do I inject values with [MemberData]?
[MemberData] members are static and can't be resolved from the container, so use [MethodData] instead — it resolves the referenced method's parameters from DI.
Integrating with OpenTelemetry
Register the Xunit.DependencyInjection activity source with your TracerProviderBuilder to capture the spans this library emits:
TracerProviderBuilder builder;
builder.AddSource("Xunit.DependencyInjection");
Running code before and after each test
Inherit from BeforeAfterTest and register your implementation as a BeforeAfterTest service.
Initializing data on startup
For synchronous initialization, use the Configure method. For asynchronous initialization, use an IHostedService.
Related packages
| Package | Description |
|---|---|
| Xunit.DependencyInjection.Logging | Write Microsoft.Extensions.Logging output to ITestOutputHelper, see above |
| Xunit.DependencyInjection.AspNetCoreTesting | Integration with ASP.NET Core Minimal API TestHost, see above |
| Xunit.DependencyInjection.StaFact | Run [StaFact]/[StaTheory] test cases on an STA thread (e.g. for UI tests) |
| Xunit.DependencyInjection.xRetry | Support xRetry's [RetryFact]/[RetryTheory] |
| Xunit.DependencyInjection.FsCheck | Support FsCheck property-based [Property] tests |
| Xunit.DependencyInjection.Demystifier | Use Ben.Demystifier to format exception stack traces |
| Xunit.DependencyInjection.Analyzer | Roslyn analyzer that validates Startup class shape at compile time |
| Xunit.DependencyInjection.Template | dotnet new xunit-di template to scaffold a new test project |
StaFact
dotnet add package Xunit.DependencyInjection.StaFact
public class Startup
{
public void ConfigureServices(IServiceCollection services) => services.AddStaFactSupport();
}
public class MyStaTests
{
[StaFact]
public void RunOnStaThread() { }
[StaTheory]
[InlineData(1)]
public void RunOnStaThread(int value) { }
}
xRetry
dotnet add package Xunit.DependencyInjection.xRetry
public class Startup
{
public void ConfigureServices(IServiceCollection services) => services.AddXRetrySupport();
}
public class MyRetryTests
{
[RetryFact(3)]
public void FlakyTest() { }
}
FsCheck
dotnet add package Xunit.DependencyInjection.FsCheck
public class Startup
{
public void ConfigureServices(IServiceCollection services) => services.AddFsCheckSupport();
}
Demystifier
dotnet add package Xunit.DependencyInjection.Demystifier
public class Startup
{
public void ConfigureServices(IServiceCollection services) => services.UseDemystifyExceptionFilter();
}
Analyzer
The analyzer is automatically added as an analyzer reference when you install Xunit.DependencyInjection, and reports compile-time diagnostics (e.g. multiple Startup constructors, invalid Configure* method signatures) so misconfigured Startup classes are caught early.
Project template
dotnet new install Xunit.DependencyInjection.Template
dotnet new create xunit-di -n MyTestProject
See Xunit.DependencyInjection.Template for details.
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net8.0 is compatible. net8.0-android was computed. net8.0-browser was computed. net8.0-ios was computed. net8.0-maccatalyst was computed. net8.0-macos was computed. net8.0-tvos was computed. net8.0-windows was computed. net9.0 was computed. net9.0-android was computed. net9.0-browser was computed. net9.0-ios was computed. net9.0-maccatalyst was computed. net9.0-macos was computed. net9.0-tvos was computed. net9.0-windows was computed. net10.0 was computed. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
| .NET Framework | net472 is compatible. net48 was computed. net481 was computed. |
-
.NETFramework 4.7.2
- MartinCostello.Logging.XUnit.v3 (>= 0.7.1)
- Xunit.DependencyInjection (>= 12.0.0)
-
net8.0
- MartinCostello.Logging.XUnit.v3 (>= 0.7.1)
- Xunit.DependencyInjection (>= 12.0.0)
NuGet packages (3)
Showing the top 3 NuGet packages that depend on Xunit.DependencyInjection.Logging:
| Package | Downloads |
|---|---|
|
Stl.Testing
Stl.Testing is a collection of testing helpers used by Stl.Fusion tests. |
|
|
ActualLab.Testing
ActualLab.Testing is a collection of testing helpers used by ActualLab.Fusion tests. |
|
|
ZC.Tests.Core
Package Description |
GitHub repositories (9)
Showing the top 9 popular GitHub repositories that depend on Xunit.DependencyInjection.Logging:
| Repository | Stars |
|---|---|
|
dotnetcore/Util
Util是一个.Net平台下的应用框架,旨在提升中小团队的开发能力,由工具类、分层架构基类、Ui组件,配套代码生成模板,权限等组成。
|
|
|
chromelyapps/Chromely
Build Cross Platform HTML Desktop Apps on .NET using native GUI, HTML5, JavaScript, CSS, Owin, AspNetCore (MVC, RazorPages, Blazor)
|
|
|
microsoft/kernel-memory
Research project. A Memory solution for users, teams, and applications.
|
|
|
Nexus-Mods/NexusMods.App
Home of the development of the Nexus Mods App
|
|
|
servicetitan/Stl.Fusion
Build real-time apps (Blazor included) with less than 1% of extra code responsible for real-time updates. Host 10-1000x faster APIs relying on transparent and nearly 100% consistent caching. We call it DREAM, or Distributed REActive Memoization, and it's here to turn real-time on!
|
|
|
wabbajack-tools/wabbajack
An automated Modlist installer for various games.
|
|
|
bing-framework/Bing.NetCore
Bing是基于 .net core 3.1 的框架,旨在提升团队的开发输出能力,由常用公共操作类(工具类、帮助类)、分层架构基类,第三方组件封装,第三方业务接口封装等组成。
|
|
|
grate-devs/grate
grate - the SQL scripts migration runner
|
|
|
ActualLab/Fusion
Build real-time Blazor and MAUI apps while writing just 0.1% of the usual real-time update code. Handle 10× more API requests with the ActualLab.Rpc protocol—or 1000× more with Fusion’s transparent and perfectly coherent caching.
|
Support Microsoft.Extensions.Logging to ITestOutputHelper.
public void Configure(IServiceProvider provider)
{
XunitTestOutputLoggerProvider.Register(provider);
}