Inject generic interface in .NET Core


Solution 1

1.) if you want to write hard code

services.AddScoped<IDatabaseService<Project>, ProjectService>();

2.) if you want to register dynamically that all types of implemented IDatabaseService<>

            .Where(item => item.GetInterfaces()
            .Where(i => i.IsGenericType).Any(i => i.GetGenericTypeDefinition() == typeof(IDatabaseService<>)) && !item.IsAbstract && !item.IsInterface)
            .ForEach(assignedTypes =>
                var serviceType = assignedTypes.GetInterfaces().First(i => i.GetGenericTypeDefinition() == typeof(IDatabaseService<>));
                services.AddScoped(serviceType, assignedTypes);

Solution 2

You can do this by adding the below line in Startup.cs

// best practice  

Visit Here to know more about Dependency injection in ASP.NET Core

Solution 3

You can use services.AddScoped to use only 1 instance in the scope request. So in general improvement compare to AddTransient

services.AddScoped(typeof(IGenericRepository<>), typeof(GenericRepository<>));

So my interface and class will look like this

public interface IGenericRepository<T> where T : class
public class GenericRepository<T> : IGenericRepository<T> where T : class

Solution 4

Feel free to use helpers:

by Generic interface

services.AddAllGenericTypes(typeof(IDatabaseService<>), new[] {typeof(ProjectService).GetTypeInfo().Assembly});

With extensions from:

Author by


Updated on July 09, 2022


  • michasaucer
    michasaucer 11 months

    I want to inject this interface to my controllers:

    public interface IDatabaseService<T>
        IEnumerable<T> GetList();

    I want to use generic, because in my WebApi project i have controllers like ProjectController, TaskController etc and i want to use generic interface to each of type (for example, IDatabaseService<Project>, IdatabaseService<Task> etc).

    Class, that will be injected to controller will look like this:

    public class ProjectService : IDatabaseService<Project>
        private readonly DbContext context;
        public ProjectService(DbContext context)
            this.context = context;
        public IEnumerable<Project> GetList() { }

    But when I try to ineject in my Startup.cs:


    I need to pass T type.

    My question is, how to make injection generic and how inject it properly in controller? For example:

    public class ProjectController : ControllerBase
        private readonly ProjectService projectService;
        public ProjectController (IDatabaseService<Project> projectService)
            this.projectService = projectService;

    If it will work? And is it good practice to make generic interface to inject into controllers? If no, how to do it better?

  • Tseng
    Tseng about 4 years
    services.AddTransient<IDatabaseService<T>, DatabaseService<T>>(); this isnt going to work with a generic type, you'd have to add the concrete type instead of T. When using generic parameters, they must be known at compile time. Second line is the only way to register it w/o knowing and defining the concrete type(s) (per type registration)
  • michasaucer
    michasaucer about 4 years
    I wanted to work only on DbSet with Projects in my mind, so how it work in "real life" scenerios? Its better to deal with one IDatabaseService and DatabaseService if each one controller? I think ProjectController dont need to have (for example) reference to Tasks
  • Voodoo
    Voodoo about 4 years
    Thanks for the comments. I have removed the wrong example.
  • michasaucer
    michasaucer about 4 years
    Thanks, but as you can see in my quesion, i wan to have classes like TaskService : IDatabaseService<Task> and ProjectService : IDatabaseService<Project>. I dobt have 'DatabaseService' class
  • michasaucer
    michasaucer about 4 years
    Could you provide more complex explenation about second paragraph?
  • levent
    levent about 4 years
    If you have a large number of services that implement the IDatabaseService<> interface, it provides to find and register all of them.
  • mehmetgelmedi
    mehmetgelmedi about 3 years
    Such as this use case, how we handle? public class GenericRepository<T, U> : IGenericRepository<T> where T : class where U class I tried below code but runtime error services.AddScoped(typeof(IGenericRepository<>), typeof(GenericRepository<,>));
  • Tony Ngo
    Tony Ngo about 3 years
    You can read my blog for full source code…
  • Victorio Berra
    Victorio Berra over 2 years
    Can Scrutor do this?
  • Jethro Cao
    Jethro Cao about 1 year
    Is the use of reflection then iterating over all service types to AddScoped a one time cost at application startup? My hunch says yes, but just want to confirm.