I got use the following class to print out messages using log4net:
public class Message
{
public String Text { get; set; }
public int Id { get; set; }
public override string ToString()
{
return Text;
}
}
I use Logger.Info(MessageInstance)
, so log4net just invokes the ToString
method and prints out the message. I would like to also log the Id
property of the message object, but I cannot figure out how to achive this.
My conversion pattern looks similiar to this:
<conversionPattern value="%date %-5level %message%newline" />
I tried adding %message{Id}
but that would just print the whole message twice.
Any Suggestions?
I just wrote a custom pattern, which allows to read properies of the message object.
public class ReflectionReader : PatternLayoutConverter
{
public ReflectionReader()
{
_getValue = GetValueFirstTime;
}
protected override void Convert(TextWriter writer, LoggingEvent loggingEvent)
{
writer.Write(_getValue(loggingEvent.MessageObject));
}
private Func<object, String> _getValue;
private string GetValueFirstTime(object source)
{
_targetProperty = source.GetType().GetProperty(Option);
if (_targetProperty == null)
{
_getValue = x => "<NULL>";
}
else
{
_getValue = x => String.Format("{0}", _targetProperty.GetValue(x, null));
}
return _getValue(source);
}
private PropertyInfo _targetProperty;
}
Combine with this:
public class ReflectionLayoutPattern : PatternLayout
{
public ReflectionLayoutPattern()
{
this.AddConverter("item", typeof(ReflectionReader));
}
}
Config looks like this:
<layout type="MyAssembly.MyNamespace.ReflectionLayoutPattern, MyAssembly">
<conversionPattern value="[%item{Id}]	%message%newline" />
</layout>
You can use a CustomXmlLayout class that derives from XmlLayoutBase and override the FormatXml method. This method takes a LoggingEvent object as parameter which will contain the MessageObject that was passed to the log method.
public class SpecialXmlLayout : XmlLayoutBase
{
protected override void FormatXml(XmlWriter writer, LoggingEvent loggingEvent)
{
Message message = loggingEvent.MessageObject as Message;
writer.WriteStartElement("LoggingEvent");
writer.WriteElementString("Message", GetMessage(message));
// ... write other things
writer.WriteEndElement();
}
}
Inside the GetMessaage method create your string as you would like from the message.
Then use this layout class in log4net config:
<log4net>
<appender name="EventLogAppender" type="log4net.Appender.EventLogAppender">
<applicationName value="My Application" />
<layout type="Namespace.SpecialXmlLayout">
</layout>
<filter type="log4net.Filter.LevelRangeFilter">
<param name="LevelMin" value="ERROR" />
<param name="LevelMax" value="FATAL" />
</filter>
</appender>
</log4net>
This is the idea. For more specific details you will have to consult the log4Net SDK documentation.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With