timer-logs
Advanced tools
Comparing version 1.0.6 to 1.1.0
declare type Config = { | ||
/** | ||
* the severity of the log, changes the way its printed in google cloud logging | ||
* the severity of the log, defaults to DEFAULT | ||
*/ | ||
severity?: 'INFO' | 'ERROR' | 'DEBUG' | 'NOTICE'; | ||
severity?: 'DEFAULT' | 'DEBUG' | 'INFO' | 'NOTICE' | 'WARNING' | 'ERROR' | 'CRITICAL' | 'ALERT' | 'EMERGENCY'; | ||
/** | ||
@@ -18,3 +18,29 @@ * the label of the log. gets printed in the google cloud summary message | ||
filename: string; | ||
/** | ||
* This will be printed on all log output, to distinguish logs output by this library from other logging in | ||
* your application. Its possible but not recommended to override it in the config. | ||
*/ | ||
loggerName?: 'timer-logs logger'; | ||
/** | ||
* This will be printed on all log output from the instance configured with it, to help identify where a log has | ||
* come from, or what it relates to. This is mostly useful if you have | ||
* multiple instances of this class in a single file. Otherwise the file acts as an identifier. | ||
*/ | ||
logClass?: string; | ||
/** | ||
* Omit the stack trace from error logging. (still prints the provided file path) | ||
*/ | ||
omitStackTrace?: boolean; | ||
}; | ||
declare enum Severity { | ||
DEFAULT = "DEFAULT", | ||
DEBUG = "DEBUG", | ||
INFO = "INFO", | ||
NOTICE = "NOTICE", | ||
WARNING = "WARNING", | ||
ERROR = "ERROR", | ||
CRITICAL = "CRITICAL", | ||
ALERT = "ALERT", | ||
EMERGENCY = "EMERGENCY" | ||
} | ||
export default class Timer { | ||
@@ -26,2 +52,4 @@ private readonly startTime; | ||
private readonly savedTimes; | ||
private splitFilePath; | ||
private readonly uniqueId; | ||
/** | ||
@@ -33,2 +61,4 @@ * Create a new Timer object. Can have multiple timers within this object. | ||
constructor(config: Config); | ||
private _severity; | ||
set severity(value: Severity); | ||
/** | ||
@@ -65,3 +95,3 @@ * Start a new timer | ||
/** | ||
* prints times to the console in JSON format for Google Cloud Logging. | ||
* Prints times to the console in JSON format for Google Cloud Logging. | ||
* | ||
@@ -123,2 +153,21 @@ * Will end the most recently started timer if not already ended | ||
genericError(e: Error, message?: string): void; | ||
/** | ||
* Logs any type of Error in a separate log to the main Timer. | ||
* | ||
* This is a convenience wrapper on `genericError` to allow you to add a custom message, | ||
* and still use in a promise catch clause. | ||
* @param message custom message to log with error. | ||
* | ||
* @example | ||
* await new Promise | ||
*/ | ||
genericErrorCustomMessage(message: string): (e: Error) => void; | ||
/** | ||
* Internal printing method which makes sure all of the properties are printed with each log. | ||
* | ||
* @param details object of | ||
* @param severity | ||
* @private | ||
*/ | ||
private printLog; | ||
} | ||
@@ -125,0 +174,0 @@ /** |
121
index.js
"use strict"; | ||
Object.defineProperty(exports, "__esModule", { value: true }); | ||
const crypto = require("crypto"); | ||
var Severity; | ||
(function (Severity) { | ||
Severity["DEFAULT"] = "DEFAULT"; | ||
Severity["DEBUG"] = "DEBUG"; | ||
Severity["INFO"] = "INFO"; | ||
Severity["NOTICE"] = "NOTICE"; | ||
Severity["WARNING"] = "WARNING"; | ||
Severity["ERROR"] = "ERROR"; | ||
Severity["CRITICAL"] = "CRITICAL"; | ||
Severity["ALERT"] = "ALERT"; | ||
Severity["EMERGENCY"] = "EMERGENCY"; | ||
})(Severity || (Severity = {})); | ||
class Timer { | ||
@@ -9,6 +22,13 @@ constructor(config) { | ||
this.config.details = (_a = config === null || config === void 0 ? void 0 : config.details) !== null && _a !== void 0 ? _a : {}; | ||
this.splitFilePath = config.filename.split('/').filter(p => p.length > 0); | ||
this.savedTimes = {}; | ||
if (((_b = this.config) === null || _b === void 0 ? void 0 : _b.label) !== undefined) | ||
this.start(this.config.label); | ||
this._severity = Severity[(_b = this.config.severity) !== null && _b !== void 0 ? _b : Severity.DEFAULT]; | ||
if (this.config.label === undefined) | ||
this.config.label = this.splitFilePath.slice(-1)[0].split('.')[0]; | ||
this.uniqueId = crypto.randomBytes(8).toString('hex'); | ||
this.start(this.config.label); | ||
} | ||
set severity(value) { | ||
this._severity = value; | ||
} | ||
start(label) { | ||
@@ -48,3 +68,2 @@ console.assert(!this.savedTimes.hasOwnProperty(label), 'Timer started more than once for same label'); | ||
flush() { | ||
var _a, _b, _c, _d, _e, _f; | ||
this.finishTime = Date.now(); | ||
@@ -54,16 +73,15 @@ if (this.mostRecentlyStartedLabel && !this.savedTimes[this.mostRecentlyStartedLabel].finishTime) | ||
const printObject = { | ||
severity: (_b = (_a = this.config) === null || _a === void 0 ? void 0 : _a.severity) !== null && _b !== void 0 ? _b : 'INFO', | ||
message: ((_d = (_c = this.config) === null || _c === void 0 ? void 0 : _c.label) !== null && _d !== void 0 ? _d : `Timer`) + `: ${this.finishTime - this.startTime}ms`, | ||
filename: (_e = this.config) === null || _e === void 0 ? void 0 : _e.filename | ||
message: this.config.label + `: ${this.finishTime - this.startTime}ms` | ||
}; | ||
const printMap = new Map(Object.entries(printObject)); | ||
Object.entries(this.savedTimes) | ||
.forEach(([label, times]) => { | ||
if (typeof times.time === 'number') | ||
printObject[label] = times.time; | ||
printMap.set(label, times.time); | ||
}); | ||
if ((_f = this === null || this === void 0 ? void 0 : this.config) === null || _f === void 0 ? void 0 : _f.details) | ||
if (this.config.details) | ||
Object.entries(this.config.details).forEach(([label, detail]) => { | ||
printObject[label] = detail; | ||
printMap.set(label, detail); | ||
}); | ||
console.log(JSON.stringify(printObject)); | ||
this.printLog(printMap, this._severity); | ||
return this.finishTime - this.startTime; | ||
@@ -83,35 +101,68 @@ } | ||
customError(message) { | ||
var _a; | ||
const errorLog = { | ||
severity: 'ERROR', | ||
message: message, | ||
filename: (_a = this.config) === null || _a === void 0 ? void 0 : _a.filename | ||
}; | ||
console.log(JSON.stringify(errorLog)); | ||
const errorDetails = new Map(Object.entries({ message })); | ||
this.printLog(errorDetails, Severity.ERROR); | ||
} | ||
postgresError(e) { | ||
var _a; | ||
const errorLog = { | ||
severity: 'ERROR', | ||
message: 'Postgres Error: ' + e.message, | ||
errno: e.errno, | ||
code: e.code, | ||
filename: (_a = this === null || this === void 0 ? void 0 : this.config) === null || _a === void 0 ? void 0 : _a.filename, | ||
characterPositionInQuery: e.position | ||
}; | ||
console.log(JSON.stringify(errorLog)); | ||
const errorDetails = new Map(Object.entries(e)); | ||
errorDetails.set("databaseType", "postgres"); | ||
this.printLog(errorDetails, Severity.ERROR); | ||
} | ||
genericError(e, message) { | ||
const errorDetails = new Map([ | ||
['errorName', e.name] | ||
]); | ||
if (!this.config.omitStackTrace && e.stack) | ||
errorDetails.set('stackTrace', e.stack); | ||
if (message) { | ||
errorDetails.set('message', message); | ||
errorDetails.set('errorMessage', e.message); | ||
} | ||
else | ||
errorDetails.set('message', e.message); | ||
this.printLog(errorDetails, Severity.ERROR); | ||
} | ||
genericErrorCustomMessage(message) { | ||
return (e) => this.genericError(e, message); | ||
} | ||
printLog(details, severity) { | ||
var _a; | ||
const errorLog = { | ||
severity: 'ERROR', | ||
message, | ||
errorMessage: e.message, | ||
errorName: e.name, | ||
stackTrace: e.stack, | ||
filename: (_a = this.config) === null || _a === void 0 ? void 0 : _a.filename | ||
const log = { | ||
severity: severity, | ||
filename: this.config.filename, | ||
logClass: (_a = this.config.logClass) !== null && _a !== void 0 ? _a : this.splitFilePath.slice(-1)[0].split('.')[0], | ||
loggerName: this.config.loggerName, | ||
uniqueId: this.uniqueId | ||
}; | ||
console.log(JSON.stringify(errorLog)); | ||
details.forEach((value, key) => { | ||
log[key] = value; | ||
}); | ||
this.splitFilePath.forEach((filePath, level) => { | ||
log[`FilePathDepth${level + 1}`] = filePath; | ||
}); | ||
const logString = JSON.stringify(log); | ||
switch (severity) { | ||
case Severity.DEBUG: | ||
console.debug(logString); | ||
break; | ||
case Severity.DEFAULT: | ||
console.log(logString); | ||
break; | ||
case Severity.INFO: | ||
case Severity.NOTICE: | ||
console.info(logString); | ||
break; | ||
case Severity.WARNING: | ||
console.warn(logString); | ||
break; | ||
case Severity.ERROR: | ||
case Severity.CRITICAL: | ||
case Severity.ALERT: | ||
case Severity.EMERGENCY: | ||
console.error(logString); | ||
break; | ||
default: | ||
console.log(logString); | ||
} | ||
} | ||
} | ||
exports.default = Timer; |
173
index.ts
@@ -0,6 +1,8 @@ | ||
import * as crypto from 'crypto' | ||
type Config = { | ||
/** | ||
* the severity of the log, changes the way its printed in google cloud logging | ||
* the severity of the log, defaults to DEFAULT | ||
*/ | ||
severity?: 'INFO' | 'ERROR' | 'DEBUG' | 'NOTICE' | ||
severity?: 'DEFAULT' | 'DEBUG' | 'INFO' | 'NOTICE' | 'WARNING' | 'ERROR' | 'CRITICAL' | 'ALERT' | 'EMERGENCY' | ||
/** | ||
@@ -16,3 +18,31 @@ * the label of the log. gets printed in the google cloud summary message | ||
filename: string | ||
/** | ||
* This will be printed on all log output, to distinguish logs output by this library from other logging in | ||
* your application. Its possible but not recommended to override it in the config. | ||
*/ | ||
loggerName?: 'timer-logs logger' | ||
/** | ||
* This will be printed on all log output from the instance configured with it, to help identify where a log has | ||
* come from, or what it relates to. This is mostly useful if you have | ||
* multiple instances of this class in a single file. Otherwise the file acts as an identifier. | ||
*/ | ||
logClass?: string | ||
/** | ||
* Omit the stack trace from error logging. (still prints the provided file path) | ||
*/ | ||
omitStackTrace?: boolean | ||
} | ||
enum Severity { | ||
DEFAULT = "DEFAULT", | ||
DEBUG = "DEBUG", | ||
INFO = "INFO", | ||
NOTICE = "NOTICE", | ||
WARNING = "WARNING", | ||
ERROR = "ERROR", | ||
CRITICAL = "CRITICAL", | ||
ALERT = "ALERT", | ||
EMERGENCY = "EMERGENCY" | ||
} | ||
export default class Timer { | ||
@@ -24,2 +54,5 @@ private readonly startTime: number | ||
private readonly savedTimes: { [label: string]: { startTime: number; finishTime?: number; time?: number } } | ||
private splitFilePath: string[] | ||
private readonly uniqueId: string | ||
/** | ||
@@ -34,6 +67,16 @@ * Create a new Timer object. Can have multiple timers within this object. | ||
this.config.details = config?.details ?? {} | ||
this.splitFilePath = config.filename.split('/').filter(p => p.length > 0) | ||
this.savedTimes = {} | ||
if (this.config?.label !== undefined) this.start(this.config.label) | ||
this._severity = Severity[this.config.severity ?? Severity.DEFAULT] | ||
if (this.config.label === undefined) this.config.label = this.splitFilePath.slice(-1)[0].split('.')[0] | ||
this.uniqueId = crypto.randomBytes(8).toString('hex') | ||
this.start(this.config.label) | ||
} | ||
private _severity: Severity | ||
set severity(value: Severity) { | ||
this._severity = value; | ||
} | ||
/** | ||
@@ -49,3 +92,3 @@ * Start a new timer | ||
this.mostRecentlyStartedLabel = label | ||
this.savedTimes[label] = { startTime: Date.now() } | ||
this.savedTimes[label] = {startTime: Date.now()} | ||
/** | ||
@@ -88,3 +131,3 @@ * Stops the timer and saves the time taken | ||
public next(label: string) { | ||
if(!this.mostRecentlyStartedLabel){ | ||
if (!this.mostRecentlyStartedLabel) { | ||
console.error('Next called before a timer was started') | ||
@@ -103,4 +146,5 @@ return | ||
} | ||
/** | ||
* prints times to the console in JSON format for Google Cloud Logging. | ||
* Prints times to the console in JSON format for Google Cloud Logging. | ||
* | ||
@@ -113,15 +157,14 @@ * Will end the most recently started timer if not already ended | ||
const printObject: { [label: string]: string | number } = { | ||
severity: this.config?.severity ?? 'INFO', | ||
message: (this.config?.label ?? `Timer`) + `: ${this.finishTime - this.startTime}ms`, | ||
filename: this.config?.filename | ||
message: this.config.label + `: ${this.finishTime - this.startTime}ms` | ||
} | ||
const printMap = new Map(Object.entries(printObject)) | ||
Object.entries(this.savedTimes) | ||
.forEach(([label, times]) => { | ||
if(typeof times.time === 'number') printObject[label] = times.time | ||
}) | ||
if (this?.config?.details) | ||
if (typeof times.time === 'number') printMap.set(label, times.time) | ||
}) | ||
if (this.config.details) | ||
Object.entries(this.config.details).forEach(([label, detail]) => { | ||
printObject[label] = detail | ||
printMap.set(label, detail) | ||
}) | ||
console.log(JSON.stringify(printObject)) | ||
this.printLog(printMap, this._severity) | ||
return this.finishTime - this.startTime | ||
@@ -137,3 +180,3 @@ } | ||
public addDetail(key: string, value: string | number | boolean = true) { | ||
Object.assign(this.config?.details, { [key]: value }) | ||
Object.assign(this.config?.details, {[key]: value}) | ||
} | ||
@@ -156,2 +199,3 @@ | ||
} | ||
/** | ||
@@ -162,8 +206,4 @@ * Logs a custom error message in a separate log to the main Timer | ||
public customError(message: string) { | ||
const errorLog = { | ||
severity: 'ERROR', | ||
message: message, | ||
filename: this.config?.filename | ||
} | ||
console.log(JSON.stringify(errorLog)) | ||
const errorDetails = new Map(Object.entries({message})) | ||
this.printLog(errorDetails, Severity.ERROR) | ||
} | ||
@@ -181,11 +221,5 @@ | ||
public postgresError(e: PostgresError): void { | ||
const errorLog = { | ||
severity: 'ERROR', | ||
message: 'Postgres Error: ' + e.message, | ||
errno: e.errno, | ||
code: e.code, | ||
filename: this?.config?.filename, | ||
characterPositionInQuery: e.position | ||
} | ||
console.log(JSON.stringify(errorLog)) | ||
const errorDetails = new Map(Object.entries(e)) | ||
errorDetails.set("databaseType", "postgres") | ||
this.printLog(errorDetails, Severity.ERROR) | ||
} | ||
@@ -211,11 +245,73 @@ | ||
public genericError(e: Error, message?: string) { | ||
const errorLog = { | ||
severity: 'ERROR', | ||
message, | ||
errorMessage: e.message, | ||
errorName: e.name, | ||
stackTrace: e.stack, | ||
filename: this.config?.filename | ||
const errorDetails = new Map([ | ||
['errorName', e.name] | ||
]) | ||
if (!this.config.omitStackTrace && e.stack) errorDetails.set('stackTrace', e.stack) | ||
if (message) { | ||
errorDetails.set('message', message) | ||
errorDetails.set('errorMessage', e.message) | ||
} else errorDetails.set('message', e.message) | ||
this.printLog(errorDetails, Severity.ERROR) | ||
} | ||
/** | ||
* Logs any type of Error in a separate log to the main Timer. | ||
* | ||
* This is a convenience wrapper on `genericError` to allow you to add a custom message, | ||
* and still use in a promise catch clause. | ||
* @param message custom message to log with error. | ||
* | ||
* @example | ||
* await new Promise | ||
*/ | ||
public genericErrorCustomMessage(message: string) { | ||
return (e: Error) => this.genericError(e, message) | ||
} | ||
/** | ||
* Internal printing method which makes sure all of the properties are printed with each log. | ||
* | ||
* @param details object of | ||
* @param severity | ||
* @private | ||
*/ | ||
private printLog(details: Map<string, string | number | boolean | null | undefined>, severity: Severity) { | ||
const log: { [label: string]: string | number | boolean | null | undefined } = { | ||
severity: severity, | ||
filename: this.config.filename, | ||
logClass: this.config.logClass ?? this.splitFilePath.slice(-1)[0].split('.')[0], | ||
loggerName: this.config.loggerName, | ||
uniqueId: this.uniqueId | ||
} | ||
console.log(JSON.stringify(errorLog)) | ||
details.forEach((value, key) => { | ||
log[key] = value | ||
}) | ||
this.splitFilePath.forEach((filePath, level) => { | ||
log[`FilePathDepth${level + 1}`] = filePath | ||
}) | ||
const logString: string = JSON.stringify(log) | ||
// this affects how logs are printed in the browser | ||
switch (severity) { | ||
case Severity.DEBUG: | ||
console.debug(logString) | ||
break; | ||
case Severity.DEFAULT: | ||
console.log(logString) | ||
break; | ||
case Severity.INFO: | ||
case Severity.NOTICE: | ||
console.info(logString) | ||
break; | ||
case Severity.WARNING: | ||
console.warn(logString) | ||
break; | ||
case Severity.ERROR: | ||
case Severity.CRITICAL: | ||
case Severity.ALERT: | ||
case Severity.EMERGENCY: | ||
console.error(logString) | ||
break; | ||
default: | ||
console.log(logString) | ||
} | ||
} | ||
@@ -248,1 +344,2 @@ } | ||
} | ||
{ | ||
"name": "timer-logs", | ||
"version": "1.0.6", | ||
"version": "1.1.0", | ||
"devDependencies": { | ||
@@ -5,0 +5,0 @@ "@types/node": "^15.00.0" |
Sorry, the diff of this file is not supported yet
50629
15
986