ASP.NET Core 过滤器

过滤器

过滤器与中间件很相似,能够在某些功能前后执行,由此而形成一个管道

ASP.NET Core MVC 提供了5种类型的过滤器#

  • AuthorizationFilter:最先执行,用于判断用户是否授权如果未授权直接结束当前请求
  • ResourceFilter:在Authorization后执行,可以用来对请求判断是否执行Action
  • ActionFilter:在Action执行的前后执行,与Resource不同的是,它在模型绑定之后执行。
  • ExceptionFilter:用于捕获异常
  • ResultFilter:在最后执行,可以控制Action执行的结果

以上五种类型过滤器的工作顺序

中间件
AuthorizationFilter
ResourceFilter
ExceptionFilter
模型绑定
ActionFilter
Action
ActionFilter
ResultAction

快速入门#

Action过滤器将在Controller的Action执行之前和执行相应的方法

首先我们新建一个类,实现IActionFilter,查看IActionFilter里面会发现有两个接口

Copy
// // 摘要: // A filter that surrounds execution of the action. public interface IActionFilter : IFilterMetadata { // // 摘要: // Called after the action executes, before the action result. // // 参数: // context: // The Microsoft.AspNetCore.Mvc.Filters.ActionExecutedContext. void OnActionExecuted(ActionExecutedContext context); // // 摘要: // Called before the action executes, after model binding is complete. // // 参数: // context: // The Microsoft.AspNetCore.Mvc.Filters.ActionExecutingContext. void OnActionExecuting(ActionExecutingContext context); }

根据描述我们可得知第一个是在执行方法之后执行,第二个在执行方法之前执行

然后就可以写我们自己的过滤器啦

Copy
public class TestActionFilterAttribute : Attribute, IActionFilter { public void OnActionExecuted(ActionExecutedContext context) { Console.WriteLine("OnActionExecuted执行了"); } public void OnActionExecuting(ActionExecutingContext context) { Console.WriteLine("OnActionExecuting执行了"); } }

心细的小伙伴可能看到我这里还继承了Attribute,没错可以直接通过特性应用在方法或者类上表示对这个方法或者类进行过滤

Copy
[HttpGet] [TestActionFilter] public IActionResult Test() { Console.WriteLine("Action执行"); return Ok(new { msg = "OK" }); }
Copy
[Route("api/[controller]")] [ApiController] [TestActionFilter] public class TestController : ControllerBase { }

也可以在startupConfigureServices()里面进行添加,表示全局注册

Copy
public void ConfigureServices(IServiceCollection services) { services.AddControllers(options => options.Filters.Add(new WebApplication2.Utility.Filter.TestActionFilterAttribute())); }

执行结果

Copy
OnActionExecuting执行了 Action执行 OnActionExecuted执行了

多个过滤器执行时,会保持着先进后出的原则,例如

Copy
public class TestActionFilterAttribute : Attribute, IActionFilter { public void OnActionExecuted(ActionExecutedContext context) { Console.WriteLine("OnActionExecuted1执行了"); } public void OnActionExecuting(ActionExecutingContext context) { Console.WriteLine("OnActionExecuting1执行了"); } }
Copy
public class TestActionFilterAttribute2 : Attribute, IActionFilter { public void OnActionExecuted(ActionExecutedContext context) { Console.WriteLine("OnActionExecuted2执行了"); } public void OnActionExecuting(ActionExecutingContext context) { Console.WriteLine("OnActionExecuting2执行了"); } }

执行结果为

Copy
OnActionExecuting1执行了 OnActionExecuting2执行了 Action执行 OnActionExecuted2执行了 OnActionExecuted1执行了

除了直接实现Filter接口,.Net Core同时提供了一些基于特性的过滤器,我们可以继承相应的特性来实现自定义的过滤器。这些特性包括ActionFilterAttributeExceptionFilterAttributeResultFilterAttributeFormatFilterAttributeServiceFilterAttributeTypeFilterAttribute

Filter通过注解的话如何注入实例呢#

如果特性类的构造函数有参的话特性也是需要带入参数的并且只能是常量,那么如何注入呢?

  1. ServiceFilter 需要在容器中注册过滤器
Copy
[ServiceFilter(typeof(TestActionFilterAttribute))]
  1. TypeFilter 通过使用Microsoft.Extensions.DependencyInjection.ObjectFactory对指定的过滤器类型进行实例化因此不需要注册容器
Copy
[TypeFilter(typeof(TestActionFilterAttribute))]
  1. IFilterFactory 需要自己手动实现工厂类(其实就是第一种的实现方式,也需要在容器中注册过滤器)
Copy
public class CustomFilterFactory : Attribute,IFilterFactory { private Type _filterType = null; public CustomFilterFactory(Type type) { this._filterType = type; } public bool IsReusable => true; public IFilterMetadata CreateInstance(IServiceProvider serviceProvider) { return (IFilterMetadata)serviceProvider.GetService(this._filterType); // throw new NotImplementedException(); } }
posted @   赵小源  阅读(1920)  评论(4编辑  收藏  举报
编辑推荐:
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
阅读排行:
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· AI技术革命,工作效率10个最佳AI工具
点击右上角即可分享
微信分享提示
CONTENTS