C# 简单注射器条件注射

C# 简单注射器条件注射,c#,.net,dependency-injection,simple-injector,C#,.net,Dependency Injection,Simple Injector,假设我有两个控制器:ControllerA和ControllerB。这两个控制器都接受IFooInterface作为参数。现在我有两个IFooInterface的实现,FooA和FooB。我想在ControllerA中注入FooA,在ControllerB中注入FooB。这在Ninject中很容易实现,但由于性能更好,我将转向简单的喷油器。那么,如何在简单的喷油器中实现这一点呢?请注意,ControllerA和ControllerB位于不同的程序集中,并动态加载 谢谢,SimpleInjecto

假设我有两个控制器:ControllerA和ControllerB。这两个控制器都接受IFooInterface作为参数。现在我有两个IFooInterface的实现,FooA和FooB。我想在ControllerA中注入FooA,在ControllerB中注入FooB。这在Ninject中很容易实现,但由于性能更好,我将转向简单的喷油器。那么,如何在简单的喷油器中实现这一点呢?请注意,ControllerA和ControllerB位于不同的程序集中,并动态加载


谢谢,SimpleInjector文档称之为。从版本3开始,您将使用
注册表条件
。从2.8版开始,SimpleInjector中没有实现此功能,但是文档中包含了对
容器
类的扩展

使用这些扩展方法,您可以执行以下操作:

Type fooAType = Assembly.LoadFrom(@"path\to\fooA.dll").GetType("FooA");
Type fooBType = Assembly.LoadFrom(@"path\to\fooB.dll").GetType("FooB");
container.RegisterWithContext<IFooInterface>(context => {
    if (context.ImplementationType.Name == "ControllerA") 
    {
        return container.GetInstance(fooAType);
    } 
    else if (context.ImplementationType.Name == "ControllerB") 
    {
        return container.GetInstance(fooBType)
    } 
    else 
    {
        return null;
    }
});
Type fooAType=Assembly.LoadFrom(@“path\to\fooA.dll”).GetType(“fooA”);
类型fooBType=Assembly.LoadFrom(@“path\to\fooB.dll”).GetType(“fooB”);
container.RegisterWithContext(context=>{
if(context.ImplementationType.Name==“ControllerA”)
{
返回container.GetInstance(fooAType);
} 
else if(context.ImplementationType.Name==“ControllerB”)
{
return container.GetInstance(fooBType)
} 
其他的
{
返回null;
}
});

自版本3以来,简单喷油器具有注册条件方法

container.RegisterConditional<IFooInterface, FooA>(c => c.Consumer.ImplementationType == typeof(ControllerA));
container.RegisterConditional<IFooInterface, FooB>(c => c.Consumer.ImplementationType == typeof(ControllerB));
container.RegisterConditional<IFooInterface, DefaultFoo>(c => !c.Handled);
container.registerCondition(c=>c.Consumer.ImplementationType==typeof(ControllerA));
container.registerCondition(c=>c.Consumer.ImplementationType==typeof(ControllerB));
容器注册条件(c=>!c.Handled);

这个问题在Stackoverflow上多次出现,我有责任对这种设计提出质疑。尽管这样的设计并不总是错误的,但您必须小心不要违反Liskov替换原则。所以问题是,当ControllerA被注入FooB时,它是否仍然有效,或者它是否中断?如果它坏了,你违反了LSP,这意味着FooA和FooB应该各自实现一个不同的接口。@Steven谢谢,你给了我一些想法:)@Steven再想一想,当注入FooB时ControllerA仍然可以工作,从这个角度看,原则上我可以减少控制器的数量。问题是,控制器向IFooInterface提供来自数据库的一些数据,这与FooA和FooB不同,因此它应该知道从db中选择哪些数据。由于站点的规则,通常很难讨论Stackoverflow上的应用程序设计。如果您感兴趣,可以在simpleinjector.codeplex.com论坛上用一些具体的代码示例开始新的讨论(而不是使用诸如IFoo和Controller1之类的抽象名称)。该论坛上有很多开发人员(比如我和qujck),他们渴望与您讨论设计并给您一些反馈。