ASP.NET核心筛选器-忽略定义的方法

Nat*_*a P 3 c# asp.net custom-attributes asp.net-core-mvc asp.net-core

我们将日志信息实现到我们的数据库中。我将为其使用过滤器(IActionFilter)功能。我写了下面的课:

public class ActionFilter: Attribute, IActionFilter
{
    DateTime start;
    public void OnActionExecuting(ActionExecutingContext context)
    {
        start = DateTime.Now;
    }

    public void OnActionExecuted(ActionExecutedContext context)
    {
        DateTime end = DateTime.Now;
        double processTime = end.Subtract(start).TotalMilliseconds;
        ... some log actions
    }
}
Run Code Online (Sandbox Code Playgroud)

然后,我将以下代码添加到Startup.cs中:

services.AddMvc(options => {
            options.Filters.Add(typeof(ActionFilter));

        });
Run Code Online (Sandbox Code Playgroud)

工作正常。我在每个方法的ActionFilter中都有一个断点。

但是我想忽略大部分方法的日志记录。据我了解,我可以使用自己的属性来实现。我以前没有使用自己的属性。好的,我写了以下属性:

public class IgnoreAttribute : Attribute
{
    public IgnoreAttribute()
    { }
}
Run Code Online (Sandbox Code Playgroud)

我将属性添加到方法:

[Ignore]
    [HttpGet]
    [Route("api/AppovedTransactionAmountByDays/{daysCount}")]
    public JsonResult GetAppovedTransactionAmountByDays(int daysCount)
    {
        var result = daysCount;

        return new JsonResult(result);
    }
Run Code Online (Sandbox Code Playgroud)

当然,简单的操作是行不通的。

我如何更改我的属性或ActionFilter以忽略方法?

提前致谢。

juu*_*nas 6

felix-b关于命名的注释是一个很好的注释。

我想再说一遍。以这种方式注册状态时,不应将状态存储在过滤器中。由于它是一个属性,因此只能实例化一次!因此,您那里的比赛条件繁重。一种选择是使用:

services.AddMvc(o =>
{
    o.Filters.Add(new ServiceFilterAttribute(typeof(LoggingActionFilter)));
});
Run Code Online (Sandbox Code Playgroud)

并将其注册为瞬态:

services.AddTransient<LoggingActionFilter>();
Run Code Online (Sandbox Code Playgroud)

现在,该属性在每次需要时都会实例化,因此您可以安全地存储状态。

还可以对其进行配置,以便在标记属性存在时忽略操作:

public class LoggingActionFilter : Attribute, IActionFilter
{
    private DateTime start;
    private bool skipLogging = false;

    public void OnActionExecuting(ActionExecutingContext context)
    {
        var descriptor = (ControllerActionDescriptor)context.ActionDescriptor;
        var attributes = descriptor.MethodInfo.CustomAttributes;

        if (attributes.Any(a => a.AttributeType == typeof(SkipLoggingAttribute)))
        {
            skipLogging = true;
            return;
        }

        start = DateTime.Now;
    }

    public void OnActionExecuted(ActionExecutedContext context)
    {
        if (skipLogging)
        {
            return;
        }

        DateTime end = DateTime.Now;
        double processTime = end.Subtract(start).TotalMilliseconds;
    }
}

public class SkipLoggingAttribute : Attribute
{
}
Run Code Online (Sandbox Code Playgroud)

在这里,我们从参数获取可用的动作描述符,并确定所讨论的方法是否具有SkipLogging属性。如果是这样,请跳过日志记录代码。