app.Use vs app.Run in ASP.NET Core middleware

Earlier I posted quick summary of what’s changed in ASP.NET Core and one of the biggest change is Introduction of middleware. If you are coming from ASP.NET background then you should be aware about HTTPHandlers and HTTPModules. Middleware are replacement of these things. It’s a new and cleaner approach to play with HTTP pipeline. Read my post How ASP.NET Core 1.0 Middleware is different from HttpModule.

Along with built-in middleware, there are 2 options to define inline middleware using app.Use and app.Run extension methods. And if you are currently working and playing with ASP.NET Core 1.0 then you may find examples of app.Use and app.Run in configure() method of Startup.cs class. Both of them are used for same purpose but they are different. How?

app.Use vs app.Run in ASP.NET Core middleware

Middleware are executed in the same order in which they are added. The difference is, middleware defined using app.Use may call next middleware component in the pipeline. On the other hand, middlware defined using app.Run will never call subsequent middleware. Let’s see via code.

Create a new ASP.NET Core 1.0 web application and change the Startup.configure method to below code. The following example defines 2 inline middleware using app.Use and one using app.Run. The first middleware defined using app.Use writes HTML to response object asynchronously, calls next middleware and again writes closing HTML. And middleware defined using app.Run writes message and then returns. And after app.Run middlware, we defined another inline middleware using app.Use and also using some of the built-in middleware.

public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
{
    app.Use(async (context, next) =>
    {
        await context.Response.WriteAsync("<html><body>");
        await context.Response.WriteAsync("<div>Inside middleware defined using app.Use</div>");
        await next();
        await context.Response.WriteAsync("</body></html>");
    });

    app.Run(async context => { 
       await context.Response.WriteAsync("<div>Inside middleware defined using app.Run</div>"); 
    });

    app.Use(async (context, next) =>
    {
        await context.Response.WriteAsync("<html><body>");
        await context.Response.WriteAsync("<div>Another Middleware defined using app.Use</div>");
        await next();
        await context.Response.WriteAsync("</body></html>");
    });
    app.UseIISPlatformHandler(options => options.AuthenticationDescriptions.Clear());
    app.UseStaticFiles();
    app.UseIdentity();
    app.UseMvc(routes =>
    {
        routes.MapRoute(
            name: "default",
            template: "{controller=Home}/{action=Index}/{id?}");
    });
}

And as expected following is the output when you run the application.

app.Use vs app.Run in ASP.NET Core middleware

As I told you earlier, middleware defined after app.Run will not be executed. And that’s why you don’t get the response of second app.Use middleware.

Thank you for reading. Keep visiting this blog and share this in your network. Please put your thoughts and feedback in comments section.

Leave a Reply

Your email address will not be published. Required fields are marked *

12 + two =