Node: connectez-vous à un fichier au lieu de la console

Puis-je configurer console.log pour que les journaux soient écrits sur un fichier au lieu d'être imprimés dans la console?

131
demandé sur Randomblue 2011-12-06 03:58:37

16 réponses

Mise à jour 2013 - Cela a été écrit autour des nœuds V0.2 et V0.4; Il existe de bien meilleurs utilitaires maintenant autour de la journalisation. Je recommande fortement Winston

Mise à jour tardive 2013 - nous utilisons toujours winston, mais maintenant avec une bibliothèque de logger pour envelopper la fonctionnalité autour de la journalisation des objets personnalisés et de la mise en forme. Voici un échantillon de notre journal.js https://gist.github.com/rtgibbons/7354879


Devrait être aussi simple que cela.

var access = fs.createWriteStream(dir + '/node.access.log', { flags: 'a' })
      , error = fs.createWriteStream(dir + '/node.error.log', { flags: 'a' });

// redirect stdout / stderr
proc.stdout.pipe(access);
proc.stderr.pipe(error);
57
répondu Ryan Gibbons 2013-11-07 13:56:57

Vous pouvez également surcharger la console par défaut.fonction Journal:

var fs = require('fs');
var util = require('util');
var log_file = fs.createWriteStream(__dirname + '/debug.log', {flags : 'w'});
var log_stdout = process.stdout;

console.log = function(d) { //
  log_file.write(util.format(d) + '\n');
  log_stdout.write(util.format(d) + '\n');
};

L'exemple ci-dessus se connectera au débogage.journal et stdout.

Modifier: Voir la version multiparamètre de Clément également sur cette page.

148
répondu ceeroover 2017-05-23 11:33:24

Si vous cherchez quelque chose en production winston est probablement le meilleur choix.

Si vous voulez juste faire des choses dev rapidement, sortie directement dans un fichier (je pense que cela ne fonctionne que pour les systèmes * nix):

nohup node simple-server.js > output.log &
46
répondu alessioalex 2011-12-06 08:56:16

J'utilise souvent de nombreux arguments à console.log() et console.error () , donc ma solution serait:

var fs = require('fs');
var util = require('util');
var logFile = fs.createWriteStream('log.txt', { flags: 'a' });
  // Or 'w' to truncate the file every time the process starts.
var logStdout = process.stdout;

console.log = function () {
  logFile.write(util.format.apply(null, arguments) + '\n');
  logStdout.write(util.format.apply(null, arguments) + '\n');
}
console.error = console.log;
44
répondu Clément Désiles 2016-07-29 00:47:29

Winston est un module npm très populaire utilisé pour la journalisation.

Voici un how-to.
Installez winston dans votre projet comme:

npm install winston --save

Voici une configuration prête à l'emploi prête à l'emploi que j'utilise fréquemment dans mes projets en tant qu'enregistreur.js sous utils.

 /**
 * Configurations of logger.
 */
const winston = require('winston');
const winstonRotator = require('winston-daily-rotate-file');

const consoleConfig = [
  new winston.transports.Console({
    'colorize': true
  })
];

const createLogger = new winston.Logger({
  'transports': consoleConfig
});

const successLogger = createLogger;
successLogger.add(winstonRotator, {
  'name': 'access-file',
  'level': 'info',
  'filename': './logs/access.log',
  'json': false,
  'datePattern': 'yyyy-MM-dd-',
  'prepend': true
});

const errorLogger = createLogger;
errorLogger.add(winstonRotator, {
  'name': 'error-file',
  'level': 'error',
  'filename': './logs/error.log',
  'json': false,
  'datePattern': 'yyyy-MM-dd-',
  'prepend': true
});

module.exports = {
  'successlog': successLogger,
  'errorlog': errorLogger
};

Puis importez simplement chaque fois que nécessaire comme ceci:

const errorLog = require('../util/logger').errorlog;
const successlog = require('../util/logger').successlog;

Ensuite, vous pouvez enregistrer le succès comme:

successlog.info(`Success Message and variables: ${variable}`);

Et les erreurs comme:

errorlog.error(`Error Message : ${error}`);

