简体   繁体   English

使用Unity在构造函数中解析同一接口的多个依赖项

[英]Resolve multiple dependencies for the same interface in a constructor using Unity

I am trying to resolve two dependencies on a single interface with two different implementations when creating a new object using Unity. 我正在尝试使用Unity创建新对象时,在具有两个不同实现的单个接口上解析两个依赖项。 I am using ASP.NET MVC 4 with a controller that has a number of dependencies I will recreate a dummy scenario below: 我正在使用ASP.NET MVC 4和一个具有许多依赖项的控制器,我将在下面重新创建一个虚拟场景:

Say we have a controller that looks something like this: 假设我们有一个看起来像这样的控制器:

public class HomeController : Controller
{
    public HomeController(IRepository repository, ISomeInterface someInterface1, ISomeInterface someInterface2, IConfiguration configuration)
    {
        // Code
    }
}

I need to be able to resolve ISomeInterface to two different classes and was hoping to do this based on name. 我需要能够将ISomeInterface解析为两个不同的类,并希望能够根据名称进行此操作。 Here is what I have so far which doesn't work in Boostrapper.cs: 到目前为止,这是我在Boostrapper.cs中无效的方法:

var someInterface1 = new FirstImplementation();
var someInterface2 = new SecondImplementation();
container.RegisterInstance(typeof(ISomeInterface), someInterface1);
container.RegisterInstance(typeof(ISomeInterface), "someInterface2", someInterface2);

I have also had a look at this post but this didn't seem to solve my problem either: http://unity.codeplex.com/discussions/355192 I think this is solving a different problem to mine since I am trying to resolve 2 dependencies automatically in a constructor. 我也看过这篇文章,但这似乎也没有解决我的问题: http//unity.codeplex.com/discussions/355192我认为这是解决一个不同的问题,因为我试图解决在构造函数中自动生成2个依赖项。

Any help with this problem would be appreciated, thanks 任何有关此问题的帮助将不胜感激,谢谢

You could use Named registrations for that; 您可以使用命名注册; in order to do so, register the types with a name (as you already did to a part in your sample): 为此,请使用名称注册类型(正如您对样本中的某个部分所做的那样):

var someInterface1 = new FirstImplementation();
var someInterface2 = new SecondImplementation();
container.RegisterInstance(typeof(ISomeInterface), "Impl1", someInterface1);
container.RegisterInstance(typeof(ISomeInterface), "Impl2", someInterface2);

You can then add a Dependency attribute to the parameter that you use to specify the relevant name: 然后,您可以将Dependency属性添加到用于指定相关名称的参数:

public class HomeController : Controller
{
    public HomeController(IRepository repository, 
               [Dependency("Impl1")] ISomeInterface someInterface1, 
               [Dependency("Impl2")] ISomeInterface someInterface2, 
               IConfiguration configuration)
    {
        // Code
    }
}

For more information, see this link . 有关更多信息,请参阅此链接

I think you'll be better to replace these two arguments ISomeInterface someInterface1, ISomeInterface someInterface2 with the only one which will get necessary implementations. 我认为你将更好地替换这两个参数ISomeInterface someInterface1, ISomeInterface someInterface2只有一个将获得必要的实现。

It could be some interface which inherited from IEnumerable<ISomeInterface> . 它可能是从IEnumerable<ISomeInterface>继承的一些接口。 This will allow you to enumerate all needed implementation. 这将允许您枚举所有需要的实现。

public interface ISomeInterfaceEnumerator : IEnumerable<ISomeInterface>
{        
}

public class HomeController : Controller
{
    public HomeController(IRepository repository, ISomeInterfaceEnumerator someInterfaces, IConfiguration configuration)
    {
        // Code
    } 
}

Or maybe you can use more simple, but less flexible approach 或许您可以使用更简单但不太灵活的方法

public interface ISomeInterfaceInstances
{
    ISomeInterface someInterface1 { get; }
    ISomeInterface someInterface2 { get; }
}

public class HomeController : Controller
{
    public HomeController(IRepository repository, ISomeInterfaceInstances someInterfaces, IConfiguration configuration)
    {
        // Code
    } 
}

This is just idea, but implementation could be various 这只是一个想法,但实施可能是多种多样的

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

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM