使用Log.ForContext <t>注入Serilog的ILogger,其中T是消费者

时间:2016-06-03 18:02:34

标签: c# simple-injector serilog

Serilog允许创建一个上下文感知记录器:

Log.ForContext<T>()

我想用SimpleInjector注册Serilog,使得T是消费者的类型,即它注入的是哪个类。

e.g。

public class Car
{
    public Car(ILogger logger) <= would be injected using Log.ForContext<Car>()
    {             
    }
}

我可以看到has been done with AutoFac

通过SimpleInjector documentation查看RegisterConditional()Func<TypeFactoryContext, Type>参数)非常有希望的重载。

c.RegisterConditional(typeof (ILogger),
    x => Log.ForContext(x.Consumer.ImplementationType), <= won't compile as expecting a Type
    Lifestyle.Scoped,
    x => true);

但是,我不想告诉SimpleInjector 要构建哪个 Type,而是如何构建

1 个答案:

答案 0 :(得分:9)

我已经将Serilog与Simple Injector集成在一起,其代码基于StackOverflow上的@Steven天才答案:logger wrapper best practice

public interface ILogger
{
    void Log(LogEntry entry);
}

public class SerilogLogger<T> : ILogger
{
    private readonly Serilog.ILogger _logger;

    public SerilogLogger()
    {
        _logger = new LoggerConfiguration()
            .WriteTo
            .Trace(LogEventLevel.Information)
            .CreateLogger()
            .ForContext(typeof (T));
    }

    public void Log(LogEntry entry)
    {
        /* Logging abstraction handling */
    }
}

public static class ContainerExtensions {

    public static void RegisterLogging(this Container container)
    {
        container.RegisterConditional(
            typeof(ILogger),
            c => typeof(SerilogLogger<>).MakeGenericType(c.Consumer.ImplementationType),
            Lifestyle.Singleton,
            c => true);
    }

}

在你的作文根目录中:

var container = new Container();
container.RegisterLogging();