简体   繁体   English

如何在 ASP NET Core 中使用 DI 注入特定的接口实现

[英]How to inject specific interface implementation using DI in ASP NET Core

I have the following problem.我有以下问题。 I have an interface that is implemented by 2 classes.我有一个由 2 个类实现的接口。 One of these classes does the real work while the other uses the first one mentioned.其中一个类执行实际工作,而另一个使用提到的第一个类。 How can I tell the framework to use a specific implementation of an interface when instantiating a type of object?在实例化 object 类型时,如何告诉框架使用接口的特定实现? I want the controller to get the facade implementation and not the real one:我希望 controller 获得外观实现,而不是真正的实现:

public interface IDependency
{
   void Method();
}

public class Real : IDependency
{
   public void Method()
   {
   }
}

public class Facade : IDependency
{
   private IDependency dependency;
   Facade(IDependency dependency)  //I want a Real here
   {
     this.dependency=dependency;
   }
   public void Method()=>dependency.Method();
}


public MyController : Controller
{
   private IDependency dependency;
   MyController(IDependency dependency)   //I want the `Facade` here not the `Real`
   {
      this.dependency=dependency;
   }
   
   [HttpGet]
   [Route("[some route]")]
   public async Task CallMethod()
   {
      await this.dependency.Method();
   }

}

As you can see in the above example, I need a Real type of IDependency injected inside my Facade one, while I need a Facade type of IDependency injected in my MyController .正如您在上面的示例中看到的,我需要在我的Facade中注入一种Real类型的IDependency ,而我需要在MyController中注入一种Facade类型的IDependency How could that be done?怎么可能做到这一点?

Microsoft.Extensions.DependencyInjection doesn't have any means to do this. Microsoft.Extensions.DependencyInjection 没有任何方法可以做到这一点。 All you can do is inject all implementations, ie via List<IDependency> .您所能做的就是注入所有实现,即通过List<IDependency> Then, you can implement whatever manual logic you'd like to pick and choose from the available options there.然后,您可以从那里的可用选项中实现您想要选择的任何手动逻辑。

If you have any control over these classes, it would be better to simply implement a different interface, to distinguish the two.如果您对这些类有任何控制权,最好简单地实现一个不同的接口,以区分两者。 For example, you could create an IFacadeDependency interface that inherits from IDependency , and then have your Facade class implement that instead.例如,您可以创建一个从IDependency继承的IFacadeDependency接口,然后让您的Facade class 实现它。 Then, you can inject IFacadeDependency and get exactly what you want.然后,您可以注入IFacadeDependency并得到您想要的。

Register your dependency as follows:按如下方式注册您的依赖项:

public void ConfigureServices(IServiceCollection services)
{
    services.AddControllers();
    services.AddTransient<IDependency>(_ => new Facade(new Real()));
}

If you have other controllers that need a different implementation of IDependency, you'll want to register your controllers as services, allowing the registrations to be overwritten.如果您有其他控制器需要不同的 IDependency 实现,您需要将控制器注册为服务,从而允许覆盖注册。 For example, if you want most controllers to resolve with IDependency as Real, but only MyController to resolve IDependency as Facade, you could do this:例如,如果您希望大多数控制器将 IDependency 解析为 Real,但只有 MyController 将 IDependency 解析为 Facade,您可以这样做:

    public void ConfigureServices(IServiceCollection services)
    {
        // Adds controllers as services, allowing their registrations to be overwritten.
        services.AddMvc().AddControllersAsServices();  

        //services.AddControllers();  REMOVE THIS

        // Makes Real the default implementation of IDependency
        services.AddTransient<IDependency, Real>();               

        // Overwrite the default registration of MyController to instantiate using Facade.
        services.AddTransient<MyController>(sp => 
            new MyController(new Facade(sp.GetService<IDependency>())));
    }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 如何使用默认的ASP.NET Core DI容器在类中注入单个接口的多个服务类实现 - How to inject multiple service class implementation of single interface in class using default asp.net core DI container 如何使用 .NET CORE DI 为同一接口注册多个实现 - How to register multiple implementation for same interface using .NET CORE DI 如何使用 ASP.NET Core DI 注入连接字符串 - How to inject connection string using ASP.NET Core DI ASP.NET Core 中的 Serilog DI,要注入哪个 ILogger 接口? - Serilog DI in ASP.NET Core, which ILogger interface to inject? 使用ASP.NET Core DI注册接口的通用和特定实现 - Register both generic and specific implementation of an interface with ASP.NET Core DI 如何在 asp.net core 中注入特定的实现 - How to inject a specific implementation in asp.net core 无法使用 ASP.NET Core DI 注入委托 - Can't inject a delegate using ASP.NET Core DI 如何将方法注入 ASP.NET 内核中的 DI 容器? - How to inject method into DI Container in ASP.NET Core? 使用 ASP.NET 核心 DI 容器编写抽象工厂实现:如何管理对象生命周期? - Write an abstract factory implementation by using the ASP.NET core DI container: how to manage object lifetime? 依赖注入-当实现使用Unity for DI时如何使用简单注入器注入接口实现 - Dependency Injection - How to inject implementation of interface using Simple Injector when the implementation uses Unity for DI
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM