metalog 3.1.7 → 3.1.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -2,6 +2,10 @@
2
2
 
3
3
  ## [Unreleased][unreleased]
4
4
 
5
+ ## [3.1.8][] - 2022-03-30
6
+
7
+ - Add support for json-only logs
8
+
5
9
  ## [3.1.7][] - 2022-03-17
6
10
 
7
11
  - Fix unlink empty files
@@ -64,7 +68,8 @@
64
68
 
65
69
  First generation of Metarhia Logger
66
70
 
67
- [unreleased]: https://github.com/metarhia/metalog/compare/v3.1.7...HEAD
71
+ [unreleased]: https://github.com/metarhia/metalog/compare/v3.1.8...HEAD
72
+ [3.1.8]: https://github.com/metarhia/metalog/compare/v3.1.7...v3.1.8
68
73
  [3.1.7]: https://github.com/metarhia/metalog/compare/v3.1.6...v3.1.7
69
74
  [3.1.6]: https://github.com/metarhia/metalog/compare/v3.1.5...v3.1.6
70
75
  [3.1.5]: https://github.com/metarhia/metalog/compare/v3.1.4...v3.1.5
package/README.md CHANGED
@@ -21,6 +21,7 @@ const logger = await metalog.openLog({
21
21
  writeBuffer: 64 * 1024, // buffer size (default 64kb)
22
22
  keepDays: 5, // delete after N days, 0 - disable
23
23
  home: process.cwd(), // remove substring from paths
24
+ json: false, // print logs in JSON format, by default false
24
25
  });
25
26
 
26
27
  const { console } = logger;
package/metalog.d.ts CHANGED
@@ -8,6 +8,7 @@ interface LoggerOptions {
8
8
  writeInterval: number;
9
9
  writeBuffer: number;
10
10
  keepDays: number;
11
+ json?: boolean;
11
12
  toFile?: Array<string>;
12
13
  toStdout?: Array<string>;
13
14
  }
package/metalog.js CHANGED
@@ -77,10 +77,13 @@ const getNextReopen = () => {
77
77
  return nextDate - curTime + DAY_MILLISECONDS;
78
78
  };
79
79
 
