2012-09-24 11 views
7

¿Hay alguna forma de iniciar sesión con log4net y usar LogLevel como parámetro?Inicie sesión con log4net con el nivel de registro como parámetro

Es decir, en lugar de escribir

Log.Debug("Something went wrong"); 

me gustaría escribir algo como esto:

Log("Something went wrong", LogLevel.Debug); 
+0

Bien se podría ampliar la clase, pero susopect necesita decirle es por qué quiere hacer este cambio. –

+0

Es principalmente por conveniencia. Tengo una aplicación que puedo ejecutar como un servicio de Windows o una aplicación de consola. Cuando se ejecuta como una aplicación de consola, los registros deben imprimirse en la pantalla en lugar de en un archivo. Como se ha implementado, el método que realiza el registro toma el nivel de registro como parámetro. Sé que probablemente podría usar un appender de consola para log4net, pero no sé cómo decidir qué appenders usar durante la compilación. – olif

Respuesta

8

De acuerdo con la documentación log4net here (mirar debajo log4net.Core.ILogger), puede utilizar el registro método en la interfaz de ILogger.

private static ILog logger = 
    LogManager.GetLogger(
    System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 

logger.Logger.Log(logger.GetType(),LogLevel.Debug,"Something went wrong", ex); 

El parámetro tipo se utiliza por log4net para determinar el límite de la pila de llamadas entre el código de registro y código de la aplicación. Si tiene habilitado el registro de nombre de método, log4net navega por la pila de llamadas hasta que DeclaringType de MethodInfo en la pila sea igual al Tipo pasado (Tipo en la llamada de registro anterior). Cuando se encuentra con DeclaringType, el siguiente método en la pila de llamadas es el método de llamada real (código de la aplicación).

También puede usar la sobrecarga que toma una estructura LoggingEvent.

La documentación también dice que el método de registro está destinado a ser utilizado por los contenedores. No sé si eso debería considerarse como un mensaje "informativo" o una fuerte sugerencia de no usarlo directamente.

Si desea hacer todas sus llamadas de registro a través del método de registro, puede cambiar el código de donde se obtiene el registrador sea así (por lo que se puede eliminar mediante la propiedad Logger para cada registro de llamadas):

private static ILogger logger = 
    LogManager.GetLogger(
    System.Reflection.MethodBase.GetCurrentMethod().DeclaringType).Logger; 

logger.Log(logger.GetType(),LogLevel.Debug,"Something went wrong", ex); 
6

Extendiéndose sobre la respuesta de @ wageoghe, he escrito los siguientes métodos de extensión:

public static bool Log(this ILog log, Level level, string message, Exception exception = null) 
{ 
    var logger = log.Logger; 
    if (logger.IsEnabledFor(level)) 
    { 
     logger.Log(logger.GetType(), level, message, exception); 
     return true; 
    } 

    return false; 
} 

public static bool LogFormat(this ILog log, Level level, string messageFormat, params object[] messageArguments) 
{ 
    var logger = log.Logger; 
    if (logger.IsEnabledFor(level)) 
    { 
     var message = string.Format(messageFormat, messageArguments); 
     logger.Log(logger.GetType(), level, message, exception: null); 

     return true; 
    } 

    return false; 
}  

Estos le permiten hacer llamadas como:

Log.Log(Level.Debug, "Something went wrong", myException); 

o formateados mensajes:

Log.Log(Level.Info, "Request took {0:0} seconds", duration.TotalSeconds); 
+0

Esto es justo lo que necesitaba, tengo la necesidad de iniciar sesión rutinariamente en un nivel, pero sobrepasar el nivel a veces para poder volcar objetos en el archivo de registro 'a pedido'. –

+0

Esto es bueno, pero para mayor flexibilidad, el primer método debe aceptar 'object message' en lugar de' string message'. – Miral

Cuestiones relacionadas