Search code examples
c#asp.net-coremiddleware

Middleware Invoke called only on Request (but not on Response)


I have a controller action that when called from client goes through the JwtMiddleware Invoke method. But when I return from the action using BaseController Ok method method Invoke is not called. Is that correct behaviour?


Solution

  • Yes. As described in the docs the middleware class must include:

    • A public constructor with a parameter of type RequestDelegate.
    • A public method named Invoke or InvokeAsync. This method must:
      • Return a Task.
      • Accept a first parameter of type HttpContext.

    And sample Invoke(Async) method can look like this:

    public async Task InvokeAsync(HttpContext context)
    {
        // Do something before the next delegate/middleware
        // ...
    
        // Call the next delegate/middleware in the pipeline. 
        // (actually can be not invoked in some cases, i.e. if request is already handled by current middleware)
        await _next(context);
    
        // Do something after the next delegate/middleware in the pipeline has finished.
        // ...
    }
    

    So the pipeline is architectured in a way that the Invoke(Async) method itself is called once per middleware registration during the request, but it can handle/process the request before and after next registered delegate/middleware in the pipeline.

    There is another alternative to middlewares for MVC (they are introduced for Minimal APIs in not released yet .NET 7 also but look more like endpoint specific middlewares) called filters which allow to distinguish between before and after action execution:

    enter image description here

    public class SampleActionFilter : IActionFilter
    {
        public void OnActionExecuting(ActionExecutingContext context)
        {
            // Do something before the action executes.
        }
    
        public void OnActionExecuted(ActionExecutedContext context)
        {
            // Do something after the action executes.
        }
    }