80
+ const isError = (val) =>
81
+ Object.prototype.toString.call(val) === '[object Error]';
82
+
80
83
  class Console {
81
84
  constructor(write) {
82
85
  this._write = write;
83
- this._groupIndent = '';
86
+ this._groupIndent = 0;
84
87
  this._counts = new Map();
85
88
  this._times = new Map();
86
89
  }
@@ -89,7 +92,7 @@ class Console {
89
92
  try {
90
93
  console.assert(assertion, ...args);
91
94
  } catch (err) {
92
- this._write('error', `${this._groupIndent}${err.stack}`);
95
+ this._write('error', this._groupIndent, err.stack);
93
96
  }
94
97
  }
95
98
 
@@ -102,7 +105,7 @@ class Console {
102
105
  let cnt = this._counts.get(label) || 0;
103
106
  cnt++;
104
107
  this._counts.set(label, cnt);
105
- this._write('debug', `${this._groupIndent}${label}: ${cnt}`);
108
+ this._write('debug', this._groupIndent, `${label}: ${cnt}`);
106
109
  }
107
110
 
108
111
  countReset(label = 'default') {
@@ -110,23 +113,38 @@ class Console {
110
113
  }
111
114
 
112
115
  debug(...args) {
113
- const msg = util.format(...args);
114
- this._write('debug', `${this._groupIndent}${msg}`);
116
+ this._write('debug', this._groupIndent, ...args);
115
117
  }
116
118
 
117
119
  dir(...args) {
118
- const msg = util.inspect(...args);
119
- this._write('debug', `${this._groupIndent}${msg}`);
120
+ this._write('debug', this._groupIndent, ...args);
120
121
  }
121
122
 
122
- error(...args) {
123
+ trace(...args) {
123
124
  const msg = util.format(...args);
124
- this._write('error', `${this._groupIndent}${msg}`);
125
+ const err = new Error(msg);
126
+ this._write('debug', this._groupIndent, `Trace${err.stack}`);
127
+ }
128
+
129
+ info(...args) {
130
+ this._write('info', this._groupIndent, ...args);
131
+ }
132
+
133
+ log(...args) {
134
+ this._write('log', this._groupIndent, ...args);
135
+ }
136
+
137
+ warn(...args) {
138
+ this._write('warn', this._groupIndent, ...args);
139
+ }
140
+
141
+ error(...args) {
142
+ this._write('error', this._groupIndent, ...args);
125
143
  }
126
144
 
127
145
  group(...args) {
128
146
  if (args.length !== 0) this.log(...args);
129
- this._groupIndent = ' '.repeat(this._groupIndent.length + INDENT);
147
+ this._groupIndent += INDENT;
130
148
  }
131
149
 
132
150
  groupCollapsed(...args) {
@@ -135,21 +153,11 @@ class Console {
135
153
 
136
154
  groupEnd() {
137
155
  if (this._groupIndent.length === 0) return;
138
- this._groupIndent = ' '.repeat(this._groupIndent.length - INDENT);
139
- }
140
-
141
- info(...args) {
142
- const msg = util.format(...args);
143
- this._write('info', `${this._groupIndent}${msg}`);
144
- }
145
-
146
- log(...args) {
147
- const msg = util.format(...args);
148
- this._write('log', `${this._groupIndent}${msg}`);
156
+ this._groupIndent -= INDENT;
149
157
  }
150
158
 
151
159
  table(tabularData) {
152
- this._write('log', JSON.stringify(tabularData));
160
+ this._write('log', 0, JSON.stringify(tabularData));
153
161
  }
154
162
 
155
163
  time(label = 'default') {
@@ -160,31 +168,18 @@ class Console {
160
168
  const startTime = this._times.get(label);
161
169
  const totalTime = process.hrtime(startTime);
162
170
  const totalTimeMs = totalTime[0] * 1e3 + totalTime[1] / 1e6;
163
- const msg = `${this._groupIndent}${label}: ${totalTimeMs}ms`;
164
- this.timeLog(label, msg);
171
+ this.timeLog(label, `${label}: ${totalTimeMs}ms`);
165
172
  this._times.delete(label);
166
173
  }
167
174
 
168
175
  timeLog(label, ...args) {
169
176
  const startTime = this._times.get(label);
170
177
  if (startTime === undefined) {
171
- const msg = `${this._groupIndent}Warning: No such label '${label}'`;
172
- this._write('warn', msg);
178
+ const msg = `Warning: No such label '${label}'`;
179
+ this._write('warn', this._groupIndent, msg);
173
180
  return;
174
181
  }
175
- const msg = util.format(...args);
176
- this._write('debug', msg);
177
- }
178
-
179
- trace(...args) {
180
- const msg = util.format(...args);
181
- const err = new Error(msg);
182
- this._write('debug', `${this._groupIndent}Trace${err.stack}`);
183
- }
184
-
185
- warn(...args) {
186
- const msg = util.format(...args);
187
- this._write('warn', `${this._groupIndent}${msg}`);
182
+ this._write('debug', this._groupIndent, ...args);
188
183
  }
189
184
  }
190
185
 
@@ -192,7 +187,7 @@ class Logger extends events.EventEmitter {
192
187
  constructor(args) {
193
188
  super();
194
189
  const { workerId = 0, createStream = fs.createWriteStream } = args;
195
- const { writeInterval, writeBuffer, keepDays, home } = args;
190
+ const { writeInterval, writeBuffer, keepDays, home, json } = args;
196
191
  const { toFile, toStdout } = args;
197
192
  this.active = false;
198
193
  this.path = args.path;
@@ -202,6 +197,7 @@ class Logger extends events.EventEmitter {
202
197
  this.writeBuffer = writeBuffer || DEFAULT_BUFFER_SIZE;
203
198
  this.keepDays = keepDays || DEFAULT_KEEP_DAYS;
204
199
  this.home = home;
200
+ this.json = Boolean(json);
205
201
  this.stream = null;
206
202
  this.reopenTimer = null;
207
203
  this.flushTimer = null;
@@ -211,7 +207,7 @@ class Logger extends events.EventEmitter {
211
207
  this.toFile = logTypes(toFile);
212
208
  this.fsEnabled = Object.keys(this.toFile).length !== 0;
213
209
  this.toStdout = logTypes(toStdout);
214
- this.console = new Console((type, message) => this.write(type, message));
210
+ this.console = new Console((...args) => this.write(...args));
215
211
  return this.open();
216
212
  }
217
213
 
@@ -323,25 +319,63 @@ class Logger extends events.EventEmitter {
323
319
  }
324
320
  }
325
321
 
326
- write(type, s) {
327
- const date = new Date();
328
- const dateTime = date.toISOString();
322
+ format(type, indent, ...args) {
329
323
  const normalize = type === 'error' || type === 'debug';
330
- const message = normalize ? this.normalizeStack(s) : s;
324
+ const s = `${' '.repeat(indent)}${util.format(...args)}`;
325
+ return normalize ? this.normalizeStack(s) : s;
326
+ }
327
+
328
+ formatPretty(type, indent, ...args) {
329
+ const dateTime = new Date().toISOString();
330
+ const message = this.format(type, indent, ...args);
331
+ const normalColor = TEXT_COLOR[type];
332
+ const markColor = TYPE_COLOR[type];
333
+ const time = normalColor(dateTime.substring(TIME_START, TIME_END));
334
+ const id = normalColor(this.workerId);
335
+ const mark = markColor(' ' + type.padEnd(TYPE_LENGTH));
336
+ const msg = normalColor(message);
337
+ return `${time} ${id} ${mark} ${msg}`;
338
+ }
339
+
340
+ formatFile(type, indent, ...args) {
341
+ const dateTime = new Date().toISOString();
342
+ const message = this.format(type, indent, ...args);
343
+ const msg = metautil.replace(message, '\n', LINE_SEPARATOR);
344
+ return `${dateTime} [${type}] ${msg}`;
345
+ }
346
+
347
+ formatJson(type, indent, ...args) {
348
+ const log = {
349
+ timestamp: new Date().toISOString(),
350
+ workerId: this.workerId,
351
+ level: type,
352
+ message: null,
353
+ };
354
+ if (isError(args[0])) {
355
+ log.err = this.expandError(args[0]);
356
+ args = args.slice(1);
357
+ } else if (typeof args[0] === 'object') {
358
+ Object.assign(log, args[0]);
359
+ if (isError(log.err)) log.err = this.expandError(log.err);
360
+ if (isError(log.error)) log.error = this.expandError(log.error);
361
+ args = args.slice(1);
362
+ }
363
+ log.message = util.format(...args);
364
+ return JSON.stringify(log);
365
+ }
366
+
367
+ write(type, indent, ...args) {
331
368
  if (this.toStdout[type]) {
332
- const normalColor = TEXT_COLOR[type];
333
- const markColor = TYPE_COLOR[type];
334
- const time = normalColor(dateTime.substring(TIME_START, TIME_END));
335
- const id = normalColor(this.workerId);
336
- const mark = markColor(' ' + type.padEnd(TYPE_LENGTH));
337
- const msg = normalColor(message);
338
- const line = `${time} ${id} ${mark} ${msg}\n`;
339
- process.stdout.write(line);
369
+ const line = this.json
370
+ ? this.formatJson(type, indent, ...args)
371
+ : this.formatPretty(type, indent, ...args);
372
+ process.stdout.write(line + '\n');
340
373
  }
341
374
  if (this.toFile[type]) {
342
- const msg = metautil.replace(message, '\n', LINE_SEPARATOR);
343
- const line = `${dateTime} [${type}] ${msg}\n`;
344
- const buffer = Buffer.from(line);
375
+ const line = this.json
376
+ ? this.formatJson(type, indent, ...args)
377
+ : this.formatFile(type, indent, ...args);
378
+ const buffer = Buffer.from(line + '\n');
345
379
  this.buffer.push(buffer);
346
380
  }
347
381
  }
@@ -377,6 +411,14 @@ class Logger extends events.EventEmitter {
377
411
  if (this.home) res = metautil.replace(res, this.home, '');
378
412
  return res;
379
413
  }
414
+
415
+ expandError(err) {
416
+ return {
417
+ message: err.message,
418
+ stack: this.normalizeStack(err.stack),
419
+ ...err,
420
+ };
421
+ }
380
422
  }
381
423
 
382
424
  const openLog = async (args) => new Logger(args);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "metalog",
3
- "version": "3.1.7",
3
+ "version": "3.1.8",
4
4
  "author": "Timur Shemsedinov <timur.shemsedinov@gmail.com>",
5
5
  "description": "Logger for Metarhia",
6
6
  "license": "MIT",