Подтвердить что ты не робот

Node.js: Winston: могу ли я добавлять метаданные по умолчанию ко всем сообщениям журнала

Я использую Winston в Node.js для регистрации. Я знаю, что могу добавить метаданные индивидуально к каждому сообщению журнала, но есть способ указать стандартный набор метаданных, которые будут добавлены к каждому сообщению журнала (такие как имя приложения), как я не хочу, чтобы указать его каждый раз, Мне нужно отправить сообщение журнала.

4b9b3361

Ответ 1

Нет встроенного способа сделать это, но вы можете определенно добавить его сами - вот как:

Сначала настройте свой регистратор, как обычно. Например:

var logger = new (winston.Logger)({
            "exitOnError" : true,
            "transports" : [
                new (winston.transports.Console)({ "colorize" : true, "level" : "silly", "silent" : false, "handleExceptions" : false }),
            ]
        });

Затем переопределите метод log() (это всегда вызывается методами уровня - logger.foo() на самом деле вызывает logger.log('foo').)

logger.log = function(){
  var args = arguments;
  if(args[2]) args[3] = args[2];
  args[2] = {
    "foo" : "bar"
  }
  winston.Logger.prototype.log.apply(this,args);
}

Все, что я делаю выше, делает это так, когда вызывается logger.log(), вместо этого он вызывает вышеупомянутый метод, который добавляет метаданные (в данном случае объект, содержащий ключ foo). Затем он вызывает метод winston Logger.log из соответствующего контекста.

Вышеприведенный код будет в модуле, который вы создаете, внизу просто экспортируйте регистратор:

module.exports = logger;

и импортируйте модуль регистратора вместо модуля winston в подклассы.

var logger = require('./logger.js');

Надеюсь, что это поможет!

Ответ 2

Для Winston v2 (см. комментарии)

Теперь есть rewriters, которые являются документированным и официальным способом сделать это:

logger.rewriters.push(function(level, msg, meta) {
  meta.app = 'myApp';

  return meta;
});

Добавит свойство app ко всем метаданным, проходящим через этот регистратор.
Вы также можете объявить это при сборке регистратора:

new (winston.Logger)({
        level: config.log[file].level,
        rewriters: [
            (level, msg, meta) => {
                meta.app = 'myApp';
                return meta;
            }
        ],
        transports: [
            /*your transports*/
        ]
});

Ответ 3

Для Winston v3:

const addAppNameFormat = winston.format(info => {
  info.appName = "My Program";
  return info;
});

const logger = winston.createLogger({
  format: winston.format.combine(
    addAppNameFormat(),
    winston.format.json()
  ),
transports: [new winston.transports.Console()]
});

logger.warn('Danger Will Robinson!');
// {"message":"Danger Will Robinson!","level":"warn","appName":"My Program"}

См: https://github.com/winstonjs/winston/blob/HEAD/UPGRADE-3.0.md#migrating-filters-and-rewriters-to-formats-in-winston3

Ответ 4

Другая опция с выходом больше похожа на log4j (s):

В транспорте Консоли есть (в настоящее время недокументированное) свойство label, которое добавит метку к выходу (json или line):

var _ = require('lodash');
var winston = require('winston');
var path = require('path');
var baseDir = path.resolve(__dirname, '..');

// SETUP WINSTON LOGGER
var container = new winston.Container();
container.add("exception", {
    console: {
        handleExceptions: true,
        timestamp: true,
        label: "EXCEPTION",
        colorize: true
    }
});
container.get("exception").exitOnError = false;
var keys = [];

module.exports = function(filename) {
    var label = path.relative(baseDir, filename);
    if (!_.contains(keys, label)) {
        container.add(label, {
            console: {
                handleExceptions: false,
                level: 'debug',
                timestamp: true,
                label: label,
                colorize: true
            }
        });
        keys.push(label);
    }
    var logger = container.get(label);
    logger.exitOnError = false;
    return logger;
};

И в других модулях требуется следующее:

var logger = require('./logger')(__filename);

Пример вывода:

2014-07-23T07:05:27.770Z - info: [config/config.js] .......

Ответ 5

Я нашел лучший способ, используя util-extend на основе того, что я читал на этот блог. Он будет добавлять данные во всех случаях, которые я нашел полезными для ловушки logger.info vs logger.log( "информация", сообщение) и не перезаписывать ваши другие аргументы.

logger.log = function(){
   var args = arguments;
   var level = args[0];

   var newArgs = {
        foo: "bar",
        baz: "abc"
   };
   var originalMeta = args[2] || {};
   args[2] = extend(originalMeta, newArgs);

   winston.Logger.prototype.log.apply(this,args);
};

Будет выводиться в консоли и в ваших журналах.

Ответ 6

Теперь (20.08.19) есть свойство defaultMeta, которое передается в createLogger, которое будет вставлять мета, указанную вами, в каждый журнал. https://github.com/baronapp/cameo-microservices-sdk/pull/49

const logger = winston.createLogger({
  level: 'info',
  format: winston.format.json(),
  defaultMeta: { service: 'user-service' },
  transports: [
    //
    // - Write to all logs with level 'info' and below to 'combined.log' 
    // - Write all logs error (and below) to 'error.log'.
    //
    new winston.transports.File({ filename: 'error.log', level: 'error' }),
    new winston.transports.File({ filename: 'combined.log' })
  ]
});