Il enregistre également tous les journaux de réussite et les journaux fichier sous logs répertoire date-sage comme vous pouvez le voir ici.
journal de répertoire

23
répondu keshavDulal 2018-03-12 09:25:16

Si c'est pour une application, il vaut probablement mieux utiliser un module de journalisation. Elle vous donne plus de flexibilité. Quelques suggestions.

10
répondu Marco 2012-04-25 21:12:20
const fs = require("fs");
const keys = Object.keys;
const Console = console.Console;

/**
 * Redirect console to a file.  Call without path or with false-y
 * value to restore original behavior.
 * @param {string} [path]
 */
function file(path) {
    const con = path ? new Console(fs.createWriteStream(path)) : null;

    keys(Console.prototype).forEach(key => {
        if (path) {
            this[key] = function() {
                con[key].apply(con, arguments);
            };
        } else {
            delete this[key];
        }
    });
};

// patch global console object and export
module.exports = console.file = file;

Pour l'utiliser, faites quelque chose comme:

require("./console-file");
console.file("/path/to.log");
console.log("write to file!");
console.error("also write to file!");
console.file();    // go back to writing to stdout
9
répondu rich remer 2017-08-14 05:05:17

Console D'écrasement.le journal est le chemin à parcourir. Mais pour que cela fonctionne dans les modules requis, vous devez l'exporter.

module.exports = console;

Pour vous épargner la peine d'écrire des fichiers journaux, de tourner et d'autres choses, vous pouvez envisager d'utiliser un module de logger simple comme winston:

// Include the logger module
var winston = require('winston');
// Set up log file. (you can also define size, rotation etc.)
winston.add(winston.transports.File, { filename: 'somefile.log' });
// Overwrite some of the build-in console functions
console.error=winston.error;
console.log=winston.info;
console.info=winston.info;
console.debug=winston.debug;
console.warn=winston.warn;
module.exports = console;
3
répondu Simon Rigét 2017-11-07 20:59:58

Une autre solution non encore mentionnée consiste à accrocher les flux Writable dans process.stdout et process.stderr. De cette façon, vous n'avez pas besoin de remplacer Toutes les fonctions de console qui sortent vers stdout et stderr. Cette implémentation redirige stdout et stderr vers un fichier journal:

var log_file = require('fs').createWriteStream(__dirname + '/log.txt', {flags : 'w'})

function hook_stream(stream, callback) {
    var old_write = stream.write

    stream.write = (function(write) {
        return function(string, encoding, fd) {
            write.apply(stream, arguments)  // comments this line if you don't want output in the console
            callback(string, encoding, fd)
        }
    })(stream.write)

    return function() {
        stream.write = old_write
    }
}

console.log('a')
console.error('b')

var unhook_stdout = hook_stream(process.stdout, function(string, encoding, fd) {
    log_file.write(string, encoding)
})

var unhook_stderr = hook_stream(process.stderr, function(string, encoding, fd) {
    log_file.write(string, encoding)
})

console.log('c')
console.error('d')

unhook_stdout()
unhook_stderr()

console.log('e')
console.error('f')

Il devrait imprimer dans la console

a
b
c
d
e
f

Et dans le fichier journal:

c
d

Pour plus d'informations, consultez ce gist.

2
répondu reliasn 2016-12-14 05:28:30

Directement à partir des documents API de nodejs sur Console

const output = fs.createWriteStream('./stdout.log');
const errorOutput = fs.createWriteStream('./stderr.log');
// custom simple logger
const logger = new Console(output, errorOutput);
// use it like console
const count = 5;
logger.log('count: %d', count);
// in stdout.log: count 5
2
répondu Mr. 14 2017-07-25 00:16:02

Vous pouvez maintenant utiliser Caterpillar qui est un système de journalisation basé sur les flux, vous permettant de vous connecter, puis de rediriger la sortie vers différents transformations et emplacements.

La sortie dans un fichier est aussi simple que:

var logger = new (require('./').Logger)();
logger.pipe(require('fs').createWriteStream('./debug.log'));
logger.log('your log message');

Exemple complet sur le site Web Caterpillar

1
répondu balupton 2013-05-08 01:09:11

Vous pouvez également jeter un oeil à ce module npm: https://www.npmjs.com/package/noogger

