David Fredman
David Fredman

Reputation: 21

Logging Mongo driver queries performance in a text file

I'm working on a university project and my instructor asked us to log everything include queries and the execution time. So I tried hard to find if there is any available solution but I didn't found.

Edit: My project is a web api with Asp.net core and mongo db ( latest mongo driver)

Upvotes: 1

Views: 2091

Answers (2)

Pavel Shastov
Pavel Shastov

Reputation: 3027

You can subscribe to driver's events and log them.

public class Startup
{
    ...

    public void ConfigureServices(IServiceCollection services)
    {
        ...

        services.AddSingleton<IMongoClient>(s =>
        {
            string connectionString = Configuration.GetConnectionString("MongoDb");
            var settings = MongoClientSettings.FromUrl(new MongoUrl(connectionString));
            settings.ClusterConfigurator = builder =>
            {
                var logger = s.GetRequiredService<ILogger<FileLogEvents>>();
                builder.Subscribe(new FileLogEvents(logger));
            };

            return new MongoClient(settings);
        });
    }
}

public class FileLogEvents : IEventSubscriber
{
    private readonly ILogger _logger;

    private ReflectionEventSubscriber _subscriber;

    public FileLogEvents(ILogger logger)
    {
        _logger = logger;
        _subscriber = new ReflectionEventSubscriber(this);
    }
    public bool TryGetEventHandler<TEvent>(out Action<TEvent> handler)
    {
        return _subscriber.TryGetEventHandler(out handler);
    }

    public void Handle(CommandStartedEvent e)
    {
        _logger.LogInformation("Command Started: {Event}, Json: {Json}", e.CommandName, e.ToJson());
    }

    public void Handle(CommandSucceededEvent e)
    {
        _logger.LogInformation("Command Succeeded: {Event}", e.CommandName);
    }
}

And Serilog configuration example

public class Program
{
    public static void Main(string[] args)
    {
        Log.Logger = new LoggerConfiguration()
            .Enrich.FromLogContext()
            .WriteTo.Console()
            .WriteTo.File("log.txt")
            .CreateLogger();

        CreateHostBuilder(args).Build().Run();
    }

    public static IHostBuilder CreateHostBuilder(string[] args) =>
        Host.CreateDefaultBuilder(args)
            .UseSerilog()
            .ConfigureWebHostDefaults(webBuilder =>
            {
                webBuilder.UseStartup<Startup>();
            });
}

Upvotes: 2

D. SM
D. SM

Reputation: 14520

To log queries as they are executed by the server:

https://www.mysoftkey.com/mongodb/profiling-for-slow-query-log-in-mongodb/

MongoDB logging all queries

To log queries as they are issued by a particular client, use command monitoring. .net driver documentation: http://mongodb.github.io/mongo-csharp-driver/2.10/reference/driver_core/events/#command-events

There doesn't seem to be an example of what you get from those events in the .net driver. Here is an example of using equivalent functionality in Ruby: https://docs.mongodb.com/ruby-driver/current/tutorials/ruby-driver-monitoring/#command-monitoring

Upvotes: 1

Related Questions