Skip to content

Errors send messages #32

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 3 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitattributes
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
*.txt text eol=lf
*.xml text eol=lf
.husky/* text eol=lf
*.yml text eol=lf

# Exclude the `.htaccess` file from GitHub's language statistics
# https://github.com/github/linguist#using-gitattributes
Expand Down
8 changes: 6 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,11 @@ logger.info("some interesting log message");

// global context variables can be modified anywhere in the app
MDC.sessionID = 222;
logger.error("something has gone wrong", new Error("exception message"));
logger.error(new Error("exception message"), "something has gone wrong");
```

This example will result in two log events being sent to `lfs-server`. Both events will have a `requestId` property with a value of `123`. First event will have `sessionID` of `111` and second `sessionID` of `222`. Also since `enableCallStack` is set, both events will include location details such as file name, function name and line number. Second event will have a stack trace of a trown error.
This example will result in two log events being sent to `lfs-server`. Both events will have a `requestId` property with a value of `123`. The first event will have `sessionID` of `111` and second will have `sessionID` of `222`. Also since `enableCallStack` is set, both events will include location details such as file name, function name and line number.

The second event will have a full stack trace of the `Error` object passed in.

Without `enableCallStack`, the `Error` stack would still get logged, but not the file name, function name, and line number as those are parsed earlier.
20 changes: 16 additions & 4 deletions lib/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,24 @@
const util = require('util');
const axios = require('axios');

/**
*
* @param {any[]} logData
* @returns {string}
*/
function format(logData) {
// do not format error with stack, it is reported separetely
const filtered = logData.filter(
(item) => !(item instanceof Error && item.stack)
let foundError = false;
return util.format(
...logData.map((item) => {
if (!foundError && item instanceof Error && item.stack) {
foundError = true;
// send only the base string for the first Error with a stack
// note: all errors on node have `stack` unless it's specifically deleted
return item.toString();
}
return item;
})
);
return util.format(...filtered);
}

function getErrorStack(logData) {
Expand Down
19 changes: 11 additions & 8 deletions test/tap/index-test.js
Original file line number Diff line number Diff line change
Expand Up @@ -127,14 +127,17 @@ test('logFaces appender', (batch) => {
const setup = setupLogging('stack-traces', false, {
url: 'http://localhost/receivers/rx1',
});

setup.logger.error('Oh no', new Error('something went wrong'));
const event = setup.fakeAxios.args[1];
t.equal(event.m, 'Oh no');
t.equal(event.w, true);
t.match(event.i, /Error: something went wrong/);
t.match(event.i, /at (Test.batch.test|Test.<anonymous>)/);

const error = new Error('something went wrong');
setup.logger.error(error, 'Oh no');
let [, event] = setup.fakeAxios.args;
t.equal(event.m, `${error.toString()} Oh no`);
const eventErrorLog = { w: true, i: error.stack };
t.match(event, eventErrorLog);

setup.logger.error('Oh no', error);
[, event] = setup.fakeAxios.args;
t.equal(event.m, `Oh no ${error.toString()}`);
t.match(event, eventErrorLog);
t.end();
});

Expand Down