]>
Commit | Line | Data |
---|---|---|
1 | 'use strict'; | |
2 | ||
3 | const Utilities = require('./utilities'); | |
4 | ||
5 | const internals = { | |
6 | ||
7 | // Maps log levels to their syslog labels | |
8 | ||
9 | kLevelStrings: [ | |
10 | 'emerg', | |
11 | 'alert', | |
12 | 'crit', | |
13 | 'error', | |
14 | 'warning', | |
15 | 'notice', | |
16 | 'info', | |
17 | 'debug' | |
18 | ], | |
19 | ||
20 | // Version of the Cologne Log Format used | |
21 | ||
22 | kLogVersion: '2.0.0' | |
23 | }; | |
24 | ||
25 | /** TYPE DEFINITIONS **/ | |
26 | ||
27 | /** | |
28 | * Main interface for Cologne Loggers | |
29 | * | |
30 | * @interface ILogger | |
31 | */ | |
32 | ||
33 | /** | |
34 | * Receives any number of cologne log objects and logs them. | |
35 | * | |
36 | * @memberof ILogger | |
37 | * @function | |
38 | * @name log | |
39 | */ | |
40 | ||
41 | /** | |
42 | * Main interface for Cologne Formatters | |
43 | * | |
44 | * @interface IFormatter | |
45 | */ | |
46 | ||
47 | /** | |
48 | * Receives a cologne log object and returns a formatted string. | |
49 | * | |
50 | * @memberof IFormatter | |
51 | * @function | |
52 | * @name format | |
53 | * @param {tCologneLog} logObject the log to be formatted | |
54 | * @returns {string} the formatted log | |
55 | */ | |
56 | ||
57 | /** | |
58 | * The main cologne log format. | |
59 | * | |
60 | * @typedef {object} tCologneLog | |
61 | * @property {Bigint} _timestamp the timestamp in nanoseconds | |
62 | * @property {String} _cologneLog main identifier, encodes the version of the | |
63 | * cologne log format being used. | |
64 | * @property {String} _from the origin of the log message. | |
65 | * @property {String} _level the severity level of the log, uses syslog | |
66 | * priorities. | |
67 | * @property {String} _levelString the severity level keyword of the log, | |
68 | * uses syslog priority keywords. | |
69 | */ | |
70 | ||
71 | /** | |
72 | * The main logger class. It can be instantiated with loggers in order to | |
73 | * send messages to different destinations. | |
74 | * | |
75 | * @class Cologne | |
76 | */ | |
77 | const Cologne = class Cologne { | |
78 | ||
79 | constructor(config) { | |
80 | ||
81 | /** | |
82 | * The name of this logger, useful to distinguish between different | |
83 | * loggers. | |
84 | * | |
85 | * @name from | |
86 | * @instance | |
87 | * @memberof Cologne | |
88 | * @type String | |
89 | * @default 'Generic Cologne Logger | |
90 | */ | |
91 | this.from = 'Generic Cologne Logger'; | |
92 | ||
93 | /** | |
94 | * The array containing all the loggers it will call to. | |
95 | * | |
96 | * @name loggers | |
97 | * @instance | |
98 | * @memberof Cologne | |
99 | * @type ILogger[] | |
100 | * @default [] | |
101 | */ | |
102 | this.loggers = []; | |
103 | ||
104 | Object.assign(this, config); | |
105 | } | |
106 | ||
107 | /** | |
108 | * Adds a logger to the current instance. | |
109 | * | |
110 | * @function addLogger | |
111 | * @instance | |
112 | * @memberof Cologne | |
113 | * @param {ILogger} logger the logger to add | |
114 | */ | |
115 | addLogger(logger) { | |
116 | ||
117 | this.loggers.push(logger); | |
118 | } | |
119 | ||
120 | /** | |
121 | * Removes a logger from the current instance. | |
122 | * | |
123 | * @function removeLogger | |
124 | * @instance | |
125 | * @memberof Cologne | |
126 | * @param {ILogger} logger the logger to remove | |
127 | * @return {ILogger[]} the removed log, inside an array. | |
128 | */ | |
129 | removeLogger(logger) { | |
130 | ||
131 | const index = this.loggers.indexOf(logger); | |
132 | if (index >= 0) { | |
133 | this.loggers.splice(index, 1); | |
134 | } | |
135 | } | |
136 | ||
137 | /** | |
138 | * Given a message, it builds a cologne log object without logging it. | |
139 | * If you send a cologne log object, it will only update the level. | |
140 | * | |
141 | * If the message is an object, the log object will be extended with | |
142 | * its properties. | |
143 | * | |
144 | * @function buildLog | |
145 | * @instance | |
146 | * @memberof Cologne | |
147 | * @param {*} message The message to log | |
148 | * @param {number} [level=6] The level of the message to log | |
149 | * @return {tCologneLog} a cologne log object | |
150 | */ | |
151 | buildLog(rawMessage, level) { | |
152 | ||
153 | if (typeof rawMessage === 'undefined' || rawMessage === null || !rawMessage._cologneLog) { | |
154 | ||
155 | const message = typeof rawMessage === 'object' ? Utilities.stringify(rawMessage) : rawMessage; | |
156 | ||
157 | const logObject = { | |
158 | message: String(message), | |
159 | _cologneLog: internals.kLogVersion, | |
160 | _from: this.from, | |
161 | _level: level || 6, | |
162 | _timestamp: Utilities.now() | |
163 | }; | |
164 | ||
165 | logObject._levelString = internals.kLevelStrings[logObject._level]; | |
166 | ||
167 | if (typeof rawMessage === 'object') { | |
168 | Object.assign(logObject, rawMessage); | |
169 | } | |
170 | ||
171 | return logObject; | |
172 | } | |
173 | ||
174 | rawMessage._level = level || rawMessage._level; | |
175 | rawMessage._levelString = internals.kLevelStrings[rawMessage._level]; | |
176 | ||
177 | return rawMessage; | |
178 | } | |
179 | ||
180 | /** | |
181 | * Default log function. Sends arguments to loggers. If not specified in log | |
182 | * object, it will set the severity to 6 - INFO. | |
183 | * | |
184 | * @function log | |
185 | * @instance | |
186 | * @memberof Cologne | |
187 | */ | |
188 | log(...logs) { | |
189 | ||
190 | this._log(null, ...logs); | |
191 | } | |
192 | ||
193 | /** | |
194 | * Logs with debug level | |
195 | * | |
196 | * @function debug | |
197 | * @instance | |
198 | * @memberof Cologne | |
199 | */ | |
200 | debug(...logs) { | |
201 | ||
202 | this._log(7, ...logs); | |
203 | } | |
204 | ||
205 | /** | |
206 | * Logs with info level | |
207 | * | |
208 | * @function info | |
209 | * @instance | |
210 | * @memberof Cologne | |
211 | */ | |
212 | info(...logs) { | |
213 | ||
214 | this._log(6, ...logs); | |
215 | } | |
216 | ||
217 | /** | |
218 | * Logs with notice level | |
219 | * | |
220 | * @function notice | |
221 | * @instance | |
222 | * @memberof Cologne | |
223 | */ | |
224 | notice(...logs) { | |
225 | ||
226 | this._log(5, ...logs); | |
227 | } | |
228 | ||
229 | /** | |
230 | * Logs with warn level | |
231 | * | |
232 | * @function warn | |
233 | * @instance | |
234 | * @memberof Cologne | |
235 | */ | |
236 | warn(...logs) { | |
237 | ||
238 | this._log(4, ...logs); | |
239 | } | |
240 | ||
241 | /** | |
242 | * Logs with error level | |
243 | * | |
244 | * @function error | |
245 | * @instance | |
246 | * @memberof Cologne | |
247 | */ | |
248 | error(...logs) { | |
249 | ||
250 | this._log(3, ...logs); | |
251 | } | |
252 | ||
253 | // Private method that builds all the logs and sends them to the loggers. | |
254 | ||
255 | _log(level, ...logs) { | |
256 | ||
257 | const structuredLogs = logs.map((log) => this.buildLog(log, level)); | |
258 | ||
259 | for (const logger of this.loggers) { | |
260 | logger.log(...structuredLogs); | |
261 | } | |
262 | } | |
263 | }; | |
264 | ||
265 | /** | |
266 | * Namespace that includes the built-in formatters. | |
267 | * | |
268 | * @namespace Formatters | |
269 | */ | |
270 | const Formatters = {}; | |
271 | Formatters.Simple = require('./formatters/simple'); | |
272 | Formatters.Token = require('./formatters/token'); | |
273 | ||
274 | /** | |
275 | * Namespace that includes the built-in loggers. | |
276 | * | |
277 | * @namespace Loggers | |
278 | */ | |
279 | const Loggers = {}; | |
280 | Loggers.Console = require('./loggers/console'); | |
281 | Loggers.File = require('./loggers/file'); | |
282 | ||
283 | module.exports = { | |
284 | Cologne, | |
285 | Formatters, | |
286 | Loggers, | |
287 | Utilities | |
288 | }; |