log4js is one of the best modules in Node.js log processing. Compared with console or TJ debug, the following are indispensable for Node.js projects that are put into production:
This article will give you a comprehensive introduction to log4js, allowing you to use log4js in your project with ease, easy development and debugging, and better monitoring or troubleshooting online.
A small test
The following three lines of code show you the easiest usage of log4js:
// file: simplest.jsvar log4js = require('log4js');var logger = log4js.getLogger();logger.debug("Time:", new Date());Calling .getLogger() can obtain a log4js Logger instance. The usage of this instance is the same as that of console. You can call .debug (also .info, .error and other methods) to output logs.
Run node simplest.js and the output is as follows:
$node simplest.js[2016-08-21 00:01:24.852] [DEBUG] [default] - Time: 2016-08-20T16:01:24.852Z
Time: 2016-08-20T16:01:24.852Z is what we want to output. The previous one contains the specifier [2016-08-21 00:01:24.852] [DEBUG] [default] is listed later.
Isn't it very easy to use? Well, before we dive into the advanced usage of log4js, let's first get familiar with the concepts in log4js.
Level
This is not difficult to understand, it is the grading of logs. Only when logs are hierarchical can log4js better show us logs (different levels of logs use different colors in the console, such as error is usually red), and when production, you can selectively drop-off logs, such as avoiding some sensitive information that belongs to .debugs are leaked.
The logs of log4js are divided into nine levels, and the names and weights of each level are as follows:
{ ALL: new Level(Number.MIN_VALUE, "ALL"), TRACE: new Level(5000, "TRACE"), DEBUG: new Level(10000, "DEBUG"), INFO: new Level(20000, "INFO"), WARN: new Level(30000, "WARN"), ERROR: new Level(40000, "ERROR"), FATAL: new Level(50000, "FATAL"), MARK: new Level(9007199254740992, "MARK"), // 2^53 OFF: new Level(Number.MAX_VALUE, "OFF")}Previous picture:
ALL OFF These two levels are not directly used in business code. The remaining seven are the seven methods corresponding to the Logger instance, .trace .debug .info... In other words, when you call these methods, it is equivalent to leveling these logs. Therefore, the previous [2016-08-21 00:01:24.852] [DEBUG] [default] - Time: 2016-08-20T16:01:24.852Z is the level of this log.
type
log4js also has a concept called category (type). You can set the type of a Logger instance and distinguish logs according to another dimension:
// file: set-catetory.jsvar log4js = require('log4js');var logger = log4js.getLogger('example');logger.debug("Time:", new Date());When obtaining a Logger instance through getLogger, the only parameter that can be passed is loggerCategory (such as 'example'). This parameter specifies which category the Logger instance belongs to. This is the same as TJ's debug:
var debug = require('debug')('worker');setInterval(function(){ debug('doing some work');}, 1000);In debug 'worker', it is also a log classification. OK, come back and run node set-catetory.js:
[2016-08-21 01:16:00.212] [DEBUG] example - Time: 2016-08-20T17:16:00.212Z
The only difference from the previous [2016-08-21 00:01:24.852] [DEBUG] [default] - Time: 2016-08-20T16:01:24.852Z is that [default] has become an example.
What's the use of the category? It's more flexible than the level and provides a second distinction dimension for the logs. For example, you can set a different category for each file, such as in set-catetory.js:
// file: set-catetory.jsvar log4js = require('log4js');var logger = log4js.getLogger('set-catetory.js');logger.debug("Time:", new Date());You can see from the log [2016-08-21 01:24:07.332] [DEBUG] set-catetory.js - Time: 2016-08-20T17:24:07.331Z that this log comes from the set-catetory.js file. Or use different categories for different node packages, so that the logs can be distinguished from which module they originate from.
Appender
Well, now the log has levels and categories, which solves the problem of grading and classification of logs at the entrance. In log4js, the log export problem (i.e. where the log output is output) is solved by Appender.
Default appender
The following are the default appender settings for log4js internal:
// log4js.jsdefaultConfig = { appenders: [{ type: "console" }]}As you can see, when logs are not configured in any way, the logs are output to the console by default.
Set up your own appender
We can set the appender we want through log4js.configure.
// file: custom-appender.jsvar log4js = require('log4js');log4js.configure({ appenders: [{ type: 'file', filename: 'default.log' }]})var logger = log4js.getLogger('custom-appender');logger.debug("Time:", new Date());In the above example, we output the log to the file and run the code. log4js creates a file named default.log in the current directory. [2016-08-21 08:43:21.272] [DEBUG] custom-appender - Time: 2016-08-21T00:43:21.272Z outputs it to the file.
The appender provided by log4js
Console and File are both appenders provided by log4js, in addition to this:
DateFile: The log is output to a file, and the log file can be scrolled in a specific date mode, such as output to default-2016-08-21.log today, and output to default-2016-08-22.log tomorrow;
SMTP: Output log to email;
Mailgun: output logs to Mailgun through the Mailgun API;
levelFilter can be filtered through level;
And so on, some other appenders, you can see the full list here.
Filtering levels and categories
We can adjust the configuration of appender and filter the log levels and categories:
// file: level-and-category.jsvar log4js = require('log4js');log4js.configure({ appenders: [{ type: 'logLevelFilter', level: 'DEBUG', category: 'category1', appender: { type: 'file', filename: 'default.log' } }]})var logger1 = log4js.getLogger('category1');var logger2 = log4js.getLogger('category2');logger1.debug("Time:", new Date());logger1.trace("Time:", new Date());logger2.debug("Time:", new Date());Run, add a log to default.log:
[2016-08-21 10:08:21.630] [DEBUG] category1 - Time: 2016-08-21T02:08:21.629Z
Let's take a look at the code:
Use logLevelFilter and level to filter the log levels, and all logs with weights greater than or equal to DEBUG will be output. This is also the significance of the log level weight mentioned earlier;
Select the category to output the logs through category . The logs under category 2 are filtered out. The configuration also accepts an array, such as ['category1', 'category2'] , so that both categories of logs will be output to the file.
Layout
Layout is an advanced feature provided by log4js. Through layout, we can customize the format of each output log. log4js has built-in four types of formats:
messagePassThrough: only output the content of the log;
basic: The time, log level and category will be added before the content of the log, and the default layout of the log is usually added;
colored/coloured: Add color to the log on the basis of basic, the appender Console uses this layout by default;
pattern: This is a special type that can be defined by any format you want.
An example of pattern:
// file: layout-pattern.jsvar log4js = require('log4js');log4js.configure({ appenders: [{ type: 'console', layout: { type: 'pattern', pattern: '[%r] [%[%5.5p%]] - %m%n' } }]})var logger = log4js.getLogger('layout-pattern');logger.debug("Time:", new Date());%r %p $m $n is a built-in specifier for log4js. You can use this to output some meta information. For more details, you can refer to the log4js documentation.
Let’s explain the positioning of Logger, Appender and Layout in a picture.
Practical combat: output ACCESS log access.log for Node application
To facilitate the problem checking, the logs of application requests entering and exiting are often recorded in production environments. How to implement it using log4js? Just enter the code:
// file: server.jsvar log4js = require('log4js');var express = require('express');log4js.configure({ appenders: [{ type: 'DateFile', filename: 'access.log', pattern: '-yyyy-MM-dd.log', alwaysIncludePattern: true, category: 'access' }]});var app = express();app.use(log4js.connectLogger(log4js.getLogger('access'), { level: log4js.levels.INFO }));app.get('/', function(req,res) { res.send('front-end foreign journal comment');});app.listen(5000);See what we did:
An appender is configured to select a log with the category access from the log and output it to a scrolling file;
log4js.getLogger('access') Gets a Logger instance with a category access, and passes it to the log4js.connectLogger middleware. This middleware collects access information and prints it through this instance.
Start the server and visit http://localhost:5000. You will find that there is an additional file named access.log-2016-08-21.log in the directory, which contains two logs:
[2016-08-21 14:34:04.752] [INFO] access - ::1 - - "GET / HTTP/1.1" 200 18 "" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/52.0.2743.116 Safari/537.36"
[2016-08-21 14:34:05.002] [INFO] access - ::1 - - "GET /favicon.ico HTTP/1.1" 404 24 "http://localhost:5000/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/52.0.2743.116 Safari/537.36"
Through the classification and appender function of log4js logs, we output the access logs to a scroll updated file.
Summarize
This article comprehensively introduces the usage of log4js. Compared with console or simple logging tools, log4js is more complex to use, and of course more powerful, and is suitable for production-level applications. If you are interested, please leave a message to tell us. Next, you may introduce you to how to manage configuration in Node applications.