Skip to content

Instantly share code, notes, and snippets.

@tjrobinson
Created July 26, 2011 16:17
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save tjrobinson/1107148 to your computer and use it in GitHub Desktop.
Save tjrobinson/1107148 to your computer and use it in GitHub Desktop.
Common.Logging.NLog2
using System;
using System.Collections.Generic;
using Common.Logging;
using Common.Logging.Configuration;
using NLog;
using NLog.Targets;
using CommonLogging = Common.Logging;
namespace Hydra.Common.Infrastructure.Crosscutting.Logging.NLog
{
/// <summary>
/// Routes all log events logged through NLog into the Common.Logging infrastructure.
/// </summary>
/// <remarks>
/// <example>
/// To route all NLog events to Common.Logging, you must add this target to your configuration:
/// <code>
/// LoggingConfiguration cfg = new LoggingConfiguration();
/// CommonLoggingTarget target = new CommonLoggingTarget("${level:uppercase=true}|${logger}|${message}");
/// cfg.LoggingRules.Add(new LoggingRule("*", LogLevel.Trace, target));
///
/// LogManager.Configuration = cfg;
///
/// Logger log = LogManager.GetLogger("mylogger");
/// log.Debug("some message");
/// </code>
/// </example>
/// </remarks>
public sealed class CommonLoggingTarget : TargetWithLayout
{
private static readonly Dictionary<global::NLog.LogLevel, LogMethod> LogMethods;
static CommonLoggingTarget()
{
LogMethods = new Dictionary<global::NLog.LogLevel, LogMethod>();
LogMethods[global::NLog.LogLevel.Trace] = (log, msg, ex) => log.Trace(m => m(msg()), ex);
LogMethods[global::NLog.LogLevel.Debug] = (log, msg, ex) => log.Debug(m => m(msg()), ex);
LogMethods[global::NLog.LogLevel.Info] = (log, msg, ex) => log.Info(m => m(msg()), ex);
LogMethods[global::NLog.LogLevel.Warn] = (log, msg, ex) => log.Warn(m => m(msg()), ex);
LogMethods[global::NLog.LogLevel.Error] = (log, msg, ex) => log.Error(m => m(msg()), ex);
LogMethods[global::NLog.LogLevel.Fatal] = (log, msg, ex) => log.Fatal(m => m(msg()), ex);
LogMethods[global::NLog.LogLevel.Off] = (log, msg, ex) => { };
}
/// <summary>
/// Creates this target using a custom layout.
/// </summary>
public CommonLoggingTarget(string layout)
{
ArgUtils.AssertNotNull("layout", layout);
this.Layout = layout;
}
private delegate string MessageFormatter();
private delegate void LogMethod(ILog logger, MessageFormatter fmtr, Exception exception);
/// <summary>
/// Writes the event to the Common.Logging infrastructure
/// </summary>
protected override void Write(LogEventInfo logEvent)
{
ILog logger = CommonLogging.LogManager.GetLogger(logEvent.LoggerName);
LogMethod log = LogMethods[logEvent.Level];
log(logger, () => this.Layout.Render(logEvent), logEvent.Exception);
}
}
}
using System;
using Common.Logging.Factory;
using NLog;
namespace Common.Logging.NLog
{
public class NLogLogger : AbstractLogger
{
private readonly Logger logger;
private static readonly Type DeclaringType = typeof(AbstractLogger);
/// <summary>
/// Constructor
/// </summary>
protected internal NLogLogger(Logger logger)
{
this.logger = logger;
}
#region ILog Members
/// <summary>
/// Gets a value indicating whether this instance is trace enabled.
/// </summary>
/// <value>
/// <c>true</c> if this instance is trace enabled; otherwise, <c>false</c>.
/// </value>
public override bool IsTraceEnabled
{
get { return logger.IsTraceEnabled; }
}
/// <summary>
/// Gets a value indicating whether this instance is debug enabled.
/// </summary>
/// <value>
/// <c>true</c> if this instance is debug enabled; otherwise, <c>false</c>.
/// </value>
public override bool IsDebugEnabled
{
get { return logger.IsDebugEnabled; }
}
/// <summary>
/// Gets a value indicating whether this instance is info enabled.
/// </summary>
/// <value>
/// <c>true</c> if this instance is info enabled; otherwise, <c>false</c>.
/// </value>
public override bool IsInfoEnabled
{
get { return logger.IsInfoEnabled; }
}
/// <summary>
/// Gets a value indicating whether this instance is warn enabled.
/// </summary>
/// <value>
/// <c>true</c> if this instance is warn enabled; otherwise, <c>false</c>.
/// </value>
public override bool IsWarnEnabled
{
get { return logger.IsWarnEnabled; }
}
/// <summary>
/// Gets a value indicating whether this instance is error enabled.
/// </summary>
/// <value>
/// <c>true</c> if this instance is error enabled; otherwise, <c>false</c>.
/// </value>
public override bool IsErrorEnabled
{
get { return logger.IsErrorEnabled; }
}
/// <summary>
/// Gets a value indicating whether this instance is fatal enabled.
/// </summary>
/// <value>
/// <c>true</c> if this instance is fatal enabled; otherwise, <c>false</c>.
/// </value>
public override bool IsFatalEnabled
{
get { return logger.IsFatalEnabled; }
}
#endregion
/// <summary>
/// Actually sends the message to the underlying log system.
/// </summary>
/// <param name="logLevel">the level of this log event.</param>
/// <param name="message">the message to log</param>
/// <param name="exception">the exception to log (may be null)</param>
protected override void WriteInternal(LogLevel logLevel, object message, Exception exception)
{
global::NLog.LogLevel level = GetLevel(logLevel);
var logEvent = new LogEventInfo(level, logger.Name, null, "{0}", new object[] { message }, exception);
logger.Log(DeclaringType, logEvent);
}
private static global::NLog.LogLevel GetLevel(LogLevel logLevel)
{
switch (logLevel)
{
case LogLevel.All:
return global::NLog.LogLevel.Trace;
case LogLevel.Trace:
return global::NLog.LogLevel.Trace;
case LogLevel.Debug:
return global::NLog.LogLevel.Debug;
case LogLevel.Info:
return global::NLog.LogLevel.Info;
case LogLevel.Warn:
return global::NLog.LogLevel.Warn;
case LogLevel.Error:
return global::NLog.LogLevel.Error;
case LogLevel.Fatal:
return global::NLog.LogLevel.Fatal;
case LogLevel.Off:
return global::NLog.LogLevel.Off;
default:
throw new ArgumentOutOfRangeException("logLevel", logLevel, "unknown log level");
}
}
}
}
using System;
using System.Collections.Specialized;
using System.IO;
using Common.Logging.Factory;
namespace Common.Logging.NLog
{
public class NLogLoggerFactoryAdapter : AbstractCachingLoggerFactoryAdapter
{
public NLogLoggerFactoryAdapter(NameValueCollection properties)
: base(true)
{
string configType = string.Empty;
string configFile = string.Empty;
if (properties != null)
{
if (properties["configType"] != null)
{
configType = properties["configType"].ToUpper();
}
if (properties["configFile"] != null)
{
configFile = properties["configFile"];
if (configFile.StartsWith("~/") || configFile.StartsWith("~\\"))
{
configFile = Path.Combine(AppDomain.CurrentDomain.BaseDirectory.TrimEnd('/', '\\') + "/", configFile.Substring(2));
}
}
if (configType == "FILE")
{
if (configFile == string.Empty)
{
throw new ConfigurationException("Configuration property 'configFile' must be set for NLog configuration of type 'FILE'.");
}
if (!File.Exists(configFile))
{
throw new ConfigurationException("NLog configuration file '" + configFile + "' does not exists");
}
}
}
switch (configType)
{
case "INLINE":
break;
case "FILE":
global::NLog.LogManager.Configuration = new global::NLog.Config.XmlLoggingConfiguration(configFile);
break;
}
}
protected override ILog CreateLogger(string name)
{
return new NLogLogger(global::NLog.LogManager.GetLogger(name));
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment