diff --git a/src/ServiceLogger.js b/src/ServiceLogger.js index 684bfad..9dca24f 100755 --- a/src/ServiceLogger.js +++ b/src/ServiceLogger.js @@ -262,6 +262,10 @@ class ServiceLogger { error(message, additionalFields) { if (this.silence) return; + if (message instanceof Error) { + this._moveMsgObject("error", message.message, Object.assign({}, message, {stack: message.stack}, additionalFields)); + return; + } this._moveMsgObject("error", message, additionalFields); } diff --git a/test/unit/Log.test.js b/test/unit/Log.test.js index e3b3767..912a9a4 100644 --- a/test/unit/Log.test.js +++ b/test/unit/Log.test.js @@ -14,19 +14,19 @@ describe("Log UNIT", function() { }); new Logger({ - "productionMode": true, - "logDir": "logs", - "silence": false, - "loggerName": "dev", - "dockerMode": true, - "varKey": "TLOG", - "logFieldOptions": { - "log_type": "application", - "application_type": "service", - "service": "test-service" + productionMode: true, + logDir: "logs", + silence: false, + loggerName: "dev", + dockerMode: true, + varKey: "TLOG", + logFieldOptions: { + log_type: "application", + application_type: "service", + service: "test-service" }, - "serviceName": "test-service", - "level": "DEBUG" + serviceName: "test-service", + level: "DEBUG" }); const cor_value = "i-am-a-correlation-id"; @@ -40,4 +40,81 @@ describe("Log UNIT", function() { assert.ok(captured.includes(cor_value)); assert.equal(captured.split("\n").length, 4); }); + + describe("Logging of error objects", () => { + const cor_value = "i-am-a-correlation-id"; + const errorMessage = "Error message"; + const additionalText = "this is an additional property"; + const additionalProperty = "additionalPropertyOnError"; + + it("should log error objects", () => { + let captured = ""; + new Logger({ + productionMode: true, + logDir: "logs", + silence: false, + loggerName: "dev", + dockerMode: true, + varKey: "ELOG", + logFieldOptions: { + log_type: "application", + application_type: "service", + service: "test-service" + }, + serviceName: "test-service", + level: "DEBUG" + }); + + const testLogger = ELOG.createChild({"correlation-id": cor_value}); + const error = new Error(errorMessage); + error[additionalProperty] = additionalText; + + const unhook_intercept = intercept(txt => captured += txt); + testLogger.error(error); + + unhook_intercept(); + + assert.ok(captured.includes(`"${additionalProperty}":"${additionalText}"`), "includes the additional property"); + assert.ok(captured.includes(`"stack":"Error: ${errorMessage}\\n`), "Includes the stacktrace"); + assert.ok(captured.includes(`"msg":"${errorMessage}"`), "Includes the error message as log msg property"); + assert.ok(captured.includes(`"correlation-id":"${cor_value}"`), "Includes the error message as log msg property"); + }); + it("should log extended error objects", () => { + let captured = ""; + new Logger({ + productionMode: true, + logDir: "logs", + silence: false, + loggerName: "dev", + dockerMode: true, + varKey: "ELOG", + logFieldOptions: { + log_type: "application", + application_type: "service", + service: "test-service" + }, + serviceName: "test-service", + level: "DEBUG" + }); + + const testLogger = ELOG.createChild({"correlation-id": cor_value}); + class ExtError extends Error { + constructor(message) { + super(message); + this[additionalProperty] = additionalText; + } + } + const error = new ExtError(errorMessage); + + const unhook_intercept = intercept(txt => captured += txt); + testLogger.error(error); + + unhook_intercept(); + + assert.ok(captured.includes(`"${additionalProperty}":"${additionalText}"`), "includes the additional property"); + assert.ok(captured.includes(`"stack":"Error: ${errorMessage}\\n`), "Includes the stacktrace"); + assert.ok(captured.includes(`"msg":"${errorMessage}"`), "Includes the error message as log msg property"); + assert.ok(captured.includes(`"correlation-id":"${cor_value}"`), "Includes the error message as log msg property"); + }); + }); }); \ No newline at end of file