Simple injector Registration of all services from the namespace

My service interfaces have a Services.Interfaces namespace

The service interface implementation has a Web.UI.Services namespace

I have 2 implementations of a service, for example

  • IUserService that needs to register with UserService
  • ICountryService who needs to register with CountryService

This is how I am currently registering these services with SimpleInjector.

 container.Register<IUserService, UserService> (); container.Register<ICountryService, CountryService> (); 

Problem: if I have more than 100 services to exaggerate a little. I need to go and add a line for each service.

How can I register all implementations from one assembly in all interfaces from another assembly using Simple Injector?

+7
c # asp.net-mvc inversion-of-control ioc-container simple-injector
source share
2 answers

You can do this by querying the LINQ assembly and flip and register all types:

 var registrations = from type in typeof(UserService).Assembly.GetExportedTypes() where type.Namespace.StartsWith("Services.Interfaces") where type.GetInterfaces().Any() select new { Service = type.GetInterfaces().Single(), Implementation = type }; foreach (var reg in registrations) { container.Register(reg.Service, reg.Implementation); } 

This is described here .

If I have more than 100 services, to exaggerate a little. I need to go and add a line for each service.

If so, I would say that something is wrong with your design. The fact that you call your services IUserService and ICountryService is a sign that you are violating Single Responsibility , Open / closed, and Interface ICountryService Principles . This can cause serious maintainability problems.

For an alternative design, take a look at these two articles. The described design provides a much higher level of maintainability, greatly simplifies the registration of your services and makes the use of cross-cutting problems for playing with children (especially with Simple Injector).

+6
source share

You are looking for a "convention configuration." A simple injector triggers this Batch / Auto registration .

While the main DI containers provide an API for this, it seems that Simple Injector leaves it with us; With the reflection bit and LINQ, you can register types as a package, so Simple Injector does not provide a special API for this.

The idea is that you scan the assembly for specific types with some agreement, looking at whether it implements any interface; if so, register it.

Here's a sample extracted from the link above:

 var repositoryAssembly = typeof(SqlUserRepository).Assembly; var registrations = from type in repositoryAssembly.GetExportedTypes() where type.Namespace == "MyComp.MyProd.BL.SqlRepositories" where type.GetInterfaces().Any() select new { Service = type.GetInterfaces().Single(), Implementation = type }; foreach (var reg in registrations) { container.Register(reg.Service, reg.Implementation, Lifestyle.Transient); } 

You can modify this code to apply your conventions and register types in batch mode.

+7
source share

All Articles