Bagaimana cara menambahkan stempel waktu ke log menggunakan Node.js library Winston?

93

Saya ingin menambahkan stempel waktu ke log. Apa cara terbaik untuk mencapai ini?

kolrie
sumber
Ini tetap terlalu luas karena Anda TIDAK dapat melakukannya dari mesin klien.
Joshua

Jawaban:

112

Saya sendiri menghadapi masalah yang sama. Ada dua cara saya bisa melakukan ini.

Jika Anda menyertakan Winston, biasanya defaultnya adalah menambahkan transport Konsol. Agar stempel waktu berfungsi dalam kasus default ini, saya perlu:

  1. Hapus transport konsol dan tambahkan lagi dengan opsi timestamp.
  2. Buat objek Logger Anda sendiri dengan opsi stempel waktu disetel ke true.

Pertama:

var winston = require('winston');
winston.remove(winston.transports.Console);
winston.add(winston.transports.Console, {'timestamp':true});

Opsi kedua, dan lebih bersih:

var winston = require('winston');
var logger = new (winston.Logger)({
    transports: [
      new (winston.transports.Console)({'timestamp':true})
    ]
});

Beberapa opsi lain untuk pengangkutan Konsol dapat ditemukan di sini :

  • level: Level pesan yang harus dicatat oleh transport ini (default 'debug').
  • silent: Bendera Boolean yang menunjukkan apakah akan menekan keluaran (default salah).
  • colorize: Bendera Boolean yang menunjukkan apakah kita harus mewarnai keluaran (default salah).
  • timestamp: Bendera Boolean yang menunjukkan apakah kita harus menambahkan keluaran dengan stempel waktu (default false). Jika fungsi ditentukan, nilai kembaliannya akan digunakan sebagai pengganti cap waktu.
imagreenplant
sumber
1
Luar biasa dan sederhana pada saat bersamaan. Terima kasih!
kolrie
7
Ini bagus. Saya biasanya membungkus ini dalam file khusus sehingga saya dapat dengan mudah mendapatkan logger saya yang dikonfigurasi dari file apa pun, yaitu, saya meletakkan kode di atas (opsi 2) di file baru logger.js, diikuti oleh module.exports = logger; kemudian dari file apa pun saya melakukan var logger = require ('./ logger.js') dan kemudian dapat melakukan logger.info ('hello') dari file apa pun dan mendapatkan konfigurasi yang sama dari Winston.
JHH
TypeError: (nilai antara) bukan sebuah fungsi
Urasquirrel
81

Jawaban di atas tidak berhasil untuk saya. Jika Anda mencoba menambahkan cap waktu ke log Anda menggunakan versi terbaru Winston - 3.0.0-rc1, ini berfungsi seperti pesona:

    const {transports, createLogger, format} = require('winston');

    const logger = createLogger({
        format: format.combine(
            format.timestamp(),
            format.json()
        ),
        transports: [
            new transports.Console(),
            new transports.File({filename: 'logs/error/error.log', level: 'error'}),
            new transports.File({filename: 'logs/activity/activity.log', level:'info'})
        ]
    });

Saya menggunakan 'format.combine ()'. Karena saya membutuhkan stempel waktu pada semua transportasi saya, saya menambahkan opsi pemformatan di dalam createLogger, daripada di dalam setiap transportasi. Output saya pada konsol dan file (activity.log) adalah sebagai berikut:

{"message":"Connected to mongodb","level":"info","timestamp":"2018-02-01T22:35:27.758Z"}
{"message":"Connected to mongodb","level":"info","timestamp":"2018-02-01T22:35:27.758Z"}

Kita dapat menambahkan pemformatan ke stempel waktu ini di 'format.combine ()' seperti biasa menggunakan:

format.timestamp({format:'MM-YY-DD'})
Siva Kiran
sumber
14

Kita juga bisa melakukan seperti ini

var winston = require('winston');
const { createLogger, format, transports } = require('winston');
var config = require('../configurations/envconfig.js');

var loggerLevel = process.env.LOGGERLEVEL ||  config.get('LOGGERLEVEL');

var logger = winston.createLogger({
  format: format.combine(
    format.timestamp({
      format: 'YYYY-MM-DD HH:mm:ss'
    }),
    format.printf(info => `${info.timestamp} ${info.level}: ${info.message}`+(info.splat!==undefined?`${info.splat}`:" "))
  ),
  transports: [
    new (winston.transports.Console)({ level: loggerLevel }),
  ]
});
module.exports = logger;
Biswadev
sumber
Apakah ini juga berhasil logger.info('Message', someObject)? Saya menyiapkan format kustom menggunakan gabungan dan sepertinya saya tidak bisa mendapatkan yang someObjectdisertakan dalam pesan log.
Sesuatu Pada tanggal
1
Saya bisa someObjectdisertakan dengan menggunakan pernyataan printf berikut ${info.timestamp} [${info.level.toUpperCase()}]: ${info.message} ${JSON.stringify(info)}. Ini mencakup level, stempel waktu, dan pesan yang saya rasa dapat saya hapus.
Sesuatu Pada tanggal
9

Anda dapat menggunakan util bawaan dan selamanya untuk mencapai logging dengan timestap untuk server nodejs Anda. Saat Anda memulai server, tambahkan output log sebagai bagian dari parameter:

