Is it possible to inject a list of dependencies like this in Unity or other kind of IoC libraries?
public class Crawler
{
public Crawler(IEnumerable<IParser> parsers)
{
// init here...
}
}
In this way I can register multiple IParser in my container and then resolve them.
Is it possible? Thanks
yes you can.. you can look at dependency injectors. I am a big fan of the Autofac project.
Another option is Ninject,
As a matter of fact, I don't know any container that does not support this.
However, as a general advice, you should prevent injecting lists of services into consumers if you can, by wrapping that list in a composite, and inject that composite into consumers. Not wrapping the list in a composite would clutter the application with extra
foreach
loops or what ever you need to do to process that list of dependencies. While this doesn't seem bad, the consumers of these dependencies shouldn't care. But worse, when we want to change the way the list of services is handled, we will have to go through the complete application, which is a violation of the DRY principle.This advice does not hold when the consumer (in your case the
Crawler
) is part of the Composition Root instead of the application itself. Further more, when the application only has a single consumer that takes this dependency, it might not be that big of deal.Not that I'm saying it's wrong but it seems like you are trying to solve a plugin model that you could easily manage with the use of MEF instead. Hints would be inherited Export from the interface and then do ImportMany when you need the parsers.
There are ways to achieve this in Unity. For example,
http://sharpsnmplib.codeplex.com/SourceControl/changeset/view/5497af31d15e#snmpd%2fapp.config
This constructor requires an array of User objects, and all such objects defined in this container are injected by Unity into it when the UserRegistry object is created.
It is possible but you need to apply some workarounds. First you need to register each IParser with a name in the Unity Container. Second you need to register a mapping from IParser[] to IEnumerable<IParser> in the container. Otherwise the container cannot inject the parsers to the constructor. Here´s how i have done it before.
I have discarded this solution by introducing a factory, that encapsulates unity to construct the needed types. Here´s how i would do it in your case.
With this you can register the types as follows: