【问题标题】:Ninject Binding, Interface to InterfaceNinject 绑定,接口到接口
【发布时间】:2011-11-28 23:05:07
【问题描述】:

我想做一些类似的事情:

kernel.Bind<IBootTaskA>().To<BootTaskA>().InSingletonScope();
kernel.Bind<IBootTaskB>().To<BootTaskB>().InSingletonScope();

kernel.Bind<IBootTask>().To<IBootTaskA>();
kernel.Bind<IBootTask>().To<IBootTaskB>();

所以我可以这样做:

public class Boot
{
     public Boot(IBootTask[] bootTasks)
     {
          foreach(var task in bootTasks){task.Execute();}
     }
}

但我似乎无法将接口绑定到接口,有人知道解决方法吗?

【问题讨论】:

标签: c# binding dependency-injection ninject


【解决方案1】:

这就是你的做法。

public class Service : IServiceA, IServiceB {}

this.Bind<Service>().ToSelf().InSingletonScope();
kernel.BindInterfaceToBinding<IServiceA, Service>();
kernel.BindInterfaceToBinding<IServiceB, Service>();

ninject 扩展处理你需要的东西。

https://github.com/ninject/ninject.extensions.contextpreservation/wiki/Bind-Interface-to-Binding

编辑:

在 ninject 3 中这稍微容易一些,您不再需要上下文保存,简单地说:

Bind<IServiceA,IServiceB>().To<Service>().InSingletonScope();

【讨论】:

    【解决方案2】:

    更新:The V3 Bind overloads 解决了很多这样的问题。


    Ninject 没有任何这种性质的构造(我也不知道其他容器也有这样的系统)。

    我怀疑某种形式的Conditional Bindings 可能最适合您的实际问题(我假设您并没有像您展示的那样真正拥有通用的标记界面)。

    或者你只是想找到一个结构来保持你的绑定干燥?我个人会将上述内容表达为两个绑定,使用自定义 .WithStandardTaskProperties 扩展方法,而不是 4 行。

    【讨论】:

    • 引发此问题的真正问题是我实际上需要在其他地方以及引导加载程序中注入这些内容。这意味着我实际上需要 2 个不同的实例绑定,一个是要加载一个通用列表,然后还要让一个单独的实例起作用。问题是,如果我单独绑定它们,它们将转到不同的单例实例。
    • 环顾四周 - 今年这个标签中有两个答案,其中有演示 Bind... .ToBinding (IIRC) 构造的答案 - 一个来自 @Remo Gloor 的答案(如果您以任何方式使用 Ninject,无论如何,您都应该首先阅读他的所有热门答案)
    • Ta 表示赞成(你的答案是我很久以前的答案)——我在过去的答案 obv 并没有多大用处。我已经添加了相关:顶部链接,并且有一个或两个绑定多个接口问题需要投票关闭。这个问题非常不同,足以保证留下[和自学徽章的一个很好的例子!]。