中间件是被用到管道(pipeline)上来处理请求(request)和响应的(response)。app
asp.net core 自己提供了一些内置的中间件,可是有一些场景,你可能会须要写一些自定义的中间件。asp.net
1. 建立一个使用匿名委托的中间件组件的形式async
public class Startup { public void Configure(IApplicationBuilder app) { app.Use((context, next) => { var cultureQuery = context.Request.Query["culture"]; if (!string.IsNullOrWhiteSpace(cultureQuery)) { var culture = new CultureInfo(cultureQuery); CultureInfo.CurrentCulture = culture; CultureInfo.CurrentUICulture = culture; } // Call the next delegate/middleware in the pipeline return next(); }); app.Run(async (context) => { await context.Response.WriteAsync( $"Hello {CultureInfo.CurrentCulture.DisplayName}"); }); } }
注:app.use中return next()会传递到下一个中间件继续执行;而仅仅只使用app.use 的用法和app.run相同,即不会再传递到下一个中间件,在此做为请求处理的结束ui
2.把中间件的委托封装到类里面,即把中间件写成一个类的形式this
using Microsoft.AspNetCore.Http; using System.Globalization; using System.Threading.Tasks; namespace Culture { public class RequestCultureMiddleware { private readonly RequestDelegate _next; public RequestCultureMiddleware(RequestDelegate next) { _next = next; } public async Task InvokeAsync(HttpContext context) { var cultureQuery = context.Request.Query["culture"]; if (!string.IsNullOrWhiteSpace(cultureQuery)) { var culture = new CultureInfo(cultureQuery); CultureInfo.CurrentCulture = culture; CultureInfo.CurrentUICulture = culture; } // Call the next delegate/middleware in the pipeline await _next(context); } } }
而后,再使用一个中间件扩展方法,经过IApplicationBuilder使用中间件spa
using Microsoft.AspNetCore.Builder; namespace Culture { public static class RequestCultureMiddlewareExtensions { public static IApplicationBuilder UseRequestCulture( this IApplicationBuilder builder) { return builder.UseMiddleware<RequestCultureMiddleware>(); } } }
最后,在 Startup.Configure 中调用中间件.net
public class Startup { public void Configure(IApplicationBuilder app) { app.UseRequestCulture(); //调用中间件 app.Run(async (context) => { await context.Response.WriteAsync( $"Hello {CultureInfo.CurrentCulture.DisplayName}"); }); } }
另外,这里还有一点,这个地方不是很懂,说下本身的理解,欢迎大佬指正code
当中间件中注入的还有其余service(官方叫 a scoped service )时,须要使用的是Invoke方法,而不是InvokeAsync方法中间件
public class CustomMiddleware { private readonly RequestDelegate _next; public CustomMiddleware(RequestDelegate next) { _next = next; } // IMyScopedService is injected into Invoke public async Task Invoke(HttpContext httpContext, IMyScopedService svc) { svc.MyProperty = 1000; await _next(httpContext); } }
这里,Invoke和InvokeAsync是否是相同,仍是说就仅仅是命名不一样,其余用法都同样?blog
欢迎指正
参考网址:https://docs.microsoft.com/en-us/aspnet/core/fundamentals/middleware/write?view=aspnetcore-2.2