I\'ve been playing around with SimpleInjector and I\'m trying to register properly all command handlers.
Here is my code:
public interf
The Simple Injector API clearly separates between registrations for collections and one-to-one mappings. In your composition root, you are making the following registration:
container.RegisterCollection(typeof(ICommandHandler<>),
new[] { typeof(ICommandHandler<>).Assembly });
The API Documentation for RegisterCollection
states:
Registers a collection of serviceTypes, whose instances will be resolved lazily each time the resolved collection of serviceType is enumerated. The underlying collection is a stream that will return individual instances based on their specific registered lifestyle, for each call to
IEnumerator<T>.Current
. The order in which the types appear in the collection is the exact same order that the items were registered, i.e the resolved collection is deterministic.
In other words, you are allowing command handlers to be resolved as collections, by requesting IEnumerable<ICommandHandler<T>>
.
In your CommandDispatcher
however, you request a single ICommandHandler<T>
by calling container.GetInstance(handlerType)
. Since there is no one-to-one mapping for an ICommandHandler<T>
, Simple Injector informs you about this by throwing:
No registration for type
ICommandHandler<CreateUser>
could be found. There is, however, a registration forIEnumerable<ICommandHandler<CreateUser>>
; Did you mean to callGetAllInstances<ICommandHandler<CreateUser>>()
or depend onIEnumerable<ICommandHandler<CreateUser>>
?
To fix this, there are two options:
CommandDispatcher
by calling GetAllInstances(Type)
.Since there will always be a one-to-one mapping between a command and its handler (meaning: there will be exactly one handler per command), option 1 is the most obvious solution. So change your registration to the following:
// Use 'Register' instead of 'RegisterCollection'.
container.Register(typeof(ICommandHandler<>),
new[] { typeof(ICommandHandler<>).Assembly });