Search code examples
.netloggingserilogdestructuring

What is Serilog destructuring?


What is the purpose of Serilog's @ syntax?

If I run the following:

var dummy = new { Foo = "Bar", Date = DateTime.Now };
Log.Information("Dummy object: {Dummy}", dummy);

Then I get an output to the console like so:

Time: 16:20 [Level: Information] (ManagedThreadID: 8) Message: Dummy object: "Foo = Bar, Date = 25/06/2016 16:20:30 }"

If I change the {Dummy} to {@Dummy} then I get the same output

Time: 16:22 [Level: Information] (ManagedThreadID: 8) Message: Dummy object:  Foo: "Bar", Date: 06/25/2016 16:22:28 }

So, what is the @ supposed to do?


Solution

  • Look closely, and you'll see that it is not the same output.

    The @ operator in front of Dummy tells Serilog to serialize the object passed in, rather than convert it using ToString(), which is what happens on your first example without using the @ operator.


    Your log event in the first example will end up with a property like (here in JSON):

    {
      "Dummy": "{ Foo = Bar, Date = 25/06/2016 16:20:30 }"
    }
    

    Using {@Dummy} will cause the parameter to be serialized as structured data:

    {
      "Dummy":
      {
        "Foo": "Bar",
        "Date": "25/06/2016 16:20:30"
      }
    }
    

    Comment from Nicholas Blumhardt (creator of Serilog):

    Where appropriate, using the @ operator is much more useful for manipulation/analysis.

    The reason for this "opt-in" requirement is that most types in .NET programs convert nicely into strings, but aren't cleanly/meaningfully serializable. By opting in to serialization with @ you're saying: "I know what I'm doing, serialize this object!" :)