How do I provide ILogger<T> in my unit tests of .NET Core code?
Starting from dotnet core 2.0 there's a generic NullLogger<T> class available:
var foo = new Foo(NullLogger<Foo>.Instance);
https://docs.microsoft.com/en-us/dotnet/api/microsoft.extensions.logging.abstractions.nulllogger-1?view=aspnetcore-2.1 (docs) https://github.com/aspnet/Logging/blob/master/src/Microsoft.Extensions.Logging.Abstractions/NullLoggerOfT.cs (source)
Or if you need it as part of your services:
services.AddSingleton<ILoggerFactory, NullLoggerFactory>();
https://docs.microsoft.com/en-us/dotnet/api/microsoft.extensions.logging.abstractions.nullloggerfactory?view=aspnetcore-2.1 (docs)
You can create an instance of ILogger<Foo>
using NullLoggerFactory
as the factory.
Consider the following controller:
public abstract class Foo: Controller
{
public Foo(ILogger<Foo> logger) {
Logger = logger;
}
public ILogger Logger { get; private set; }
}
A sample unit test could be:
[TestMethod]
public void FooConstructorUnitTest()
{
// Arrange
ILogger<FooController> logger = new Logger<FooController>(new NullLoggerFactory());
// Act
FooController target = new FooController(logger);
// Assert
Assert.AreSame(logger, target.Logger);
}
You have two options:
- Create empty implementation of
ILogger<Foo>
by hand and pass an instance of it to ctor. - Create same empty implementation on the fly using some mocking framework like Moq, NSubstitute, etc.