es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

Filtros globales con dependencias de parámetros en .net core 5.

Tengo un filtro de validación. Quiero registrarlo a nivel global. Pero en el método ConfigureServices no puedo asignarle las dependencias. ¿Existe alguna manera eficiente de hacerlo?
Aquí está mi código.

Mi filtro.

public class ModelValidationFilterAttribute : Attribute, IAsyncActionFilter
{
    public ILogger<ModelValidationFilterAttribute> logger { get; }
    public ModelValidationFilterAttribute(ILogger<ModelValidationFilterAttribute> logger)
    {
        this.logger = logger;
    }

    public async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next)
    {
        if (!context.ModelState.IsValid)
        {
            context.Result = new BadRequestObjectResult(context.ModelState);
        }
        await next.Invoke();
    }
}

Método de extensión

public static IServiceCollection CustomServices(this IServiceCollection services)
{            
    services.AddScoped<ModelValidationFilterAttribute>();
    return services;
}

En el método ConfigureServices

public void ConfigureServices(IServiceCollection services)
{   
    services.CustomServices();         
    services.AddControllers(options =>
    { 
        options.Filters.Add(new ModelValidationFilterAttribute());
    });           
}

El código funciona bien si lo registro a nivel del controlador o acción con el atributo. Pero cuando intento registrarlo a nivel de servicio, no admite el argumento.

Tags:  , , , ,

Answer

  1. Avatar for davy.ai

    Para registrar el filtro de validación como un filtro a nivel global, debes registrarlo en el contenedor de inyección de dependencias en el método ConfigureServices del archivo Startup.cs. Sin embargo, dado que el filtro requiere una dependencia (ILogger) que debe ser inyectada, necesitas usar la sobrecarga de fábrica del método AddScoped para registrar un delegado que cree la instancia del filtro con la dependencia requerida. Así es como puedes modificar tu código para lograr esto:

    public static IServiceCollection CustomServices(this IServiceCollection services)
    {
        services.AddScoped<modelvalidationfilterattribute>(serviceProvider =>
        {
            var logger = serviceProvider.GetService<><modelvalidationfilterattribute>>();
            return new ModelValidationFilterAttribute(logger);
        });
        return services;
    }
    
    public void ConfigureServices(IServiceCollection services)
    {   
        services.AddControllers(options =>
        {
            options.Filters.AddService<modelvalidationfilterattribute>();
        });
        services.CustomServices();           
    }
    

    En el método CustomServices, ahora registramos un delegado que crea la instancia del filtro resolviendo la dependencia desde el proveedor de servicios. En el método ConfigureServices, agregamos el filtro a la colección de filtros global usando el método de extensión AddService, que busca la instancia del filtro desde el proveedor de servicios.

    Con estas modificaciones, el filtro debería ser registrado con la dependencia requerida como un filtro a nivel global.

Comments are closed.