Search code examples
c#.netmodel-view-controllerdependency-injection

Constructor Injection (Dependency Injection) in a class (NOT Controller Class) in .net core


I am struggling to understand how I can utilize dependency injection in this scenario.

Let me introduce my files one by one.

A contract called ITxtManipulator.cs

public interface ITxtManipulator
{
    public string StringCapitalize(string incoming_string);
}

A class called TxtManipulatorA.cs This implements the ITxtManipulator interface

public class TxtManipulatorA : ITxtManipulator
{
    public string StringCapitalize(string incoming_string)
    {
        return incoming_string.ToUpper();
    }
}

This is program.cs where I registered dependency injection

var builder = WebApplication.CreateBuilder(args);

builder.Services.AddScoped<ITxtManipulator, TxtManipulatorA>();   // <------- HERE

builder.Services.AddControllers();

var app = builder.Build();

app.UseHttpsRedirection();
app.UseAuthorization();
app.MapControllers();
app.Run();

I have an application layer. I created a class called SomeApplication.cs This is where I want to invoke ITxtManipulator object and use it a method. I tried to use Constructor Injection.

public class SomeApplication
{
    private readonly ITxtManipulator _magicTxtManipulator;
    
    public SomeApplication(ITxtManipulator dotnetGiveTxtManipulator)
    {
        _magicTxtManipulator = dotnetGiveTxtManipulator;
    }

    public string GetStudentDefault()
    {
        return _magicTxtManipulator.StringCapitalize("raj");
    }
}

Finally I want to invoke method 'GetStudentDefault()' in the StudentController.cs. This is where I am stuck and getting error.

[ApiController]
[Route("api/[controller]")]
public class StudentController : ControllerBase
{
    public string Get()
    {
        return new SomeApplication().GetStudentDefault();  // <--- COMPILE ERROR
    }
}

Giving me error! (I couldn't execute the code itself) Since the constructor of SomeApplication expects an argument (ITxtManipulator) which I cannot pass and dotnet has to provide.

I do not want to use dependency injection in the controller class.

I want to do dependency injection in Application Layer (SomeApplication.cs) and then invoke the method in the controller class to achieve separation of concerns.

Can someone suggest a way to leverage dependency injection and satisfy my architectural requirement in this scenario?


Solution

  • You are actually calling the constructor from a Controller. This means you can inject the ITxtManipulator in the Controller's constructor, set a field with that value and add it to the constructor parameters of SomeApplication. Your StudentController class would then look like this:

    [ApiController]
    [Route("api/[controller]")]
    public class StudentController : ControllerBase
    {
        private ITxtManipulator _manipulator;
        public StudentController(ITxtManipulator manipulator) 
        {
            _manipulator = manipulator;
        }
        
        [HttpGet]
        public string Get()
        {
            return new SomeApplication(_manipulator).GetStudentDefault();
        }
    }