Avoiding multiple bindings with Ninject Extensions inheritance

566 Views Asked by At

I have classes that create a hierarchy such as this:

public interface IHandler<T, T2> {
}

public class BaseHandler : IHandler<T, T2> {
}

public class DerivedHandler : BaseHandler {
}

Basically, the idea is that the functionality can be stacked (each derived level will append more functionality).

I am trying to use the Ninject Conventions Extensions to bind this in a nice way. What I have is this:

kernel.Bind(
    x =>
        x.FromAssemblyContaining(typeof(IHandler<,>))
         .SelectAllClasses()
         .EndingWith("Handler")
         .BindAllInterfaces());

This works flawlessly when I request the DerivedHandler. Ninject doesn't complain at all. However, when I request a BaseHandler, I am presented with a:

More than one matching bindings are available.

Obviously the conventions extension is accounting for the inheritance. When I request a BaseHandler.. should it give me a BaseHandler or a DerivedHandler? (I want the BaseHandler..).

Is there a way to avoid this? I have tried all sorts of combinations of the fluent syntax and I can either get the "Multiple bindings" error.. or "No bindings found" error.

Note that this works perfectly if I manually bind each one. I assume that proves there is no issue with Ninject handling this.. its just the Conventions.

1

There are 1 best solutions below

1
On

In your example you are requesting the concrete (class-)type you want to be instantiated.

Instead of binding .BindAllInterfaces() you need to use .BindToSelf() in the convention.

However, if you don't need to configure the binding any further (like .InSingletonScope(), or .OnActivation()...) you can also omit the binding, because whenever you are requesting a class-type which is unbound, ninject will try to instanciate the requested type.

Full Example:

kernel.Bind(x => x
     .FromAssemblyContaining(typeof(IHandler<,>))
     .SelectAllClasses()
     .EndingWith("Handler")
     .BindToSelf());