在构造函数注入期间,Unity DI 容器能否识别正在构造的类型,并在解析引用时使用它?
During constructor injection can the Unity DI Container recognize the type that is being constructed, and use it when resolving a reference?
我想使用 Unity DI 容器将 Microsoft.Extensions.Logging
记录器注入到 class 的构造函数中:
using Microsoft.Extensions.Logging;
namespace LoggingExample
{
public class MyClass
{
private readonly ILogger<MyClass> _logger;
public MyClass(ILogger<MyClass> logger)
{
_logger = logger;
}
public void DoSomething()
{
_logger.LogInformation("Doing something.");
}
}
}
Whosebug 回答表明注入 ILogger<T>
不是一个好主意,因为它太具体了。相反,答案建议注入非泛型基类型,ILogger
,它更简单、更容易测试并且更不容易出错(我猜主要是复制和粘贴错误)。
在上面的 class 中,我们想要更改构造函数参数的数据类型:
public MyClass(ILogger logger)
{
_logger = logger;
}
然后我们需要一些方法将 ILogger
解析为 Logger<MyClass>
对于这个 class,或者 Logger<T>
在更一般的情况下对于任何 class,其中 T
代表被注入的 class。
这是在 Whosebug 答案中使用简单注入器 DI 容器和条件注册完成的:
container.RegisterConditional(
typeof(ILogger),
c => typeof(Logger<>).MakeGenericType(c.Consumer.ImplementationType),
Lifestyle.Singleton,
_ => true);
Unity 中可以进行条件注册吗? Unity 是否有任何其他方式可以识别 class 它正在注入 ILogger
并解析引用以注入 Logger<T>
对象(其中 T
是 class注入)?
您可以为每个 ILogger
实例定义一个名称,并使用 [Dependency]
属性指定您想要的名称。示例:
public static class Constants
{
public const string LOGGER_MYCLASS_UNITY_KEY = "ILogger<MyClass>";
}
在您的 Unity 注册中:
IUnityContainer container = new UnityContainer();
container.RegisterType<ILogger, Logger<MyClass>>(Constants.LOGGER_MYCLASS_UNITY_KEY,
new ContainerControllerLifetimeManager());
在需要记录器的 class 的构造函数中:
public class MyClass
{
private readonly ILogger<MyClass> _logger;
public MyClass([Dependency(Constants.LOGGER_MYCLASS_UNITY_KEY)] ILogger logger)
{
_logger = (ILogger<MyClass>)logger;
}
}
HTH.
我想使用 Unity DI 容器将 Microsoft.Extensions.Logging
记录器注入到 class 的构造函数中:
using Microsoft.Extensions.Logging;
namespace LoggingExample
{
public class MyClass
{
private readonly ILogger<MyClass> _logger;
public MyClass(ILogger<MyClass> logger)
{
_logger = logger;
}
public void DoSomething()
{
_logger.LogInformation("Doing something.");
}
}
}
ILogger<T>
不是一个好主意,因为它太具体了。相反,答案建议注入非泛型基类型,ILogger
,它更简单、更容易测试并且更不容易出错(我猜主要是复制和粘贴错误)。
在上面的 class 中,我们想要更改构造函数参数的数据类型:
public MyClass(ILogger logger)
{
_logger = logger;
}
然后我们需要一些方法将 ILogger
解析为 Logger<MyClass>
对于这个 class,或者 Logger<T>
在更一般的情况下对于任何 class,其中 T
代表被注入的 class。
这是在 Whosebug 答案中使用简单注入器 DI 容器和条件注册完成的:
container.RegisterConditional(
typeof(ILogger),
c => typeof(Logger<>).MakeGenericType(c.Consumer.ImplementationType),
Lifestyle.Singleton,
_ => true);
Unity 中可以进行条件注册吗? Unity 是否有任何其他方式可以识别 class 它正在注入 ILogger
并解析引用以注入 Logger<T>
对象(其中 T
是 class注入)?
您可以为每个 ILogger
实例定义一个名称,并使用 [Dependency]
属性指定您想要的名称。示例:
public static class Constants
{
public const string LOGGER_MYCLASS_UNITY_KEY = "ILogger<MyClass>";
}
在您的 Unity 注册中:
IUnityContainer container = new UnityContainer();
container.RegisterType<ILogger, Logger<MyClass>>(Constants.LOGGER_MYCLASS_UNITY_KEY,
new ContainerControllerLifetimeManager());
在需要记录器的 class 的构造函数中:
public class MyClass
{
private readonly ILogger<MyClass> _logger;
public MyClass([Dependency(Constants.LOGGER_MYCLASS_UNITY_KEY)] ILogger logger)
{
_logger = (ILogger<MyClass>)logger;
}
}
HTH.