使用NLog

时间:2016-07-12 10:09:02

标签: c# asp.net nlog

我想使用NLog记录方法入口和退出。我发现了两种方法。 第一个,使用PostSharp,但需要购买。 第二种方法,使用unity,但我们只能在具有接口的方法上实现它。

例如, 我有一个名为 SampleController

的控制器

SampleController.cs

 public string Get()
        {
            BusinessLayerClass businessLayer = new BusinessLayerClass();
            return businessLayer.BusinessLayerMethod();
        }

BusinessLayerClass.cs

public class BusinessLayerClass
    {
        public string BusinessLayerMethod()
        {
            DataLayerClass dataLayerClass = new DataLayerClass();
           return  dataLayerClass.DataLayerMethod();
        }
    }

DataLayerClass.cs

public class DataLayerClass
    {
        public string DataLayerMethod()
        {
            return "Hi";
        }
    }

我在BusinessLayerClass中的示例控制器调用DataLayerClass.Get中有两个类BusinessLayerMethodBusinessLayerClass方法,并从中调用了DataLayerMethod。 我有一个用于记录目的的NLogging

NLogging.cs

public static class NLogging
    {
        public static bool Enabled
        {
            get { return LogManager.IsLoggingEnabled(); }
            set
            {
                if (value)
                {
                    while (!Enabled) LogManager.EnableLogging();
                }
                else
                {
                    while (Enabled) LogManager.DisableLogging();
                }
            }
        }

        public static void Fatal(string message, Exception exception = null, [CallerFilePath] string callerPath = "", [CallerMemberName] string callerMember = "", [CallerLineNumber] int callerLine = 0)
        {
            Log(LogLevel.Fatal, message, exception, callerPath, callerMember, callerLine);
        }
        public static void Trace(string message, Exception exception = null, [CallerFilePath] string callerPath = "", [CallerMemberName] string callerMember = "", [CallerLineNumber] int callerLine = 0)
        {
            Log(LogLevel.Trace, message, exception, callerPath, callerMember, callerLine);
        }

        public static void Debug(string message, Exception exception = null, [CallerFilePathAttribute] string callerPath = "", [CallerMemberName] string callerMember = "", [CallerLineNumber] int callerLine = 0)
        {
            Log(LogLevel.Debug, message, exception, callerPath, callerMember, callerLine);
        }

        public static void Info(string message, Exception exception = null, [CallerFilePathAttribute] string callerPath = "", [CallerMemberName] string callerMember = "", [CallerLineNumber] int callerLine = 0)
        {
            Log(LogLevel.Info, message, exception, callerPath, callerMember, callerLine);
        }

        public static void Warn(string message, Exception exception = null, [CallerFilePathAttribute] string callerPath = "", [CallerMemberName] string callerMember = "", [CallerLineNumber] int callerLine = 0)
        {
            Log(LogLevel.Warn, message, exception, callerPath, callerMember, callerLine);
        }

        public static void Error(string message, Exception exception = null, [CallerFilePathAttribute] string callerPath = "", [CallerMemberName] string callerMember = "", [CallerLineNumber] int callerLine = 0)
        {
            Log(LogLevel.Error, message, exception, callerPath, callerMember, callerLine);
        }

        private static void Log(LogLevel level, string message, Exception exception = null, string callerPath = "", string callerMember = "", int callerLine = 0)
        {
            LogManager.ThrowExceptions = true;
            var logger = LogManager.GetLogger(callerPath);

            if (!logger.IsEnabled(level)) return;

            var logEvent = new LogEventInfo(level, callerPath, message) { Exception = exception };
            logEvent.Properties.Add("callerpath", callerPath);
            logEvent.Properties.Add("callermember", callerMember);
            logEvent.Properties.Add("callerline", callerLine);

            logger.Log(logEvent);
        }
    }

我不能在这里使用 Unity ,因为BusinessLayerClassDataLayerClass不会实现接口。

在每种方法中调用NLogging.Trace(methodname)都不方便。例如,如果我更改了方法名称,我还需要更改日志记录代码,例如NLogging.Trace("Entered into ModifiedBusinessLayerMethod")

有没有其他方法可以在不使用这两种方法的情况下记录方法的进入和退出?

2 个答案:

答案 0 :(得分:5)

您可以使用FodyMethodDecorator.Fody 加载项。 Fody是一个免费的开源代码编织库。

如何设置:

1。安装包

public class BusinessLayerClass
    {
        [LogMethod] 
        public string BusinessLayerMethod()
        {
            DataLayerClass dataLayerClass = new DataLayerClass();
           return  dataLayerClass.DataLayerMethod();
        }
    }

2。装饰方法

 using System;
 using System.Reflection;

[module: LogMethod] // Atribute should be "registered" by adding as module or assembly custom attribute

// Any attribute which provides OnEntry/OnExit/OnException with proper args
[AttributeUsage(AttributeTargets.Method | AttributeTargets.Constructor | AttributeTargets.Assembly | AttributeTargets.Module)]
public class LogMethodAttribute : Attribute, IMethodDecorator
{
    private MethodBase _method;
    // instance, method and args can be captured here and stored in attribute instance fields
    // for future usage in OnEntry/OnExit/OnException
    public void Init(object instance, MethodBase method, object[] args)
    {
        _method = method;
    }
    public void OnEntry()
    {
        NLogging.Trace("Entering into {0}", _method.Name);
    }

    public void OnExit()
    {
        NLogging.Trace("Exiting into {0}", _method.Name);
    }

    public void OnException(Exception exception)
    {
        NLogging.Trace(exception, "Exception {0}", _method.Name);
    }
}

3。写拦截器

text

答案 1 :(得分:0)

将Tracer用于Fody

它是高度可配置的,可在不强制您修饰代码的情况下立即为您提供结果。您可以自动记录每个方法调用或通过明确包含和排除特定类和方法来执行细粒度控制。

https://github.com/csnemes/tracer

在大多数情况下,与Tracer提供的优雅功能相比,其他建议的答案过于复杂且耗时。