ninject - 在 Ninject 中继承构造函数参数

标签 ninject ninject-2

我正在尝试找到一种将构造函数参数传递给子类的构造函数的方法。 这些对象是不可变的,因此我更喜欢使用构造函数参数。

我遇到的问题是 ConstructorArgument 不会继承到子实例化,并且以下语句不可互换:

_parsingProcessor = _kernel.Get<IParsingProcessor>(new ConstructorArgument("dataFilePath", dataFilePath);

_parsingProcessor = _kernel.Get<IParsingProcessor>(new Parameter("dataFilePath", dataFilePath, true);

那么,如何获得可继承的 ConstructorArgument 以及什么时候新建 Parameter 类才有意义(如果有的话)?

最佳答案

是的,您可以这样做,但这可能不是您真正想要的。如果容器实际上并不负责实例化自己的依赖项,那么它的依赖项可能不应该共享其构造函数参数 - 这没有意义。

我很确定我知道您要做什么,推荐的方法是专门为您的一个容器创建一个唯一的绑定(bind),并使用 WhenInjectedInto 条件绑定(bind)语法,如下所示在下面的示例中:

public class Hello : IHello
{
    private readonly string name;

    public Hello(string name)
    {
        this.name = name;
    }

    public void SayHello()
    {
        Console.WriteLine("Hello, {0}!", name);
    }
}

这个类接受我们想要修改的构造函数参数,具体取决于谁请求 IHello。假设这是一个无聊的容器类:

public class MyApp : IApp
{
    private readonly IHello hello;

    public MyApp(IHello hello)
    {
        this.hello = hello;
    }

    public virtual void Run()
    {
        hello.SayHello();
        Console.ReadLine();
    }
}

现在,以下是如何进行绑定(bind):

public class MainModule : NinjectModule
{
    public override void Load()
    {
        Bind<IApp>().To<MyApp>();
        Bind<IHello>().To<Hello>()
            .WithConstructorArgument("name", "Jim");
        Bind<IHello>().To<Hello>()
            .WhenInjectedInto<MyApp>()
            .WithConstructorArgument("name", "Bob");
    }
}

基本上,这个绑定(bind)所做的就是说name应该是“Jim”除非它是由Hello请求的,在本例中是这样的确实如此,因此它将获得名称“Bob”。


如果您绝对确定您确实想要级联行为,并且了解这是非常危险且脆弱,那么您可以使用方法绑定(bind)进行欺骗。假设我们现在出于某种未指定的目的向 MyApp 类添加了一个 name 参数,则绑定(bind)将为:

Bind<IHello>().ToMethod(ctx =>
    ctx.Kernel.Get<Hello>(ctx.Request.ParentContext.Parameters
        .OfType<ConstructorArgument>()
        .Where(c => c.Name == "name")
        .First()));

请务必在执行此操作之前确保您确信这是您想要的。它看起来很简单,但在简单的重构过程中也很可能会被破坏,而且我见过的 95% 的“自定义依赖”场景都可以使用 WhenInjectedInto 绑定(bind)来解决。

关于ninject - 在 Ninject 中继承构造函数参数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5300346/

相关文章:

c# - Ninject 和 WCF - 初始化控制反转容器的正确方法

ninject - 在 Ninject 2 中,如何让两个具有不同设置的内核共享绑定(bind)?

.net - 在 Ninject 中将单例绑定(bind)到多个服务

c# - Ninject 传递实现接口(interface)的类的构造函数参数 typeof

asp.net-mvc-3 - Ninject 和 MVC3 Controller 和操作上的依赖注入(inject)操作过滤器存在问题

c# - 注入(inject) ActivationException : Error activating IAlertManagement

c# - ASP.NET MVC 3 : DefaultModelBinder with inheritance/polymorphism

asp.net-mvc-3 - ASP.NET MVC 3 和全局过滤器注入(inject)

ninject - V2 Ninject 绑定(bind)到 V3 的转换