Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

NLog auto truncate messages

Tags:

c#

nlog

I'm logging my messages to a database field with a max size of 1000 characters. Currently if I try to log a message (which often contains exception information with stack trace, HTTP request content, etc.) that's larger than 1000 characters, the insert fails and NLog (as it should) silently ignores that and keeps going.

Is there something I can put in my NLog.config to declare that the message length should always be truncated so it's no greater than 1000 characters?

Bonus points if you can tell me how to gracefully mark truncated messages by replacing the last few characters before the 1000 character limit with something like "[...Truncated]".

Can't believe I can't readily find this with some googling. Hopefully I don't have to write my own renderer?

like image 663
mo. Avatar asked Oct 14 '13 20:10

mo.


3 Answers

NLog 4.6.3 supports this:

${message:truncate=1000}

Older versions of NLog can do this:

${trim-whitespace:inner=${message:padding=-1000:fixedLength=true}}
like image 86
Rolf Kristensen Avatar answered Nov 15 '22 20:11

Rolf Kristensen


I don't know of a built in way to do it. Instead, I would write a LayoutRenderer (actually, a WrapperLayoutRenderer). It's not hard.

Something like this (untested) ought to do it:

[LayoutRenderer("truncate")]
[ThreadAgnostic]
public sealed class TruncateLayoutRendererWrapper : WrapperLayoutRendererBase
{
    public TruncateLayoutRendererWrapper()
    {
        this.Truncate = true;
        this.Ellipsis = true;
        this.Limit = 1000;
    }

    [DefaultValue(true)]
    public bool Truncate { get; set; }

    [DefaultValue(true)]
    public bool Ellipsis { get; set; }

    [DefaultValue(1000)]
    public bool Limit { get; set; }

    /// <summary>
    /// Post-processes the rendered message. 
    /// </summary>
    /// <param name="text">The text to be post-processed.</param>
    /// <returns>Trimmed string.</returns>
    protected override string Transform(string text)
    {
        if (!Truncate || Limit <= 0) return text;

        var truncated = text.Substring(0, Ellipsis ? Limit - 3 : Limit);
        if (Ellipsis) truncated += "...";

        return truncated;
    }
}
like image 23
wageoghe Avatar answered Nov 15 '22 18:11

wageoghe


One way to do this is by using regular expression replacement of the message, which you can define right in the nlog.config. I used the following to truncate to 500 characters:

<variable name="truncated_message" value="${replace:replaceWith=...TRUNCATED:regex=true:inner=${message}:searchFor=(?&lt;\=.\{500\}).+}"/>

<target name="filelog" xsi:type="File" fileName="${basedir}/../logs/jobs/${shortdate}.log" layout="${date:format=yyyy-MM-dd HH\:mm\:ss.fff}|${level:uppercase=true}|${truncated_message}"/>
like image 40
user1411430 Avatar answered Nov 15 '22 20:11

user1411430