forever start -ao log/out.log server.js

Dan kemudian Anda dapat menulis util di server.js Anda

server.js

var util = require('util');
util.log("something with timestamp");

Outputnya akan terlihat seperti ini pada file out.log:

out.log

15 Mar 15:09:28 - something with timestamp
KTU
sumber
1
Sayangnya, util.error()melewatkan waktu keluaran.
Saran
4

Meskipun saya tidak mengetahui winston, ini adalah saran. Saya menggunakan log4js untuk logging & log saya secara default terlihat seperti ini

[2012-04-23 16:36:02.965] [INFO] Development - Node Application is running on port 8090
[2012-04-23 16:36:02.966] [FATAL] Development - Connection Terminated to  '127.0.0.1' '6379'

Pengembangan adalah lingkungan proses node saya & [INFO | FATAL] adalah level log

Mempertahankan profil yang berbeda untuk logging dimungkinkan di log4js. Saya memiliki profil Pengembangan & Produksi. Juga ada tipe logger seperti rolling file appender, console appender, dll. Sebagai addon, file log Anda akan berwarna berdasarkan level log [Trace, Info, Debug, Error, Fatal];)

log4js akan menimpa console.log Anda Ini adalah parameter yang dapat dikonfigurasi sekarang dalam 0.5+

Tamil
sumber
FYI: Versi log4js-node (0.5+) yang lebih baru tidak secara otomatis menimpa console.log.
Jeff Hiltz
@jeffhiltz Ya Anda benar :) Sekarang ini adalah parameter yang dapat dikonfigurasi
Tamil
2

Terkadang format stempel waktu default tidak nyaman bagi Anda. Anda dapat menggantinya dengan penerapan Anda.

Dari pada

var winston = require('winston');
var logger = new (winston.Logger)({
transports: [
  new (winston.transports.Console)({'timestamp':true})
]
});

kamu bisa menulis

var winston = require('winston');
var logger = new (winston.Logger)({
transports: [
  new (winston.transports.Console)({
     'timestamp': function() {
        return <write your custom formatted date here>;
     }
  })
]
});

Lihat https://github.com/winstonjs/winston#custom-log-format untuk detailnya

walv
sumber
2

kita dapat menggunakan stempel konsol untuk menambahkan stempel waktu dan level log ke konsol yang ada: require('console-stamp')(console, '[yyyy-mm-dd HH:MM:ss.l]')

Lihat https://github.com/starak/node-console-stamp untuk detailnya

khoi nguyen
sumber
0

Solusi lain adalah membungkus logger ke dalam file yang mengekspor beberapa fungsi seperti logger.info (), logger.error (), dll. Kemudian Anda cukup memberikan kunci tambahan untuk dikirim pada setiap log pesan.

loggerService.js

const logger = winston.createLogger({ ... })

function handleLog(message, level) {
  const logData = {
    timestamp: Date.now(),
    message,
  }

  return logger[level](logData)
}

function info(message) {
  handleLog(message, 'info')
}

function error(message) {
  handleLog(message, 'error')
}

function warn(message) {
  handleLog(message, 'warn')
}

module.exports = {
  info,
  error,
  warn
}

apapun-file.js

const logger = require('./services/loggerService')

logger.info('Hello World!')

log-Anda.log

{"timestamp":"2019-08-21 06:42:27","message":"Hello World!","level":"info"}
Renan Coelho
sumber
0

Saya mengambil jawaban Biswadev dan membuat objek JSON yang dirangkai. Dengan cara ini jika saya perlu memproses log nanti, itu akan dalam format yang terstruktur dengan baik.

const winston = require('winston');
const { createLogger, format, transports } = require('winston');

const dotenv = require('dotenv');
dotenv.config();

var logger = createLogger({
    level: 'info',
    format: format.combine(
        format.timestamp({
            format: 'YYYY-MM-DD HH:mm:ss',
        }),
        format.printf((info) =>
            JSON.stringify({
                t: info.timestamp,
                l: info.level,
                m: info.message,
                s: info.splat !== undefined ? `${info.splat}` : '',
            }) + ','
        )
    ),
});

if (process.env.NODE_ENV !== 'PRODUCTION') {
    logger.add(new transports.Console({ format: winston.format.cli() }));

    // Turn these on to create logs as if it were production
    // logger.add(new transports.File({ filename: 'log/output/error.log', level: 'error' }));
    // logger.add(new transports.File({ filename: 'log/output/warn.log', level: 'warn' }));
    // logger.add(new transports.File({ filename: 'log/output/info.log', level: 'info' }));
} else {
    logger.add(new transports.File({ filename: 'log/output/error.log', level: 'error' }));
    logger.add(new transports.File({ filename: 'log/output/warn.log', level: 'warn' }));
    logger.add(new transports.File({ filename: 'log/output/info.log', level: 'info' }));
}

module.exports = {
    logger,
};

Pemakaian:

app.listen(port, () => logger.info(`app is running on port ${port}`));

Keluaran:

file info.log:

{"t":"2020-08-06 08:02:05","l":"info","m":"app is running on port 3001","s":""},

Menghibur:

info:    app is running on port 3001
Steve
sumber