【问题标题】:Ninject bind mulitple implementations to an interfaceNinject 将多个实现绑定到一个接口
【发布时间】:2012-12-24 16:52:24
【问题描述】:

我正在查看本教程,但不太了解如何创建一个可以为我提供接口的单独实现的工厂。

http://stefanoricciardi.com/2011/01/21/ninject-mini-tutorial-part-1/

public class IJob {
  ...
}

public class JobImpl1 : IJob {
  ...
}

public class JobImpl2 : IJob {
  ...
}

using (IKernel kernel = new StandardKernel()) {
    kernel.Bind<IJob>().To<JobImpl2>(); 
    var job = kernel.Get<IJob>();
}

我的目标是创建一个包装这个 Ninject Kernel 的工厂类,这样我就可以根据我是在单元测试环境还是实时环境中提供不同的 IJob 接口实现。但是,我还想将 Ninject 隐藏在工厂包装器中,以便其余代码不会依赖于 Ninject。

【问题讨论】:

    标签: c# dependency-injection inversion-of-control ninject


    【解决方案1】:

    有一个单独的扩展 Ninject.Extensions.Factory 允许您基于 interface

    即时生成 Abstract Factory 实现

    内核配置

    var kernel = new StandardKernel();
    
    // wire concrete implementation to abstraction/interface
    kernel.Bind<IJob>().To<JobImpl1>()
        .NamedLikeFactoryMethod<IJob, IJobFactory>(f => f.GetJob());
    
    // configure IJobFactory to be Abstract Factory
    // that will include kernel and act according to kernel configuration    
    kernel.Bind<IJobFactory>().ToFactory();
    

    在运行时使用内核解析抽象工厂

    // get an instance of Abstract Factory
    var abstractFactory = kernel.Get<IJobFactory>();
    
    // resolve dependency using Abstract Factory
    var job = abstractFactory.GetJob()
    

    抽象工厂接口

    public interface IJobFactory
    {
        IJobFactory GetJob();
    }
    

    【讨论】:

    • 这感觉好像走在了正确的轨道上,但我需要的是能够在同一个环境中拥有同一个接口的多个实现。一个例子是我需要多个 IVehicle 接口的实现(卡车、汽车、摩托车等)
    • 将新方法签名添加到Abstract Factory并使用NamedLikeFactoryMethod配置映射