Noogger

Simple et direct...

0
répondu Xsmael 2016-11-22 17:31:33

J'ai pris l'idée d'échanger le flux de sortie vers un flux my.

const LogLater                = require ('./loglater.js');
var logfile=new LogLater( 'log'+( new Date().toISOString().replace(/[^a-zA-Z0-9]/g,'-') )+'.txt' );


var PassThrough = require('stream').PassThrough;

var myout= new PassThrough();
var wasout=console._stdout;
myout.on('data',(data)=>{logfile.dateline("\r\n"+data);wasout.write(data);});
console._stdout=myout;

var myerr= new PassThrough();
var waserr=console._stderr;
myerr.on('data',(data)=>{logfile.dateline("\r\n"+data);waserr.write(data);});
console._stderr=myerr;

Loglater.js:

const fs = require('fs');

function LogLater(filename, noduplicates, interval) {
    this.filename = filename || "loglater.txt";
    this.arr = [];
    this.timeout = false;
    this.interval = interval || 1000;
    this.noduplicates = noduplicates || true;
    this.onsavetimeout_bind = this.onsavetimeout.bind(this);
    this.lasttext = "";
    process.on('exit',()=>{ if(this.timeout)clearTimeout(this.timeout);this.timeout=false; this.save(); })
}

LogLater.prototype = {
    _log: function _log(text) {
        this.arr.push(text);
        if (!this.timeout) this.timeout = setTimeout(this.onsavetimeout_bind, this.interval);
    },
    text: function log(text, loglastline) {
        if (this.noduplicates) {
            if (this.lasttext === text) return;
            this.lastline = text;
        }
        this._log(text);
    },
    line: function log(text, loglastline) {
        if (this.noduplicates) {
            if (this.lasttext === text) return;
            this.lastline = text;
        }
        this._log(text + '\r\n');
    },
    dateline: function dateline(text) {
        if (this.noduplicates) {
            if (this.lasttext === text) return;
            this.lastline = text;
        }
        this._log(((new Date()).toISOString()) + '\t' + text + '\r\n');
    },
    onsavetimeout: function onsavetimeout() {
        this.timeout = false;
        this.save();
    },
    save: function save() { fs.appendFile(this.filename, this.arr.splice(0, this.arr.length).join(''), function(err) { if (err) console.log(err.stack) }); }
}

module.exports = LogLater;
0
répondu Shimon Doodkin 2018-05-07 23:19:51

Améliorez Andres Riofrio, pour gérer n'importe quel nombre d'arguments

var fs = require('fs');
var util = require('util');

var log_file = fs.createWriteStream(__dirname + '/debug.log', {flags : 'w'});
var log_stdout = process.stdout;

console.log = function(...args) {
    var output = args.join(' ');
    log_file.write(util.format(output) + '\r\n');
    log_stdout.write(util.format(output) + '\r\n');
};
0
répondu Liran BarNiv 2018-07-04 04:42:55

Je viens de construire un pack pour le faire, j'espère que vous l'aimez ;) https://www.npmjs.com/package/writelog

0
répondu Phung Thang 2018-07-11 20:41:39

Pour ma part, j'ai simplement pris l'exemple de winston et ajouté la méthode log(...) (parce que winston le nomme info(..):

Console.js:

"use strict"

// Include the logger module
const winston = require('winston');

const logger = winston.createLogger({
    level: 'info',
    format: winston.format.json(),
    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' })
    ]
});

//
// If we're not in production then log to the `console` with the format:
// `${info.level}: ${info.message} JSON.stringify({ ...rest }) `
//
if (process.env.NODE_ENV !== 'production') {
    logger.add(new winston.transports.Console({
        format: winston.format.simple()
    }));
}

// Add log command
logger.log=logger.info;

module.exports = logger;

Ensuite, utilisez simplement dans votre code:

const console = require('Console')

Maintenant, vous pouvez simplement utiliser les fonctions de journal normales dans votre fichier et il va créer un fichier et le connecter à votre console (pendant le débogage / développement). En raison de if (process.env.NODE_ENV !== 'production') { (au cas où vous le voudriez aussi en production)...

0
répondu TechupBusiness 2018-10-05 16:11:10