如何使用Ninject检索通用接口的所有绑定

时间:2011-11-11 17:03:38

标签: generics dependency-injection ninject ninject-2 ninject-extensions

使用Ninject 2.2,我有以下失败的测试(简化):

public interface IGenericView<T>
{
}

public interface IDefaultConvention
{
}

public class DefaultConvention : IDefaultConvention
{
}

public class DefaultConventionView : IGenericView<IDefaultConvention>
{ 
}

public class StringView : IGenericView<string>
{  
}

[TestFixture]
public class NinjectTests
{
    private static IKernel _kernel;

    [SetUp]
    public void Setup()
    {
        _kernel = new StandardKernel();
    }

    [Test]
    public void CanResolveAllClassesClosingOpenGenericInterface()
    {
        // Arrange
        _kernel.Bind<IDefaultConvention>().To<DefaultConvention>();
        _kernel.Scan(
            x =>
            {
                x.FromCallingAssembly();
                x.BindWith(new GenericBindingGenerator(typeof(IGenericView<>)));
            });

        // Act
        object target1 = _kernel.Get<IGenericView<IDefaultConvention>>();
        object target2 = _kernel.Get<IGenericView<string>>();

        // Assert
        Assert.IsAssignableFrom<DefaultConventionView>(target1);
        Assert.IsAssignableFrom<StringView>(target2);
        Assert.AreEqual(2, _kernel.GetAll(typeof(IGenericView<>)).Count()); // Always returns 0
    }
}

前两个断言通过,所以我知道类型本身被正确绑定,但我不能像我想的那样检索开放通用接口的所有绑定。这有可能吗?

1 个答案:

答案 0 :(得分:4)

不,这是不可能的。 Ninject应该从哪里知道允许哪些类型作为通用参数?假设你为什么认为2是正确的值?为什么不归还IGenericView<int>?此外,返回类型应该是什么? IEnumerable<IGenericView<>>不是允许的运行时类型。 IEnumerable<IGenericView<object>>可能不是人们所期望的。

GetAll为请求类型的每个绑定返回一个实例,在这种情况下只有一个实例。在这种情况下,您必须定义一个通用的非通用基接口,并为每种类型注册它,并为此接口调用GetAll。