问题
I have a class like so:
public class LoggedFoo
{
private readonly ILog _logger;
public LoggedFoo(ILog logger)
{
this._logger = logger;
}
public DoStuff()
{
this._logger.Info(i => i("Doing stuff..."));
}
}
One of the business requirements is that logs are being generated for certain functions, so naturally I want to mock out the ILog
to verify.
However, Common.Logging library supports type-based loggers, along the lines of:
var logger = LogManager.GetLogger<LoggedFoo>();
...or:
var logger = LogManager.GetLogger(typeof(LoggedFoo));
The problem is, we are using AutoFac for dependency injection, and I cannot figure out how to instantiate an ILog
based upon the class that is being instantiated for injection.
How do I write this? I am using the latest Nuget version of AutoFac.
回答1:
I can think on 2 ways to achieve it:(well sorry the hour is 1:50 am in my country...)
Change your
ILog
toILog<T>
and then register it as an Open Generic.Use Dynamic-Providers which allows you to resolve with a context.
Autofac
's website has an example which seems to be the exact thing you were looking for.
Resolve the dependency with a context:
private static void OnComponentPreparing(object sender, PreparingEventArgs e)
{
var t = e.Component.Target.Activator.LimitType;
e.Parameters = e.Parameters.Union(
new[]
{
new ResolvedParameter((p, i) => p.ParameterType == typeof(ILog),
(p, i) => LogManager.GetLogger(t)),
});
}
Attach to:
protected override void AttachToComponentRegistration(IComponentRegistry componentRegistry, IComponentRegistration registration)
{
// Handle constructor parameters.
registration.Preparing += OnComponentPreparing;
// Handle properties.
registration.Activated += (sender, e) => InjectLoggerProperties(e.Instance);
}
回答2:
So recently I decided the best way to do this was not to inject the ILog
interface, but rather the ILogManager
interface, like so:
public class Foo
{
private readonly ILog _logger;
public Foo(ILogManager logManager)
{
_logger = logManager.GetLogger<Foo>();
}
}
By doing this, I cut out a lot of the headscratching necessary to figure out which logger needed to be referenced. I defined my ILogManager
class once with an SingleInstance
lifetime and never looked back.
来源:https://stackoverflow.com/questions/31974924/how-to-wire-up-autofac-to-common-logging