ASP.NET Core实现自定义中间件的三种方式
一、什么是中间件
请求处理管道由一系列中间件组件组成。每个组件在 HttpContext
上执行操作,调用管道中的下一个中间件或终止请求。
详情请看另外一篇文章:白话管道中间件
下图是中间件的管道模型图,有点类似过滤器。
二、中间件可以用来做什么?
在我们的应用程序当中和业务关系不大的一些需要在管道中做的事情可以使用,比如身份验证,Session存储,日志记录,定时任务等。.NET自带很多中间件,比如身份认证中间件UseAuthorization,Session中间件等。并且中间件可以自定义。
三、自定义中间件
当系统自带的中间件不能满足我们需求时,我们可以自定义中间件来实现功能,比如自己开发的定时任务等。注册中间件的方式可以使用use和run,use可以快速注册中间件,而run是终端中间件,是中间件管道末尾,当注册该中间件后,后面的中间件将不再执行。下面介绍三种自定义中间件的方式。
1、自定义匿名中间件
自定义匿名中间件在Program.cs文件中就可以实现,可以通过use和run来自定义匿名中间件。案例如下:
app.Use(async (context, next) =>
{
Console.WriteLine("测试匿名中间件");
await next();
});
//如果shi用app.run将在这里结束。
还可以通过useWhen创建子集中间件。如下代码
//UseWhen有点类似if,这里是如果访问/put或者/put/xxx会调用该中间件。
app.UseWhen(context => context.Request.Path.StartsWithSegments("/put"), app =>
{
app.Use(async (context, next) =>
{
Console.WriteLine("测试UseWhen匿名中间件");
await next();
});
});
使用注意:如果有下一个中间件,一定记得调用next(),否则会导致管道短路,后面的中间件不再被执行;如果有response操作不能调用next(),否则会报错。
2、基于工厂的中间件
基于工厂中间件需要通过IMiddleware接口实现,然后在通过UseMiddleware注册后在Program.cs文件中依赖注入。代码如下:
//通过实现IMiddleware接口
public class Middleware:IMiddleware
{
public async Task InvokeAsync(HttpContext context, RequestDelegate next)
{
//下一个之前执行
Console.WriteLine("测试基于工厂的中间件(欢迎公众号:DOTNET开发跳槽)");
await next(context);
//下一个中间件处理完之后执行
Console.WriteLine("基于工厂的中间件运行结束");
}
}
public static class MiddlewareExtensions
{
public static IApplicationBuilder Middleware(this IApplicationBuilder builder)
{
//需要注册一下才能使用
return builder.UseMiddleware<Middleware>();
}
}
//在Program.cs中注册和注入
builder.Services.AddSingleton<Middleware>();
app.Middleware();
3、基于约定中间件
主要通过RequestDelegate来实现管道传递,关键代码如下。
public class TestMiddleware
{
public RequestDelegate _requestDelegate;
public TestMiddleware(RequestDelegate requestDelegate)
{
_requestDelegate = requestDelegate;
}
public async Task InvokeAsync(HttpContext context)
{
//下一个之前执行
Console.WriteLine("测试约定中间件开始,(欢迎公众号:DOTNET开发跳槽)");
await _requestDelegate(context);
}
}
//在Program.cs中注册
app.UseMiddleware<TestMiddleware>();
执行效果如下:
结语
本文讲述了自定义中间件的三种实现方式,自定义匿名中间件、基于工厂中间件和约定中间件。如果是比较小的功能,可以使用匿名中间件,比如过滤请求的链接;基于工厂中间件和约定中间件建议比较大的功能使用,从便利上来说推荐约定中间件。这是小编在使用中间件的个人总结,仅供参考。希望本文对你有所收获,对于自定义中间件你有啥看法,欢迎留言讨论或吐槽。
本文来自博客园,作者:{春光牛牛,yak},转载请注明原文链接:https://www.cnblogs.com/yakniu/p/17011221.html
欢迎各位大佬们评论指正
QQ讨论群:610129902