【问题标题】:Inject .NET Core object as singleton instance-per-type?将 .NET Core 对象作为每个类型的单例实例注入?
【发布时间】:2020-03-18 16:13:22
【问题描述】:

是否可以使用 .NET Core 依赖注入让不同的类型解析它们自己的单例?例如,瞬态类型在其构造函数中解析一个不同的单例。即使是构造函数中的单例类型也会解析为它自己独特的单例。它类似于类类型上的注入静态成员。

HttpClientFactory 有点用 HttpClient 来做这件事。 HttpClient 是一次性的,但底层消息处理程序是所有者的生命周期控制对象。我怎样才能复制它?

理想情况下,解决方案不会让我知道所有类型都被注入到构造函数中——例如 HttpClientFactory 没有这个要求。

谢谢!

【问题讨论】:

  • 您能否更新您的问题并描述什么您要解决的潜在问题?

标签: .net-core dependency-injection


【解决方案1】:

如果其他人对未来感兴趣,我通过利用泛型解决了这个问题。例如:

public interface IStaticMember<TOwner, TValue>
    where TOwner : class
    where TValue : class
{
    public TValue Value { get; }
}

实施:

public class StaticMember<TOwner, TValue> : IStaticMember<TOwner, TValue>
    where TOwner : class
    where TValue : class
{
    public StaticMember(TValue value)
    {
        Value = value;
    }

    public TValue Value { get; private set; }
}

注册方法...

public static IServiceCollection AddStaticMember<TOwner, TValue>(
    this IServiceCollection @this)
    where TOwner : class
    where TValue : class
{
    return @this.AddSingleton<IStaticMember<TOwner, TValue>, StaticMember<TOwner, TValue>>();
}

public static IServiceCollection AddStaticMember<TOwner, TValue>(
    this IServiceCollection @this,
    Func<IServiceProvider, TValue> valueFactory)
    where TOwner : class
    where TValue : class
{
    return @this.AddSingleton<IStaticMember<TOwner, TValue>>(serviceProvider =>
    {
        return new StaticMember<TOwner, TValue>(valueFactory(serviceProvider));
    });
}

使用它的类...

public class OwningClass1 : IOwningClass1
{
    public OwningClass1(IStaticMember<IOwningClass1, IMyStatic> myStatic) { ... }
}

public class OwningClass2 : IOwningClass2
{
    public OwningClass2(IStaticMember<IOwningClass2, IMyStatic> myStatic) { ... }
}

并将静态注入瞬态(两种方式)...

services.AddTransient<IOwningClass1, OwningClass1>();
services.AddTransient<IOwningClass2, OwningClass2>();
services.AddTransient<IMyStatic, MyStatic>();
services.AddStaticMember<IOwningClass1, IMyStatic>();
services.AddStaticMember<IOwningClass2, IMyStatic>();

// or

services.AddTransient<IOwningClass1, OwningClass1>();
services.AddTransient<IOwningClass2, OwningClass2>();
services.AddStaticMember<IOwningClass1, IMyStatic>(serviceCollection => new MyStatic());
services.AddStaticMember<IOwningClass2, IMyStatic>(serviceCollection => new MyStatic());

在这两种情况下,OwningClass1 的所有实例都获得相同的实例,而 OwningClass2 的所有实例都获得另一个不同的实例。

如果有更好的方法,请告诉我。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-09-14
    • 1970-01-01
    • 2017-05-16
    • 2019-10-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多