0

I wrote a simple code in Asp.net. Adding Scoped service to builder generates this error:

System.InvalidOperationException
HResult=0x80131509
Message=Cannot resolve scoped service 'tasks.IMyLogger' from root provider.
Source=Microsoft.Extensions.DependencyInjection

My code is trivial:

var builder = WebApplication.CreateBuilder(args);
builder.Services.AddScoped<IMyLogger,ConsoleLogger>();

var app = builder.Build();

app.UseMiddleware<LogMiddleware>();

app.Run();

My Middleaware:

public class LogMiddleware
{
    private readonly RequestDelegate _next;
    private readonly IMyLogger _logger;

    public LogMiddleware(RequestDelegate next, IMyLogger logger)
    {
        _next = next;
        _logger = logger;
       
    }

    public Task Invoke(HttpContext httpContext)
    {
        _logger.Info("In Logger MiddleWare");
        return _next(httpContext);
    }
}

If I Try to add the service as singleton It works just fine.

I would love your assistance.

tal
  • 525
  • 2
  • 8
  • 26

2 Answers2

1

I assume you are trying to inject the logger into your custom middleware class?

Here is an example using a scoped service:

public class LogMiddleware
{
    private readonly RequestDelegate _next;

    public LogMiddleware(RequestDelegate next)
    {
        _next = next;
    }

    public async Task InvokeAsync(HttpContext context, IMyLogger logger)
    {
        // Use logger + other logic

        await _next(context);
    }
}

Note how we are injecting the logger in the InvokeAsync method? Since middleware classes are only instantiated once, you can only use singletons there. (I suppose transient will also work but it feels a bit odd to me)

If you need anything that is instantiated per request, you need to either add it to the InvokeAsync method signature or request for it from the HttpContext.

Documentation: https://learn.microsoft.com/en-us/aspnet/core/fundamentals/middleware/write?view=aspnetcore-7.0#per-request-middleware-dependencies

juunas
  • 54,244
  • 13
  • 113
  • 149
0

I found my error. scoped service cannot be injected to middleware constructor because middleware is a singleton.

injecting it to the Invoke method solved the problem.

    public class LogMiddleware
{
    private readonly RequestDelegate _next;

    public LogMiddleware(RequestDelegate next)
    {
        _next = next;
       
    }

    public Task Invoke(HttpContext httpContext, IMyLogger logger)
    {
        logger.Info("In Logger MiddleWare");
        return _next(httpContext);
    }
}

Cannot resolve scoped service from root provider in ASP.NET Core 6

tal
  • 525
  • 2
  • 8
  • 26