NodeJS Winston not writing in the log file - node.js

I'm trying to use Winston to create logs, but it is not writing in the file.
I have the following file in controllers/myControler/myFile.js
const path = require('path');
const winston = require('winston');
const filename = path.join(__dirname, 'testLog.log');
const logger = winston.createLogger({
transports: [
new winston.transports.Console({ filename, level: 'error' })
]
});
exports.test = async (req, res, next) => {
logger.log({
level: 'error',
message: 'Test'
});
}
I have the file testLog.log in the root of my project.
When I run the application, I can see in the terminal:
{"level":"error","message":"Test"}
However, the testLog.log file still empty.
Thanks

new winston.transports.Console does not accept filename option.
You have to append File transport for your logger.
const logger = winston.createLogger({
transports: [
new winston.transports.Console({ level: 'error' }),
// new line
new winston.transports.File({ filename, level: 'error' }),
]
});

Related

winston 3.2.1 version is not creating log file

I tried to create winston(logger file) using node js.winston 2.4.0 version its sucessfully storeing info and error in log file.but latest version its created log file but cant stored error and info messages.How to fix it
Winston.js
var winston = require('winston');
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' })
]
});
//
// 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()
}));
}
app.js
/**
* #fileoverview Root file of the application.
*/
// Import ExpressJS
const winston = require('winston');
const express = require('express');
const app = express();
// StartUp Processes
require('./startup/logging_error_startup');
require('./startup/routes_startup')(app);
require('./startup/check_security_key_startup')();
require('./startup/validation_startup')();
require('./startup/swagger_startup')(app);
require('./startup/production_startup')(app);
// Start the server
const port = process.env.PORT || 4202;
app.listen(port, () => winston.info(`Server Started and Listening on port ${port}`));
I got the output
winston] Attempt to write logs with no transports {"message":"Server Started and Listening on port 4202","level":"info"}
You need to import the logger object from Winston.js file into app.js. In your app.js code, the Winston import is for the npm package and not for the logger object created in Winston.js.
In Winston.js, export the logger object:
var winston = require('winston');
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' })
]
});
//
// 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()
}));
}
module.exports = logger;
And in app.js, use that logger object after importing.
const logger = require('./Winston'); //assuming Winston.js is in the same folder level as app.js
const express = require('express');
const app = express();
// StartUp Processes
require('./startup/logging_error_startup');
require('./startup/routes_startup')(app);
require('./startup/check_security_key_startup')();
require('./startup/validation_startup')();
require('./startup/swagger_startup')(app);
require('./startup/production_startup')(app);
// Start the server
const port = process.env.PORT || 4202;
app.listen(port, () => logger.info(`Server Started and Listening on port ${port}`));
Alternatively you can modify the default logger in your winston.js with
var winston = require('winston');
const newLogger = winston.createLogger({
level: 'info',
format: winston.format.json(),
defaultMeta: { service: 'user-service' },
transports: [.........
winston.add(newLogger);
instead of
var winston = require('winston');
const logger = winston.createLogger({....
module.exports = logger
and import the default logger in each file with
const logger = require('winston')
logger.info('log');
without dealing with relative paths each time you import the logger to different files.

Winston logging in console but not in the log files

I'm using Winston for logging in my project. I can see the logs in the console but there is no logging inside the log files.
Winston.js file
var appRoot = require('app-root-path');
var winston = require('winston');
const {transports, createLogger, format} = require('winston');
winston.addColors( winston.config.npm.colors );
const logger = winston.createLogger({
level: 'info',
format: format.combine(
format.timestamp({format:'MM-YY-DD hh:mm:ss a'}),
format.json(),
),
transports: [
new winston.transports.File({ filename: './logs/error.log', level: 'error' }),
new winston.transports.File({ handleExceptions: true,colorize:true,
json: true,filename: './logs/app.log',
})
]
});
if (process.env.NODE_ENV !== 'production') {
logger.add(new winston.transports.Console({
format: winston.format.simple()
}));
}
module.exports = logger;
Server.js code
var morgan = require('morgan');
var winston = require('./server/config/winston');
Node version
8.11.3
Winston version
3.1.0
You need to make sure 'logs' folder exists. Winston doesnt take care of non-existent folder, nor giving any warning or errors.
You can put following code in your server.js
var fs = require( 'fs' );
var logDir = 'logs';
if ( !fs.existsSync( logDir ) ) {
fs.mkdirSync( logDir );
}
winston.info('Hey NODE');
Using the absolute folder path inside the winston.js solved the problem.

node.js multiple initialization of library is fine?

I am using node.js with libraries like winston, mongodb and etc. I split nodejs to multiple files for easy maintenance like index.js, user.js, posting.js, database.js, logging.js, and etc.
logging.js is like below:
var config = require('./config'),
path = require ('path'),
winston = require('winston'),
winstonRotate = require('winston-daily-rotate-file');
winston.level = config.appSetting.winstonLogLevel;
var logger = new (winston.Logger)({
transports: [
new (winston.transports.Console)(),
new (winstonRotate)({
name: 'info-file',
datePattern: '.yyyyMMdd',
filename: path.join(__dirname, "logs", "info.log"),
level: 'info'
}),
new (winstonRotate)({
name: 'error-file',
datePattern: '.yyyyMMdd',
filename: path.join(__dirname, "logs", "error.log"),
level: 'error'
}),
new (winstonRotate)({
name: 'debug-file',
datePattern: '.yyyyMMdd',
filename: path.join(__dirname, "logs", "debug.log"),
level: 'debug'
}),
new (winstonRotate)({
name: 'warn-file',
datePattern: '.yyyyMMdd',
filename: path.join(__dirname, "logs", "warn.log"),
level: 'warn'
})
]
});
module.exports = logger;
database.js
var mongoClient = require('mongodb').MongoClient,
mongodbObjectID = require('mongodb').ObjectID,
logger = require('./logging'), database;
// Connect to the db
mongoClient.connect(config.appSetting.dbConnectionString, function(err, db) {
if(!err) {
database = db;
logger.info("Connected to DB");
} else {
logger.error("Failed to connect to moolahome mongodb : " + err);
console.dir(err);
process.exit(1);
}
});
module.exports = database;
I add logging.js to index.js, user.js and posting.js and database.js for logging and this lead to 4 times initialization of logger.
I add database.js to index.js, user.js and posting.js nd this lead to 3 times initialization of database.
Is this ok or need to make logger and database to singleton?
All libraries (or modules) are cached in require object after first load.
Check this out.
So, it's ok for runtime and sure it's your own decision about app structure :)

NodeJS Winston DailyRotateFile not writing

I'm trying to setup a simple daily rotation log write with:
// Create file transport
transports.push(new winston.transports.DailyRotateFile({
name: 'file',
datePattern: '.yyyy-MM-ddTHH',
filename: path.join(logPath, 'http')
}));
// Create new logger
var logger = new winston.Logger({
transports: transports
});
It's creating the log file just fine, however logger.info(some_data) doesn't write anything to the log.
Any thoughts, or even another solution?
This one works with minute rotation:
var winston = require('winston');
var logger = new (winston.Logger)({
transports: [
new (winston.transports.DailyRotateFile)({ filename: 'logFile', datePattern: '.yyyy-MM-dd_HH-mm' })
]
});
logger.info('Hello my friend');

Node winston cannot support multiple file transport?

I want to show error logs in one file and all logs in another file. To do that, I wrote two file transports which give the following error on compilation:
'use strict';
var winston = require('winston'),
config = require('./config');
var logger = new (winston.Logger)({
transports: [
new (winston.transports.Console)({level:'debug',handleExceptions: true,prettyPrint: true,silent:false,timestamp: true,colorize: true,json: false}),
new (winston.transports.File)({ filename: './server/logs/bv_common.log',level:'debug',maxsize: 1024000,maxFiles: 10, handleExceptions: true,json: false}),
new (winston.transports.File)({ filename: './server/logs/bv_error.log',level:'debug',maxsize: 1024000,maxFiles: 10, handleExceptions: true,json: false,level:'error'})
]
});
module.exports = logger;
Result:
[ 'Error: Transport already attached: file',
var logger = new (winston.Logger)({
exitOnError: false, //don't crash on exception
transports: [
new (winston.transports.Console)({level:'debug',handleExceptions: true,prettyPrint: true,silent:false,timestamp: true,colorize: true,json: false}),
new (winston.transports.File)({ filename: './server/logs/' + config.appname +'_common.log',name:'file.all',level:'debug',maxsize: 1024000,maxFiles: 10, handleExceptions: true,json: false}),
new (winston.transports.File)({ filename: './server/logs/' + config.appname +'_error.log',name:'file.error',level:'error',maxsize: 1024000,maxFiles: 10, handleExceptions: true,json: false})
]
});
The above code , especially with name parameter for shared transport, we can use multiple file transports for loggers.
You are getting this error because you are not providing a 'name' attribute to your file transports.

Resources