Filters in ASP.NET Core

Filters in ASP.NET Core are easy and are the best way to take care of your cross-cutting concerns. Here in this post we will see how to enable filters and control their behavior in .NET Core-based applications.

Today in this article, we will cover the below aspects,

Benefits of Filters

  • Abstract your repetitive and important cross-cutting concern to commonplace.
  • Make your business logic free of addressing those concerns implicitly
  • As we know “Code is more often read than write”. The code becomes easy to read and understand.
  • Developers can better focus on implementing business functionality.

Types of Filters in ASP.NET Core

Your cross-cutting concern can be addressed using the below filters as well

  • Authorization Filters
  • Resource level Filters
  • Action Filters
  • Exception Filters
  • Result Execution Filters etc.

Let’s look at a simple example of filter implementation using .NET Core for a WebAPI microservice.

Getting Started

Let’s create an ASP.NET core API application.

Create ASP.NET Core API

Please choose any ASP.NET Core API project template. Filters are supported in most ASP.NET Core project templates.

  • Once you have a project available, add the class ‘ServiceInterceptor’ as below. Below shows examples of handling Synchronous and Asynchronous actions, please use a suitable mechanism as per requirement.

  • Sync: Override 2 methods OnActionExecuting and OnActionExecuted as below. Here you need to derive your filter class from the IActionFilter interface

public class ServiceInterceptor : IActionFilter
    {
        public void OnActionExecuting(ActionExecutingContext context)
        {
            // do something before
        }

        public void OnActionExecuted(ActionExecutedContext context)
        {
            // do something after 
        }
    }

  • Async: For asynchronous operation use only one method OnActionExecutionAsync to execute pre and post-method execution as shown below. Derive your class from the IAsyncActionFilter interface.

public class ServiceInterceptorAsync: IAsyncActionFilter
    {
        public async Task OnActionExecutionAsync(
            ActionExecutingContext context,
            ActionExecutionDelegate next)
        {
            // do something before
            var resultContext = await next();
            // do something after the action executes
        }
    }

  • Next, To enable the filter within the service pipeline this is what you need to do.
  • This class and these/this methods get executed globally or at the REST method level

Let’s now use the above action filter within the API pipeline

Controlling Action Filter’s behavior Global and Local

Now we know how to create action filters in an API or MVC application.

These action filters can be used at multiple places depending on your requirement.

  • Global level
  • Controller level or
  • Action/Route level

Global Filters

The global level interceptor will run for all available controllers in a service. If cross-cutting concern needs to be addressed globally or needs to be centralized global filters are a very good option.

To Inject filters globally you need to add below simple single line of code within ConfigureService()s method in Startup.cs,

If using ASP.NET Core 3.1 or .NET 5 please use above filters within AddControllers()

         services.AddControllers(options => options.Filters.Add(new
          ServiceInterceptorAsync()));

Let’s debug the app now, you can see action methods are executing for controllers, once respective URLs are invoked,

blank

Controller/Class Level Filters

If you don’t want to centralize action filters at a global level then one approach is to enable action filters at your controller level. This way one can apply filters for any cross-cutting concerns of their choice of controllers.

You may have other useful controllers in your service for addressing non-business functionality like health check controller etc. then controller level approach provides more granularity.

Add Exception Filter at Controller or class level can be used as below using TypeFilterAttribute

What is TypeFilter?


TypeFilter is a filter of type Microsoft.AspNetCore.Mvc.TypeFilterAttribute.ImplementationType.
It retrieves missing constructor arguments from dependency injection if available.

    [ApiController]
    [Route("[controller]")]
    [TypeFilter(typeof(ServiceInterceptorAsync))]
    public class WeatherForecastController : ControllerBase
    {

The above approach will enable the Action filter for all the routes supported by the Controller. Ex – WeatherForecastController

Endpoint/Action Level Filters

To get further granularity and more control over the filter one can use the filter at the Endpoint/Action level too. The only difference here is we add filter attribute at route/action/method level instead of class as shown below,

Action Filters can also be added at the Endpoint/route Level,

        [HttpGet]
        [TypeFilter(typeof(ServiceInterceptorAsync))]
        public IEnumerable<WeatherForecast> Get()
        {

Filters will be executed for attributed methods only. As shown above, example filters will execute only for ‘GET()’ route but not for the other route where it is not decorated.

Once you execute REST API like GET, PUT, POST, DELETE filter gets executed prior to and post-execution of each route.

The above approach will enable the Action filter for the only routes where this attribute is decorated.

As we stated already above our important cross-cutting concerns like security, caching, exception, etc, can be addressed using the below .NET Core filters.

I shall soon cover the above filters in the upcoming articles.

References:

Summary

Today in this article we learned how to use the .NET Core filter to take care of the cross-cutting concern. There are many types of filters available that could be helpful to take care of the various needs of your application. Filter helps in abstracting your repetitive and important cross-cutting concerns to commonplace and makes your business logic free of addressing those concerns repeatedly.



Please bookmark this page and share it with your friends. Please Subscribe to the blog to receive notifications on freshly published(2024) best practices and guidelines for software design and development.



Leave a Reply

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