Reputation: 203
In the following unit tests, TestDirectRetrieval_WithNoImplementations
and TestInjection_WithNoImplementations
fail
[TestFixture]
public class KernelTests
{
[Test] //Passes
public void TestDirectRetrieval_WithMultipleImplementations()
{
//Arrange
var kernel = new StandardKernel();
kernel.Bind<Foo>().ToConstant(new Foo("a"));
kernel.Bind<Foo>().ToConstant(new Foo("b"));
//Act + Assert
Assert.DoesNotThrow(() => kernel.GetAll<Foo>().ToList());
}
[Test] //Passes
public void TestInjection_WithMultipleImplementations()
{
//Arrange
var kernel = new StandardKernel();
kernel.Bind<Foo>().ToConstant(new Foo("a"));
kernel.Bind<Foo>().ToConstant(new Foo("b"));
//Act + Assert
Assert.DoesNotThrow(() => kernel.Get<Bar>());
}
[Test] //Fails
public void TestDirectRetrieval_WithNoImplementations()
{
//Arrange
var kernel = new StandardKernel();
//Act + Assert
Assert.DoesNotThrow(() => kernel.GetAll<Foo>().ToList());
}
[Test] //Fails
public void TestInjection_WithNoImplementations()
{
//Arrange
var kernel = new StandardKernel();
//Act + Assert
Assert.DoesNotThrow(() => kernel.Get<Bar>());
}
#region Test helper classes
class Foo
{
public Foo(string someArgThatCantBeAutomaticallyResolvedByNinject){}
}
class Bar
{
private List<Foo> myFoos;
public Bar(IEnumerable<Foo> foos)
{
myFoos = foos.ToList();
}
}
#endregion
}
In a scenario were someone is binding things to constants / implementations based on some dynamic situation, how can they support the case were nothing is bound at all?
Upvotes: 0
Views: 39
Reputation: 13243
GetAll
is not used by ninject for injection, but as you found out it provides the desired behavior. To enable injection with 0-n semantics I commonly roll my own "collection", an uncomplete / pseudo code version looks like this:
class OptionalItems<T> : IEnumerable<T>
{
private readonly T[] items;
public OptionalItems(IResolutionRoot resolutionRoot)
{
this.items = resolutionRoot.TryGetAll(T).ToArray();
}
public IEnumerator<T> GetEnumerator() {
return this.items.GetEnumerator();
}
}
Now inject OptionalItems
instead of IEnumerable<T>
or IList<T>
.
For testability-reasons it might make sense to create an interface for OptionalItems
: public interface IOperationalItems<T> : IEnumerable<T>
and bind that.
Upvotes: 1