Home > Blockchain >  How to inject a specific implementation in asp.net core
How to inject a specific implementation in asp.net core

Time:05-23

I have a Repository which has a dependency of User

I need to put other implementation of User and I can do it like that, but with this approach I do not know how to mock my repository

private readonly IRepository<Entity> _repository;

public SomeClass(MyAppDbContext context)
{
  _repository= new EfRepository<WorkOrder>(context, new User());
}

Is there a way to inject a specific implementation of User here, or how I can test the code I wrote

CodePudding user response:

Just as you inject MyAppDbContext into SomeClass you can also inject an instance of User, e.g.

private readonly IRepository<Entity> _repository;

public SomeClass(MyAppDbContext context, User user)
{
  _repository= new EfRepository<WorkOrder>(context, user);
}

You can either register User in the IoC like this:

services.AddTransient<User>();

In case you have already registered a service for User and want to use another instance, you can register a factory method for SomeClass that sets up the User instance:

services.AddScoped<SomeClass>(prov => new SomeClass(
  prov.GetRequiredService<MyAppDbContext>(), 
  new User()));

The factory method approach is viable if you only have a few spots that need the special instance, otherwise you can use this approach: Unlike other IoCCs, the .NET Core IoCC does not support named registrations, but you can also use some kind of "marker interface" to register another instance:

public interface ISpecialUser : IUser {}

public class User : IUser
{
  // ...
}

public class AnotherUser : ISpecialUser
{
  // ...
}

// ...
public SomeClass(MyAppDbContext context, ISpecialUser user)
{
  _repository= new EfRepository<WorkOrder>(context, user);
}


// ...
services.AddScoped<IUser, User>();
services.AddScoped<ISpecialUser, AnotherUser>();

In the tests, you can set up an instance of User that suits your needs and use the new constructor parameter.

  • Related