Home » Nodejs » How can I change the winston log format?

How can I change the winston log format?

Posted by: admin November 30, 2017 Leave a comment

Questions:

In my node application I’m using winston module to store my application logs. We can store the the logs in two format one is json and the other one is string. While saving the log as string in winston I’m getting below log format.

  2013-09-10T06:51:34.199Z - error: error message!!!
       (timestamp)     -    (level) : (log message)

Now I want change the above log format to the following:

    2013-09-10T06:51:34.199Z/error/error message!!!
       (timestamp)    /     (level) / (log message)

How can this be achieved?

My Code:

  var winston = require('winston');
  winston.loggers.add('category1', {
   file: {
      filename: '/path/to/some/file',json:false
     }
  });              
  var category1 = winston.loggers.get('category1');
  category1.log('error','error message!!!');
Answers:

I was wondering the same thing and found an okay solution (though not ideal IMO, so perhaps someone else can weigh in on this).

You can completely customize the logger output by providing your transport object a formatter function. This might be better for File transports than Console, since you would have to manually colorize your font if that’s what you wanted.

Here is a relatively simple formatter function that you can use (and adjust for your needs):

// Define options for Date#toLocaleTimeString call we will use.
var twoDigit = '2-digit';
var options = {
  day: twoDigit,
  month: twoDigit,
  year: twoDigit,
  hour: twoDigit,
  minute: twoDigit,
  second: twoDigit
};

function formatter(args) {
  var dateTimeComponents = new Date().toLocaleTimeString('en-us', options).split(',');
  var logMessage = dateTimeComponents[0] + dateTimeComponents[1] + ' - ' + args.level + ': ' + args.message;
  return logMessage;
}

And to use this formatter in your transport, simply adjust your code to pass the function in:

winston.loggers.add('category1', {
  file: {
    filename: '/path/to/some/file',
    json: false,
    formatter: formatter
  }
});

It’s worth mentioning that the property args.meta will be set to any object argument that is passed into a log method call. So you would have to come up with a strategy for handling those objects passed in (or simply print the entire object as JSON). For example:

var error = {
  name: 'MongoError',
  code: 11000,
  err: 'insertDocument :: caused by :: 11000 E11000 duplicate key error...'
}
logger.info('Some error ocurred: ', error);

Would result in args.meta being set to the error variable.

As you can see, there is a fair amount to deal with when handling log messages this way. I wouldn’t be surprised if there was a better way of doing these things, but hopefully this helps you (or someone else) out.