Giter Site home page Giter Site logo

Date stored as string about nlog.mongo HOT 5 CLOSED

loresoft avatar loresoft commented on May 26, 2024
Date stored as string

from nlog.mongo.

Comments (5)

pwelter34 avatar pwelter34 commented on May 26, 2024

when you use a field with a layout, it has to be a string. Layouts always convert to string. I don't really know a way around it.

from nlog.mongo.

MarcAssmann avatar MarcAssmann commented on May 26, 2024

I ran into similar issues when trying to log complex/ typed /indexable objects to leverage the full power of mongo.

The goal was to log complex objects along with the usual message to mongodb like this:

log = LogManager.GetCurrentClassLogger();

var complexDataToLog = new {
    FileNames = new string[] { "a.txt", "b.jpg", "c.doc"},
    Now = DateTime.UtcNow,
    SecondsElapsed = 9.87654321
};

log.Debug(complexDataToLog, "Event occured to present logging of complex data to mongodb");

... so that in mongodb i can access the complex data in a typed/indexable fashion:

{
  "_id": {"$oid": "54bbccfbdf22cb0a24699597"},
  "Date": {"$date": 1421593851556},
  "Level": "Debug",
  "Logger": "ComplexObjectsLoggerTest",
  "Message": "Event occured to present logging of complex data to mongodb",
  "Context": {
    "FileNames": [
      "a.txt",
      "b.jpg",
      "c.doc"
    ],
    "Now": {"$date": 1421593851559},
    "SecondsElapsed": 9.87654321
  },
  "Properties": {
    "ThreadID": "7",
    "ProcessID": "2596"
  }
}

but this turned out to be impossible without modifications.

As stated above, the layout renderers are inadequate as they only produce strings. But the LogEventInfo class carries a "Dictionary<string, object> Properties" that is able to support here.

The idea is to make MongoTarget aware of properties being of type BsonValue to just include them in the DOM instead of using their string prepresentation only:

private void AddProperties(BsonDocument document, LogEventInfo logEvent)
{
    var propertiesDocument = new BsonDocument();
    foreach (var field in Properties)
    {
        string key = field.Name;
        string value = field.Layout.Render(logEvent);

        if (!string.IsNullOrEmpty(value))
            propertiesDocument[key] = new BsonString(value);
    }

    var properties = logEvent.Properties ?? Enumerable.Empty<KeyValuePair<object, object>>();
    foreach (var property in properties)
    {
        if (property.Key == null || property.Value == null)
            continue;

        string key = Convert.ToString(property.Key, CultureInfo.InvariantCulture);

        if (property.Value is BsonValue) {

            // Add BsonValue directly to the dom
            document.Add(key, property.Value as BsonValue);

        } else {

            string value = Convert.ToString(property.Value, CultureInfo.InvariantCulture);

            if (!string.IsNullOrEmpty(value))
                propertiesDocument[key] = new BsonString(value);
        }
    }

    if (propertiesDocument.ElementCount > 0)
        document.Add("Properties", propertiesDocument);
}

To make effective use of this like in the introduction above, the standard NLog logger interface can be extended via c# extension methods to allow logging of complex objects:

public static class NLogComplexObjects {

    /// <summary>
    /// Write a trace log entry along with some context to be serialized as BSON for the NLog.Mongo target
    /// </summary>
    public static void Debug(this Logger log, object context, string message, params object[] parameters) {

        var logEventInfo = LogEventInfo.Create(LogLevel.Debug, log.Name, null, message, parameters);
        if (context != null) {
            // BsonDomWriter is a modified version of Newtonsoft.Json.Bson.BsonWriter
            // that builds a BSON dom instead of writing out BSON to a stream.
            BsonDomWriter bsonDomWriter = new BsonDomWriter();
            var jsonSerializer = Newtonsoft.Json.JsonSerializer.Create();
            jsonSerializer.Serialize(bsonDomWriter, context);
            // add the serialized bson dom to the properties of the legevent so
            // it can be used later by the MongoTarget
            logEventInfo.Properties["Context"] = bsonDomWriter.DomRoot;
        }
    }
    // ... 
}

The implementation of a BsonDomWriter is a little long to be included in this post and can be provided on request.

What do you think?

from nlog.mongo.

pwelter34 avatar pwelter34 commented on May 26, 2024

Added a bsonType attribute to fields. The target will now try to convert the layout string to that type.

from nlog.mongo.

Jeky-v avatar Jeky-v commented on May 26, 2024

@MarcAssmann Could you please provide implementation of the BsonDomWriter ?

from nlog.mongo.

MarcAssmann avatar MarcAssmann commented on May 26, 2024

@Jeky-v Please find the modified BsonDomWriter here: https://gist.github.com/MarcAssmann/ed732c68702a556c40e68f6aff501783
It's just a proof of concept and since that's more than a year ago, I hope it still works for you.

from nlog.mongo.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.