The use case that Simple Injector supports is to batch register a set of implementations by their related generic interfaces. In other words, by doing this:
container.RegisterManyForOpenGeneric(
typeof(IRepository<>),
typeof(StateRepository).Assembly);
You are basically registering a closed version of the IRepository<T>
interface as service, with its corresponding implementation. In other words, this will be equivalent to doing the following:
container.Register<IRepository<A>, RepositoryA>();
container.Register<IRepository<B>, RepositoryB>();
container.Register<IRepository<C>, RepositoryC>();
/* add more here */
Since you are not implementing the common use case, you will have to fall back to doing this manually. You can do this by writing the LINQ query as you already did, or you can make use of the OpenGenericBatchRegistrationExtensions.GetTypesToRegister
method to make this easier:
var repositoryTypes = OpenGenericBatchRegistrationExtensions.GetTypesToRegister(
container, typeof(IRepository<>), repositoryAssembly);
foreach (Type implementationType in repositoryTypes)
{
Type serviceType =
implementationType.GetInterfaces().Where(i => !i.IsGenericType).Single();
container.Register(serviceType, implementationType, Lifestyle.Transient);
}
Do make sure though that you understand that you are violating the SOLID principles by implementing custom interfaces on your repositories. It be beneficial to prevent such violation. Take a look at this article for more information about this.