Peter Hurtony
Peter Hurtony

Reputation: 470

Resolve dependencies from inherited classes with Autofac

First of all, let me provide some sample code:

public abstract class BaseEntity { }
public class MyEntity : BaseEntity { }
public class MyCustomEntity : BaseEntity { }

public interface IStore<TEntity> where TEntity : BaseEntity { }
public class BaseStore<TEntity> : IStore<TEntity> where TEntity : BaseEntity { }
public class MyCustomEntityStore : BaseStore<MyEntity> { }

So basically I have an abstract entity and two derived types. I created a repository class which is hiding all the basic stuff around the BaseEntity (for example fill the "LastModifiedBy" property). But for some cases, I need specific behaviour to saving an entity, so I need to derive from the BaseStore, and implement the custom behaviour in MyCustomEntityStore. So far, it is easy.

The problem is i would like to use Autofac to resolve dependencies in my application. My goal would be to do this:

public class SomeClass {
    private readonly IStore<MyEntity> MyEntityStore;
    private readonly IStore<MyCustomEntity> MyCustomEntityStore;

    public SomeClass(IStore<MyEntity> mes, IStore<MyCustomEntity> mces)
    {
        MyEntityStore = mes;
        MyCustomEntityStore = mces;
    }
}

I would like to inject an instance of BaseStore<MyEntity> to IStore<MyEntity> and MyCustomEntityStore to IStore<MyCustomEntity>. This is working fine with the MyCustomEntityStore (which has a concrete implementation derived from the base store), but i do not want to create empty classes just to inherit the BaseStore<MyEntity>. I registered my components like this:

builder.RegisterAssemblyTypes(Assembly.Load("Project.Data")).Where(t => t.Name.EndsWith("Store")).AsImplementedInterfaces().InstancePerRequest();

Although these instances can be in the place of these interfaces, Autofac can not resolve the IStore<MyEntity>.

Thanks for all the help!

Upvotes: 1

Views: 1998

Answers (1)

Peter Hurtony
Peter Hurtony

Reputation: 470

I managed to solve the problem with this registering:

builder.RegisterGeneric(typeof(BaseStore<>))
       .As(typeof(IStore<>))
       .InstancePerRequest();
builder.RegisterAssemblyTypes(Assembly.Load("Project.Data"))
       .Where(t => t.Name.EndsWith("Store"))
       .AsImplementedInterfaces()
       .InstancePerRequest();

Can anyone confirm, this is the right way?

Upvotes: 1

Related Questions