122 lines
3.1 KiB
JavaScript
122 lines
3.1 KiB
JavaScript
/* This Source Code Form is subject to the terms of the Mozilla Public
|
|
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
|
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
|
|
|
const util = require('util');
|
|
|
|
const stacktrace = require('stack-trace');
|
|
const _Symbol = require('symbol');
|
|
|
|
const LEVELS = require('./levels');
|
|
const printf = require('./utils/printf');
|
|
|
|
const UNCAUGHT_SYMBOL = _Symbol();
|
|
const LOG_VERSION = 1; // increment when log format changes
|
|
const HOSTNAME = require('os').hostname();
|
|
const MESSAGE_CACHE = _Symbol();
|
|
const PID = process.pid;
|
|
|
|
// stack formatter helper
|
|
function stack(e) {
|
|
return {
|
|
toString: function() {
|
|
// first line is err.message, which we already show, so start from
|
|
// second line
|
|
return e.stack.substr(e.stack.indexOf('\n'));
|
|
},
|
|
toJSON: function() {
|
|
return stacktrace.parse(e);
|
|
}
|
|
};
|
|
}
|
|
|
|
function Trace(fn) {
|
|
Error.captureStackTrace(this, fn);
|
|
}
|
|
|
|
Trace.prototype.toJSON = function() {
|
|
return '[object Trace]';
|
|
};
|
|
|
|
function Record(name, level, args) {
|
|
this.name = name;
|
|
this.level = level;
|
|
this.levelname = LEVELS.getLevelName(level);
|
|
this.args = args;
|
|
this.pid = PID;
|
|
this.host = HOSTNAME;
|
|
this.v = LOG_VERSION;
|
|
this.timestamp = Date.now();
|
|
|
|
var trace;
|
|
var isErr = false;
|
|
var i = args.length;
|
|
while (i--) {
|
|
var a = args[i];
|
|
if (a && ((isErr = util.isError(a)) || a instanceof Trace)) {
|
|
trace = a;
|
|
break;
|
|
}
|
|
}
|
|
this.exception = isErr || undefined;
|
|
this.uncaughtException = isErr ? trace[UNCAUGHT_SYMBOL] : undefined;
|
|
this.stack = trace && trace.stack ? stack(trace) : undefined;
|
|
}
|
|
|
|
Record.prototype.name = undefined;
|
|
Record.prototype.level = undefined;
|
|
Record.prototype.levelname = undefined;
|
|
Record.prototype.args = undefined;
|
|
Record.prototype.pid = undefined;
|
|
Record.prototype.host = undefined;
|
|
Record.prototype.v = undefined;
|
|
Record.prototype.timestamp = undefined;
|
|
Record.prototype.exception = undefined;
|
|
Record.prototype.uncaughtException = undefined;
|
|
Record.prototype.stack = undefined;
|
|
Record.prototype[MESSAGE_CACHE] = undefined;
|
|
|
|
Object.defineProperty(Record.prototype, 'message', {
|
|
enumerable: true,
|
|
get: function() {
|
|
var message = this[MESSAGE_CACHE];
|
|
if (!message) {
|
|
var args = this.args;
|
|
message = args[0];
|
|
var isString = typeof message === 'string';
|
|
if (!isString || args.length > 1) {
|
|
if (!isString) {
|
|
args = new Array(this.args.length + 1);
|
|
args[0] = '%?';
|
|
var i = args.length - 1;
|
|
while (i--) {
|
|
args[i + 1] = this.args[i];
|
|
}
|
|
}
|
|
message = printf.apply(null, args);
|
|
}
|
|
this[MESSAGE_CACHE] = message;
|
|
}
|
|
return message;
|
|
}
|
|
});
|
|
|
|
Record.prototype.toJSON = function toJSON() {
|
|
var json = {};
|
|
var keys = Object.keys(this);
|
|
var i = keys.length;
|
|
while (i--) {
|
|
var key = keys[i];
|
|
if (key === 'timestamp') {
|
|
json.timestamp = new Date(this.timestamp);
|
|
} else {
|
|
json[key] = this[key];
|
|
}
|
|
}
|
|
return json;
|
|
};
|
|
|
|
Record._Trace = Trace;
|
|
Record._UNCAUGHT_SYMBOL = UNCAUGHT_SYMBOL;
|
|
module.exports = Record;
|