@logtail/pino 0.0.1
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/LICENSE.md +7 -0
- package/README.md +20 -0
- package/dist/cjs/helpers.d.ts +6 -0
- package/dist/cjs/helpers.js +31 -0
- package/dist/cjs/helpers.js.map +1 -0
- package/dist/cjs/index.d.ts +2 -0
- package/dist/cjs/index.js +5 -0
- package/dist/cjs/index.js.map +1 -0
- package/dist/cjs/pino-loki-index.d.ts +3 -0
- package/dist/cjs/pino-loki-index.js +62 -0
- package/dist/cjs/pino-loki-index.js.map +1 -0
- package/dist/cjs/pino.d.ts +11 -0
- package/dist/cjs/pino.js +66 -0
- package/dist/cjs/pino.js.map +1 -0
- package/dist/cjs/pino.test.d.ts +1 -0
- package/dist/cjs/pino.test.js +117 -0
- package/dist/cjs/pino.test.js.map +1 -0
- package/dist/es6/helpers.d.ts +6 -0
- package/dist/es6/helpers.js +27 -0
- package/dist/es6/helpers.js.map +1 -0
- package/dist/es6/index.d.ts +2 -0
- package/dist/es6/index.js +3 -0
- package/dist/es6/index.js.map +1 -0
- package/dist/es6/pino-loki-index.d.ts +3 -0
- package/dist/es6/pino-loki-index.js +56 -0
- package/dist/es6/pino-loki-index.js.map +1 -0
- package/dist/es6/pino.d.ts +11 -0
- package/dist/es6/pino.js +59 -0
- package/dist/es6/pino.js.map +1 -0
- package/dist/es6/pino.test.d.ts +1 -0
- package/dist/es6/pino.test.js +112 -0
- package/dist/es6/pino.test.js.map +1 -0
- package/package.json +43 -0
- package/src/helpers.ts +32 -0
- package/src/index.ts +4 -0
- package/src/pino.ts +65 -0
- package/tsconfig.es6.json +7 -0
- package/tsconfig.json +14 -0
package/LICENSE.md
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
# ISC License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2023, Better Stack, Inc.
|
|
4
|
+
|
|
5
|
+
Permission to use, copy, modify, and/or distribute this software for any purpose with or without fee is hereby granted, provided that the above copyright notice and this permission notice appear in all copies.
|
|
6
|
+
|
|
7
|
+
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
# [Logtail](https://betterstack.com/logtail) JavaScript Pino transport by [Better Stack](https://betterstack.com/)
|
|
2
|
+
|
|
3
|
+
[](https://betterstack.com/logtail)
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
[](LICENSE.md)
|
|
7
|
+
[](https://www.npmjs.com/package/@logtail/pino)
|
|
8
|
+
|
|
9
|
+
Experience SQL-compatible structured log management based on ClickHouse. [Learn more ↗](https://logtail.com/)
|
|
10
|
+
|
|
11
|
+
## Documentation
|
|
12
|
+
|
|
13
|
+
[Getting started ↗](https://betterstack.com/docs/logs/javascript)
|
|
14
|
+
|
|
15
|
+
## Need help?
|
|
16
|
+
Please let us know at [hello@beterstack.com](mailto:hello@beterstack.com). We're happy to help!
|
|
17
|
+
|
|
18
|
+
---
|
|
19
|
+
|
|
20
|
+
[ISC license](LICENSE.md), [contributing guidelines](../../CONTRIBUTING.md).
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.getLogLevel = void 0;
|
|
4
|
+
const types_1 = require("@logtail/types");
|
|
5
|
+
/**
|
|
6
|
+
* Return a Logtail `LogLevel` based on the Pino level
|
|
7
|
+
* @param level number - Pino log level
|
|
8
|
+
*/
|
|
9
|
+
function getLogLevel(level) {
|
|
10
|
+
// TODO: Trace 10
|
|
11
|
+
if (level <= 10) {
|
|
12
|
+
return types_1.LogLevel.Debug;
|
|
13
|
+
}
|
|
14
|
+
// Debug
|
|
15
|
+
if (level <= 20) {
|
|
16
|
+
return types_1.LogLevel.Debug;
|
|
17
|
+
}
|
|
18
|
+
// Info
|
|
19
|
+
if (level <= 30) {
|
|
20
|
+
return types_1.LogLevel.Info;
|
|
21
|
+
}
|
|
22
|
+
// Warn
|
|
23
|
+
if (level <= 40) {
|
|
24
|
+
return types_1.LogLevel.Warn;
|
|
25
|
+
}
|
|
26
|
+
// Everything above this level is considered an error
|
|
27
|
+
// TODO: Fatal 60 (Error 50)
|
|
28
|
+
return types_1.LogLevel.Error;
|
|
29
|
+
}
|
|
30
|
+
exports.getLogLevel = getLogLevel;
|
|
31
|
+
//# sourceMappingURL=helpers.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"helpers.js","sourceRoot":"","sources":["../../src/helpers.ts"],"names":[],"mappings":";;;AAAA,0CAA0C;AAE1C;;;GAGG;AACH,SAAgB,WAAW,CAAC,KAAa;IAEvC,iBAAiB;IACjB,IAAI,KAAK,IAAI,EAAE,EAAE;QACf,OAAO,gBAAQ,CAAC,KAAK,CAAC;KACvB;IAED,QAAQ;IACR,IAAI,KAAK,IAAI,EAAE,EAAE;QACf,OAAO,gBAAQ,CAAC,KAAK,CAAC;KACvB;IAED,OAAO;IACP,IAAI,KAAK,IAAI,EAAE,EAAE;QACf,OAAO,gBAAQ,CAAC,IAAI,CAAC;KACtB;IAED,OAAO;IACP,IAAI,KAAK,IAAI,EAAE,EAAE;QACf,OAAO,gBAAQ,CAAC,IAAI,CAAC;KACtB;IAED,qDAAqD;IACrD,4BAA4B;IAC5B,OAAO,gBAAQ,CAAC,KAAK,CAAC;AACxB,CAAC;AAzBD,kCAyBC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":";;AAAA,iCAA0C;AAE1C,kBAAe,uBAAgB,CAAA"}
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __asyncValues = (this && this.__asyncValues) || function (o) {
|
|
3
|
+
if (!Symbol.asyncIterator) throw new TypeError("Symbol.asyncIterator is not defined.");
|
|
4
|
+
var m = o[Symbol.asyncIterator], i;
|
|
5
|
+
return m ? m.call(o) : (o = typeof __values === "function" ? __values(o) : o[Symbol.iterator](), i = {}, verb("next"), verb("throw"), verb("return"), i[Symbol.asyncIterator] = function () { return this; }, i);
|
|
6
|
+
function verb(n) { i[n] = o[n] && function (v) { return new Promise(function (resolve, reject) { v = o[n](v), settle(resolve, reject, v.done, v.value); }); }; }
|
|
7
|
+
function settle(resolve, reject, d, v) { Promise.resolve(v).then(function(v) { resolve({ value: v, done: d }); }, reject); }
|
|
8
|
+
};
|
|
9
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
10
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
11
|
+
};
|
|
12
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
13
|
+
const pino_abstract_transport_1 = __importDefault(require("pino-abstract-transport"));
|
|
14
|
+
const LogPusher_1 = require("./LogPusher");
|
|
15
|
+
async function default_1(options) {
|
|
16
|
+
var _a, _b, _c, _d, _e, _f;
|
|
17
|
+
(_a = options.timeout) !== null && _a !== void 0 ? _a : ;
|
|
18
|
+
30000;
|
|
19
|
+
(_b = options.silenceErrors) !== null && _b !== void 0 ? _b : ;
|
|
20
|
+
false;
|
|
21
|
+
(_c = options.batching) !== null && _c !== void 0 ? _c : ;
|
|
22
|
+
true;
|
|
23
|
+
(_d = options.interval) !== null && _d !== void 0 ? _d : ;
|
|
24
|
+
5;
|
|
25
|
+
(_e = options.replaceTimestamp) !== null && _e !== void 0 ? _e : ;
|
|
26
|
+
false;
|
|
27
|
+
(_f = options.propsToLabels) !== null && _f !== void 0 ? _f : ;
|
|
28
|
+
[];
|
|
29
|
+
const logPusher = new LogPusher_1.LogPusher(options);
|
|
30
|
+
return pino_abstract_transport_1.default(async (source) => {
|
|
31
|
+
var e_1, _a;
|
|
32
|
+
let pinoLogBuffer = [];
|
|
33
|
+
if (options.batching) {
|
|
34
|
+
setInterval(async () => {
|
|
35
|
+
if (pinoLogBuffer.length === 0) {
|
|
36
|
+
return;
|
|
37
|
+
}
|
|
38
|
+
logPusher.push(pinoLogBuffer);
|
|
39
|
+
pinoLogBuffer = [];
|
|
40
|
+
}, options.interval * 1000);
|
|
41
|
+
}
|
|
42
|
+
try {
|
|
43
|
+
for (var source_1 = __asyncValues(source), source_1_1; source_1_1 = await source_1.next(), !source_1_1.done;) {
|
|
44
|
+
let obj = source_1_1.value;
|
|
45
|
+
if (options.batching) {
|
|
46
|
+
pinoLogBuffer.push(obj);
|
|
47
|
+
continue;
|
|
48
|
+
}
|
|
49
|
+
logPusher.push(obj);
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
catch (e_1_1) { e_1 = { error: e_1_1 }; }
|
|
53
|
+
finally {
|
|
54
|
+
try {
|
|
55
|
+
if (source_1_1 && !source_1_1.done && (_a = source_1.return)) await _a.call(source_1);
|
|
56
|
+
}
|
|
57
|
+
finally { if (e_1) throw e_1.error; }
|
|
58
|
+
}
|
|
59
|
+
});
|
|
60
|
+
}
|
|
61
|
+
exports.default = default_1;
|
|
62
|
+
//# sourceMappingURL=pino-loki-index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pino-loki-index.js","sourceRoot":"","sources":["../../src/pino-loki-index.ts"],"names":[],"mappings":";;;;;;;;;;;;AAAA,sFAA2C;AAE3C,2CAAuC;AAExB,KAAK,oBAAW,OAAgC;;IAC7D,MAAA,OAAO,CAAC,OAAO,mCAAG,CAAA;IAAE,KAAK,CAAA;IACzB,MAAA,OAAO,CAAC,aAAa,mCAAG,CAAA;IAAE,KAAK,CAAA;IAC/B,MAAA,OAAO,CAAC,QAAQ,mCAAG,CAAA;IAAE,IAAI,CAAA;IACzB,MAAA,OAAO,CAAC,QAAQ,mCAAG,CAAA;IAAE,CAAC,CAAA;IACtB,MAAA,OAAO,CAAC,gBAAgB,mCAAG,CAAA;IAAE,KAAK,CAAA;IAClC,MAAA,OAAO,CAAC,aAAa,mCAAG,CAAA;IAAE,EAAE,CAAA;IAC5B,MAAM,SAAS,GAAG,IAAI,qBAAS,CAAC,OAAO,CAAC,CAAA;IAExC,OAAO,iCAAK,CAAC,KAAK,EAAE,MAAW,EAAE,EAAE;;QACjC,IAAI,aAAa,GAAc,EAAE,CAAA;QAEjC,IAAI,OAAO,CAAC,QAAQ,EAAE;YACpB,WAAW,CAAC,KAAK,IAAI,EAAE;gBACrB,IAAI,aAAa,CAAC,MAAM,KAAK,CAAC,EAAE;oBAC9B,OAAM;iBACP;gBAED,SAAS,CAAC,IAAI,CAAC,aAAa,CAAC,CAAA;gBAC7B,aAAa,GAAG,EAAE,CAAA;YACpB,CAAC,EAAE,OAAO,CAAC,QAAS,GAAG,IAAI,CAAC,CAAA;SAC7B;;YAED,KAAsB,IAAA,WAAA,cAAA,MAAM,CAAA,YAAA;gBAAjB,IAAI,GAAG,mBAAA,CAAA;gBAChB,IAAI,OAAO,CAAC,QAAQ,EAAE;oBACpB,aAAa,CAAC,IAAI,CAAC,GAAG,CAAC,CAAA;oBACvB,SAAQ;iBACT;gBAED,SAAS,CAAC,IAAI,CAAC,GAAG,CAAC,CAAA;aACpB;;;;;;;;;IACH,CAAC,CAAC,CAAA;AACJ,CAAC;AAhCD,4BAgCC"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
/// <reference types="node" />
|
|
2
|
+
import { ILogtailOptions } from "@logtail/types";
|
|
3
|
+
export interface PinoLog {
|
|
4
|
+
level: number;
|
|
5
|
+
[key: string]: any;
|
|
6
|
+
}
|
|
7
|
+
export interface IPinoLogtailOptions {
|
|
8
|
+
sourceToken: string;
|
|
9
|
+
options: Partial<ILogtailOptions>;
|
|
10
|
+
}
|
|
11
|
+
export declare function logtailTransport(options: IPinoLogtailOptions): Promise<import("stream").Transform & import("pino-abstract-transport").OnUnknown>;
|
package/dist/cjs/pino.js
ADDED
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __asyncValues = (this && this.__asyncValues) || function (o) {
|
|
3
|
+
if (!Symbol.asyncIterator) throw new TypeError("Symbol.asyncIterator is not defined.");
|
|
4
|
+
var m = o[Symbol.asyncIterator], i;
|
|
5
|
+
return m ? m.call(o) : (o = typeof __values === "function" ? __values(o) : o[Symbol.iterator](), i = {}, verb("next"), verb("throw"), verb("return"), i[Symbol.asyncIterator] = function () { return this; }, i);
|
|
6
|
+
function verb(n) { i[n] = o[n] && function (v) { return new Promise(function (resolve, reject) { v = o[n](v), settle(resolve, reject, v.done, v.value); }); }; }
|
|
7
|
+
function settle(resolve, reject, d, v) { Promise.resolve(v).then(function(v) { resolve({ value: v, done: d }); }, reject); }
|
|
8
|
+
};
|
|
9
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
10
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
11
|
+
};
|
|
12
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
13
|
+
exports.logtailTransport = void 0;
|
|
14
|
+
const pino_abstract_transport_1 = __importDefault(require("pino-abstract-transport"));
|
|
15
|
+
const node_1 = require("@logtail/node");
|
|
16
|
+
const helpers_1 = require("./helpers");
|
|
17
|
+
async function logtailTransport(options) {
|
|
18
|
+
// FIXME: error handling for no source token
|
|
19
|
+
const logtail = new node_1.Logtail(options.sourceToken);
|
|
20
|
+
return pino_abstract_transport_1.default(async (source) => {
|
|
21
|
+
var e_1, _a;
|
|
22
|
+
try {
|
|
23
|
+
for (var source_1 = __asyncValues(source), source_1_1; source_1_1 = await source_1.next(), !source_1_1.done;) {
|
|
24
|
+
let obj = source_1_1.value;
|
|
25
|
+
// Log should have string `msg` key, > 0 length
|
|
26
|
+
if (typeof obj.msg !== "string" || !obj.msg.length) {
|
|
27
|
+
console.error('Field "msg" has to be a non-empty string.');
|
|
28
|
+
continue;
|
|
29
|
+
}
|
|
30
|
+
// Logging meta data
|
|
31
|
+
const meta = {};
|
|
32
|
+
// Copy `time` if set
|
|
33
|
+
if (typeof obj.time === "string" || obj.time.length) {
|
|
34
|
+
const time = new Date(obj.time);
|
|
35
|
+
if (!isNaN(time.valueOf())) {
|
|
36
|
+
meta.dt = time;
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
// Carry over any additional data fields
|
|
40
|
+
Object.keys(obj)
|
|
41
|
+
.filter(key => ["time", "msg", "level", "v"].indexOf(key) < 0)
|
|
42
|
+
.forEach(key => (meta[key] = obj[key]));
|
|
43
|
+
// Determine the log level
|
|
44
|
+
let level;
|
|
45
|
+
try {
|
|
46
|
+
level = helpers_1.getLogLevel(obj.level);
|
|
47
|
+
}
|
|
48
|
+
catch (_) {
|
|
49
|
+
console.error('Error while mapping log level.');
|
|
50
|
+
continue;
|
|
51
|
+
}
|
|
52
|
+
// Log to Logtail
|
|
53
|
+
logtail.log(obj.msg, level, meta);
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
catch (e_1_1) { e_1 = { error: e_1_1 }; }
|
|
57
|
+
finally {
|
|
58
|
+
try {
|
|
59
|
+
if (source_1_1 && !source_1_1.done && (_a = source_1.return)) await _a.call(source_1);
|
|
60
|
+
}
|
|
61
|
+
finally { if (e_1) throw e_1.error; }
|
|
62
|
+
}
|
|
63
|
+
});
|
|
64
|
+
}
|
|
65
|
+
exports.logtailTransport = logtailTransport;
|
|
66
|
+
//# sourceMappingURL=pino.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pino.js","sourceRoot":"","sources":["../../src/pino.ts"],"names":[],"mappings":";;;;;;;;;;;;;AAAA,sFAA2C;AAE3C,wCAAwC;AAGxC,uCAAwC;AAiBjC,KAAK,UAAU,gBAAgB,CAAC,OAA4B;IACjE,6CAA6C;IAC7C,MAAM,OAAO,GAAG,IAAI,cAAO,CAAC,OAAO,CAAC,WAAW,CAAC,CAAA;IAEhD,OAAO,iCAAK,CAAC,KAAK,EAAE,MAAW,EAAE,EAAE;;;YACjC,KAAsB,IAAA,WAAA,cAAA,MAAM,CAAA,YAAA;gBAAjB,IAAI,GAAG,mBAAA,CAAA;gBAChB,+CAA+C;gBAC/C,IAAI,OAAO,GAAG,CAAC,GAAG,KAAK,QAAQ,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,MAAM,EAAE;oBAClD,OAAO,CAAC,KAAK,CAAC,2CAA2C,CAAC,CAAA;oBAC1D,SAAQ;iBACT;gBAED,oBAAoB;gBACpB,MAAM,IAAI,GAAY,EAAE,CAAC;gBAEzB,qBAAqB;gBACrB,IAAI,OAAO,GAAG,CAAC,IAAI,KAAK,QAAQ,IAAI,GAAG,CAAC,IAAI,CAAC,MAAM,EAAE;oBACnD,MAAM,IAAI,GAAG,IAAI,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;oBAChC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC,EAAE;wBAC1B,IAAI,CAAC,EAAE,GAAG,IAAI,CAAC;qBAChB;iBACF;gBAED,wCAAwC;gBACxC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC;qBACb,MAAM,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,MAAM,EAAE,KAAK,EAAE,OAAO,EAAE,GAAG,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC;qBAC7D,OAAO,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,GAAG,GAAG,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC;gBAE1C,0BAA0B;gBAC1B,IAAI,KAAe,CAAC;gBAEpB,IAAI;oBACF,KAAK,GAAG,qBAAW,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC;iBAChC;gBAAC,OAAO,CAAC,EAAE;oBACV,OAAO,CAAC,KAAK,CAAC,gCAAgC,CAAC,CAAA;oBAC/C,SAAQ;iBACT;gBAED,iBAAiB;gBACjB,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,EAAE,KAAK,EAAE,IAAI,CAAC,CAAC;aACnC;;;;;;;;;IACH,CAAC,CAAC,CAAA;AACJ,CAAC;AA1CD,4CA0CC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
const pino_1 = __importDefault(require("pino"));
|
|
7
|
+
const node_1 = require("@logtail/node");
|
|
8
|
+
const types_1 = require("@logtail/types");
|
|
9
|
+
// Numeric log level test type
|
|
10
|
+
// type LevelTest = [number, LogLevel, LogLevelString];
|
|
11
|
+
// Sample log message
|
|
12
|
+
const message = "Something to do with something";
|
|
13
|
+
/**
|
|
14
|
+
* Create a Pino logger instance with Logtail transport
|
|
15
|
+
*
|
|
16
|
+
*/
|
|
17
|
+
function createLogger() {
|
|
18
|
+
const token = "invalid source token";
|
|
19
|
+
const logtailOptions = { ignoreExceptions: true };
|
|
20
|
+
const options = { sourceToken: token, options: logtailOptions };
|
|
21
|
+
const transport = pino_1.default.transport({
|
|
22
|
+
target: "./pino.js",
|
|
23
|
+
options: options
|
|
24
|
+
});
|
|
25
|
+
return pino_1.default(transport);
|
|
26
|
+
}
|
|
27
|
+
/**
|
|
28
|
+
* Test a Bunyan log level vs. a Logtail `LogLevel`
|
|
29
|
+
*
|
|
30
|
+
* @param level LogLevelString - Bunyan log level (string)
|
|
31
|
+
* @param logLevel LogLevel - Logtail log level
|
|
32
|
+
* @param cb Function - Callback to execute to signal test completion
|
|
33
|
+
*/
|
|
34
|
+
async function testLevel(level, logLevel, cb) {
|
|
35
|
+
// Logtail fixtures
|
|
36
|
+
const logtail = new node_1.Logtail("test", { batchInterval: 1 });
|
|
37
|
+
logtail.setSync(async (logs) => {
|
|
38
|
+
// Should be exactly one log
|
|
39
|
+
expect(logs.length).toBe(1);
|
|
40
|
+
// Message should match
|
|
41
|
+
expect(logs[0].message).toBe(message);
|
|
42
|
+
// Log level should be 'info'
|
|
43
|
+
expect(logs[0].level).toBe(logLevel);
|
|
44
|
+
// Signal that the test has finished
|
|
45
|
+
setImmediate(() => cb());
|
|
46
|
+
return logs;
|
|
47
|
+
});
|
|
48
|
+
// Create Bunyan logger
|
|
49
|
+
const logger = createLogger(logtail);
|
|
50
|
+
// Log out to Bunyan
|
|
51
|
+
logger[level](message);
|
|
52
|
+
}
|
|
53
|
+
describe("Bunyan tests", () => {
|
|
54
|
+
it("should log at the 'debug' level", async (done) => {
|
|
55
|
+
return testLevel("debug", types_1.LogLevel.Debug, done);
|
|
56
|
+
});
|
|
57
|
+
it("should log at the 'info' level", async (done) => {
|
|
58
|
+
return testLevel("info", types_1.LogLevel.Info, done);
|
|
59
|
+
});
|
|
60
|
+
it("should log at the 'warn' level", async (done) => {
|
|
61
|
+
return testLevel("warn", types_1.LogLevel.Warn, done);
|
|
62
|
+
});
|
|
63
|
+
it("should log at the 'error' level", async (done) => {
|
|
64
|
+
return testLevel("error", types_1.LogLevel.Error, done);
|
|
65
|
+
});
|
|
66
|
+
it("should log at the 'fatal' level", async (done) => {
|
|
67
|
+
return testLevel("fatal", types_1.LogLevel.Error, done);
|
|
68
|
+
});
|
|
69
|
+
it("should log using number levels", async (done) => {
|
|
70
|
+
// Fixtures
|
|
71
|
+
const levels = [
|
|
72
|
+
[25, types_1.LogLevel.Debug, "debug"],
|
|
73
|
+
[35, types_1.LogLevel.Info, "info"],
|
|
74
|
+
[45, types_1.LogLevel.Warn, "warn"],
|
|
75
|
+
[55, types_1.LogLevel.Error, "error"]
|
|
76
|
+
];
|
|
77
|
+
const logtail = new node_1.Logtail("test", {
|
|
78
|
+
batchInterval: 1000,
|
|
79
|
+
batchSize: levels.length
|
|
80
|
+
});
|
|
81
|
+
logtail.setSync(async (logs) => {
|
|
82
|
+
expect(logs.length).toBe(levels.length);
|
|
83
|
+
done();
|
|
84
|
+
return logs;
|
|
85
|
+
});
|
|
86
|
+
// Create Bunyan logger
|
|
87
|
+
const logger = createLogger(logtail);
|
|
88
|
+
// Cycle through levels, and log
|
|
89
|
+
levels.forEach(level => logger[level[2]](message));
|
|
90
|
+
});
|
|
91
|
+
it("should include arbitrary extra data fields", async (done) => {
|
|
92
|
+
const logtail = new node_1.Logtail("test");
|
|
93
|
+
logtail.setSync(async (logs) => {
|
|
94
|
+
expect(logs).toHaveLength(1);
|
|
95
|
+
expect(logs[0].message).toEqual("i am the message");
|
|
96
|
+
expect(logs[0].foo).toEqual("bar");
|
|
97
|
+
expect(logs[0].some).toEqual({ nested: "stuff" });
|
|
98
|
+
done();
|
|
99
|
+
return logs;
|
|
100
|
+
});
|
|
101
|
+
const logger = createLogger(logtail);
|
|
102
|
+
logger.info({ foo: "bar", some: { nested: "stuff" } }, "i am the message");
|
|
103
|
+
});
|
|
104
|
+
it("should include correct context fields", async (done) => {
|
|
105
|
+
const logtail = new node_1.Logtail("test");
|
|
106
|
+
logtail.setSync(async (logs) => {
|
|
107
|
+
const context = logs[0].context;
|
|
108
|
+
const runtime = context.runtime;
|
|
109
|
+
expect(runtime.file).toEqual("bunyan.test.ts");
|
|
110
|
+
done();
|
|
111
|
+
return logs;
|
|
112
|
+
});
|
|
113
|
+
const logger = createLogger(logtail);
|
|
114
|
+
logger.info("message with context");
|
|
115
|
+
});
|
|
116
|
+
});
|
|
117
|
+
//# sourceMappingURL=pino.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pino.test.js","sourceRoot":"","sources":["../../src/pino.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import { LogLevel } from "@logtail/types";
|
|
2
|
+
/**
|
|
3
|
+
* Return a Logtail `LogLevel` based on the Pino level
|
|
4
|
+
* @param level number - Pino log level
|
|
5
|
+
*/
|
|
6
|
+
export function getLogLevel(level) {
|
|
7
|
+
// TODO: Trace 10
|
|
8
|
+
if (level <= 10) {
|
|
9
|
+
return LogLevel.Debug;
|
|
10
|
+
}
|
|
11
|
+
// Debug
|
|
12
|
+
if (level <= 20) {
|
|
13
|
+
return LogLevel.Debug;
|
|
14
|
+
}
|
|
15
|
+
// Info
|
|
16
|
+
if (level <= 30) {
|
|
17
|
+
return LogLevel.Info;
|
|
18
|
+
}
|
|
19
|
+
// Warn
|
|
20
|
+
if (level <= 40) {
|
|
21
|
+
return LogLevel.Warn;
|
|
22
|
+
}
|
|
23
|
+
// Everything above this level is considered an error
|
|
24
|
+
// TODO: Fatal 60 (Error 50)
|
|
25
|
+
return LogLevel.Error;
|
|
26
|
+
}
|
|
27
|
+
//# sourceMappingURL=helpers.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"helpers.js","sourceRoot":"","sources":["../../src/helpers.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,gBAAgB,CAAC;AAE1C;;;GAGG;AACH,MAAM,UAAU,WAAW,CAAC,KAAa;IAEvC,iBAAiB;IACjB,IAAI,KAAK,IAAI,EAAE,EAAE;QACf,OAAO,QAAQ,CAAC,KAAK,CAAC;KACvB;IAED,QAAQ;IACR,IAAI,KAAK,IAAI,EAAE,EAAE;QACf,OAAO,QAAQ,CAAC,KAAK,CAAC;KACvB;IAED,OAAO;IACP,IAAI,KAAK,IAAI,EAAE,EAAE;QACf,OAAO,QAAQ,CAAC,IAAI,CAAC;KACtB;IAED,OAAO;IACP,IAAI,KAAK,IAAI,EAAE,EAAE;QACf,OAAO,QAAQ,CAAC,IAAI,CAAC;KACtB;IAED,qDAAqD;IACrD,4BAA4B;IAC5B,OAAO,QAAQ,CAAC,KAAK,CAAC;AACxB,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,gBAAgB,EAAE,MAAM,QAAQ,CAAC;AAE1C,eAAe,gBAAgB,CAAA"}
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
var __asyncValues = (this && this.__asyncValues) || function (o) {
|
|
2
|
+
if (!Symbol.asyncIterator) throw new TypeError("Symbol.asyncIterator is not defined.");
|
|
3
|
+
var m = o[Symbol.asyncIterator], i;
|
|
4
|
+
return m ? m.call(o) : (o = typeof __values === "function" ? __values(o) : o[Symbol.iterator](), i = {}, verb("next"), verb("throw"), verb("return"), i[Symbol.asyncIterator] = function () { return this; }, i);
|
|
5
|
+
function verb(n) { i[n] = o[n] && function (v) { return new Promise(function (resolve, reject) { v = o[n](v), settle(resolve, reject, v.done, v.value); }); }; }
|
|
6
|
+
function settle(resolve, reject, d, v) { Promise.resolve(v).then(function(v) { resolve({ value: v, done: d }); }, reject); }
|
|
7
|
+
};
|
|
8
|
+
import build from 'pino-abstract-transport';
|
|
9
|
+
import { LogPusher } from './LogPusher';
|
|
10
|
+
export default async function (options) {
|
|
11
|
+
var _a, _b, _c, _d, _e, _f;
|
|
12
|
+
(_a = options.timeout) !== null && _a !== void 0 ? _a : ;
|
|
13
|
+
30000;
|
|
14
|
+
(_b = options.silenceErrors) !== null && _b !== void 0 ? _b : ;
|
|
15
|
+
false;
|
|
16
|
+
(_c = options.batching) !== null && _c !== void 0 ? _c : ;
|
|
17
|
+
true;
|
|
18
|
+
(_d = options.interval) !== null && _d !== void 0 ? _d : ;
|
|
19
|
+
5;
|
|
20
|
+
(_e = options.replaceTimestamp) !== null && _e !== void 0 ? _e : ;
|
|
21
|
+
false;
|
|
22
|
+
(_f = options.propsToLabels) !== null && _f !== void 0 ? _f : ;
|
|
23
|
+
[];
|
|
24
|
+
const logPusher = new LogPusher(options);
|
|
25
|
+
return build(async (source) => {
|
|
26
|
+
var e_1, _a;
|
|
27
|
+
let pinoLogBuffer = [];
|
|
28
|
+
if (options.batching) {
|
|
29
|
+
setInterval(async () => {
|
|
30
|
+
if (pinoLogBuffer.length === 0) {
|
|
31
|
+
return;
|
|
32
|
+
}
|
|
33
|
+
logPusher.push(pinoLogBuffer);
|
|
34
|
+
pinoLogBuffer = [];
|
|
35
|
+
}, options.interval * 1000);
|
|
36
|
+
}
|
|
37
|
+
try {
|
|
38
|
+
for (var source_1 = __asyncValues(source), source_1_1; source_1_1 = await source_1.next(), !source_1_1.done;) {
|
|
39
|
+
let obj = source_1_1.value;
|
|
40
|
+
if (options.batching) {
|
|
41
|
+
pinoLogBuffer.push(obj);
|
|
42
|
+
continue;
|
|
43
|
+
}
|
|
44
|
+
logPusher.push(obj);
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
catch (e_1_1) { e_1 = { error: e_1_1 }; }
|
|
48
|
+
finally {
|
|
49
|
+
try {
|
|
50
|
+
if (source_1_1 && !source_1_1.done && (_a = source_1.return)) await _a.call(source_1);
|
|
51
|
+
}
|
|
52
|
+
finally { if (e_1) throw e_1.error; }
|
|
53
|
+
}
|
|
54
|
+
});
|
|
55
|
+
}
|
|
56
|
+
//# sourceMappingURL=pino-loki-index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pino-loki-index.js","sourceRoot":"","sources":["../../src/pino-loki-index.ts"],"names":[],"mappings":";;;;;;;AAAA,OAAO,KAAK,MAAM,yBAAyB,CAAA;AAE3C,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAA;AAEvC,MAAM,CAAC,OAAO,CAAC,KAAK,WAAW,OAAgC;;IAC7D,MAAA,OAAO,CAAC,OAAO,mCAAG,CAAA;IAAE,KAAK,CAAA;IACzB,MAAA,OAAO,CAAC,aAAa,mCAAG,CAAA;IAAE,KAAK,CAAA;IAC/B,MAAA,OAAO,CAAC,QAAQ,mCAAG,CAAA;IAAE,IAAI,CAAA;IACzB,MAAA,OAAO,CAAC,QAAQ,mCAAG,CAAA;IAAE,CAAC,CAAA;IACtB,MAAA,OAAO,CAAC,gBAAgB,mCAAG,CAAA;IAAE,KAAK,CAAA;IAClC,MAAA,OAAO,CAAC,aAAa,mCAAG,CAAA;IAAE,EAAE,CAAA;IAC5B,MAAM,SAAS,GAAG,IAAI,SAAS,CAAC,OAAO,CAAC,CAAA;IAExC,OAAO,KAAK,CAAC,KAAK,EAAE,MAAW,EAAE,EAAE;;QACjC,IAAI,aAAa,GAAc,EAAE,CAAA;QAEjC,IAAI,OAAO,CAAC,QAAQ,EAAE;YACpB,WAAW,CAAC,KAAK,IAAI,EAAE;gBACrB,IAAI,aAAa,CAAC,MAAM,KAAK,CAAC,EAAE;oBAC9B,OAAM;iBACP;gBAED,SAAS,CAAC,IAAI,CAAC,aAAa,CAAC,CAAA;gBAC7B,aAAa,GAAG,EAAE,CAAA;YACpB,CAAC,EAAE,OAAO,CAAC,QAAS,GAAG,IAAI,CAAC,CAAA;SAC7B;;YAED,KAAsB,IAAA,WAAA,cAAA,MAAM,CAAA,YAAA;gBAAjB,IAAI,GAAG,mBAAA,CAAA;gBAChB,IAAI,OAAO,CAAC,QAAQ,EAAE;oBACpB,aAAa,CAAC,IAAI,CAAC,GAAG,CAAC,CAAA;oBACvB,SAAQ;iBACT;gBAED,SAAS,CAAC,IAAI,CAAC,GAAG,CAAC,CAAA;aACpB;;;;;;;;;IACH,CAAC,CAAC,CAAA;AACJ,CAAC"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
/// <reference types="node" />
|
|
2
|
+
import { ILogtailOptions } from "@logtail/types";
|
|
3
|
+
export interface PinoLog {
|
|
4
|
+
level: number;
|
|
5
|
+
[key: string]: any;
|
|
6
|
+
}
|
|
7
|
+
export interface IPinoLogtailOptions {
|
|
8
|
+
sourceToken: string;
|
|
9
|
+
options: Partial<ILogtailOptions>;
|
|
10
|
+
}
|
|
11
|
+
export declare function logtailTransport(options: IPinoLogtailOptions): Promise<import("stream").Transform & import("pino-abstract-transport").OnUnknown>;
|
package/dist/es6/pino.js
ADDED
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
var __asyncValues = (this && this.__asyncValues) || function (o) {
|
|
2
|
+
if (!Symbol.asyncIterator) throw new TypeError("Symbol.asyncIterator is not defined.");
|
|
3
|
+
var m = o[Symbol.asyncIterator], i;
|
|
4
|
+
return m ? m.call(o) : (o = typeof __values === "function" ? __values(o) : o[Symbol.iterator](), i = {}, verb("next"), verb("throw"), verb("return"), i[Symbol.asyncIterator] = function () { return this; }, i);
|
|
5
|
+
function verb(n) { i[n] = o[n] && function (v) { return new Promise(function (resolve, reject) { v = o[n](v), settle(resolve, reject, v.done, v.value); }); }; }
|
|
6
|
+
function settle(resolve, reject, d, v) { Promise.resolve(v).then(function(v) { resolve({ value: v, done: d }); }, reject); }
|
|
7
|
+
};
|
|
8
|
+
import build from 'pino-abstract-transport';
|
|
9
|
+
import { Logtail } from "@logtail/node";
|
|
10
|
+
import { getLogLevel } from "./helpers";
|
|
11
|
+
export async function logtailTransport(options) {
|
|
12
|
+
// FIXME: error handling for no source token
|
|
13
|
+
const logtail = new Logtail(options.sourceToken);
|
|
14
|
+
return build(async (source) => {
|
|
15
|
+
var e_1, _a;
|
|
16
|
+
try {
|
|
17
|
+
for (var source_1 = __asyncValues(source), source_1_1; source_1_1 = await source_1.next(), !source_1_1.done;) {
|
|
18
|
+
let obj = source_1_1.value;
|
|
19
|
+
// Log should have string `msg` key, > 0 length
|
|
20
|
+
if (typeof obj.msg !== "string" || !obj.msg.length) {
|
|
21
|
+
console.error('Field "msg" has to be a non-empty string.');
|
|
22
|
+
continue;
|
|
23
|
+
}
|
|
24
|
+
// Logging meta data
|
|
25
|
+
const meta = {};
|
|
26
|
+
// Copy `time` if set
|
|
27
|
+
if (typeof obj.time === "string" || obj.time.length) {
|
|
28
|
+
const time = new Date(obj.time);
|
|
29
|
+
if (!isNaN(time.valueOf())) {
|
|
30
|
+
meta.dt = time;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
// Carry over any additional data fields
|
|
34
|
+
Object.keys(obj)
|
|
35
|
+
.filter(key => ["time", "msg", "level", "v"].indexOf(key) < 0)
|
|
36
|
+
.forEach(key => (meta[key] = obj[key]));
|
|
37
|
+
// Determine the log level
|
|
38
|
+
let level;
|
|
39
|
+
try {
|
|
40
|
+
level = getLogLevel(obj.level);
|
|
41
|
+
}
|
|
42
|
+
catch (_) {
|
|
43
|
+
console.error('Error while mapping log level.');
|
|
44
|
+
continue;
|
|
45
|
+
}
|
|
46
|
+
// Log to Logtail
|
|
47
|
+
logtail.log(obj.msg, level, meta);
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
catch (e_1_1) { e_1 = { error: e_1_1 }; }
|
|
51
|
+
finally {
|
|
52
|
+
try {
|
|
53
|
+
if (source_1_1 && !source_1_1.done && (_a = source_1.return)) await _a.call(source_1);
|
|
54
|
+
}
|
|
55
|
+
finally { if (e_1) throw e_1.error; }
|
|
56
|
+
}
|
|
57
|
+
});
|
|
58
|
+
}
|
|
59
|
+
//# sourceMappingURL=pino.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pino.js","sourceRoot":"","sources":["../../src/pino.ts"],"names":[],"mappings":";;;;;;;AAAA,OAAO,KAAK,MAAM,yBAAyB,CAAA;AAE3C,OAAO,EAAE,OAAO,EAAE,MAAM,eAAe,CAAC;AAGxC,OAAO,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AAiBxC,MAAM,CAAC,KAAK,UAAU,gBAAgB,CAAC,OAA4B;IACjE,6CAA6C;IAC7C,MAAM,OAAO,GAAG,IAAI,OAAO,CAAC,OAAO,CAAC,WAAW,CAAC,CAAA;IAEhD,OAAO,KAAK,CAAC,KAAK,EAAE,MAAW,EAAE,EAAE;;;YACjC,KAAsB,IAAA,WAAA,cAAA,MAAM,CAAA,YAAA;gBAAjB,IAAI,GAAG,mBAAA,CAAA;gBAChB,+CAA+C;gBAC/C,IAAI,OAAO,GAAG,CAAC,GAAG,KAAK,QAAQ,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,MAAM,EAAE;oBAClD,OAAO,CAAC,KAAK,CAAC,2CAA2C,CAAC,CAAA;oBAC1D,SAAQ;iBACT;gBAED,oBAAoB;gBACpB,MAAM,IAAI,GAAY,EAAE,CAAC;gBAEzB,qBAAqB;gBACrB,IAAI,OAAO,GAAG,CAAC,IAAI,KAAK,QAAQ,IAAI,GAAG,CAAC,IAAI,CAAC,MAAM,EAAE;oBACnD,MAAM,IAAI,GAAG,IAAI,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;oBAChC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC,EAAE;wBAC1B,IAAI,CAAC,EAAE,GAAG,IAAI,CAAC;qBAChB;iBACF;gBAED,wCAAwC;gBACxC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC;qBACb,MAAM,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,MAAM,EAAE,KAAK,EAAE,OAAO,EAAE,GAAG,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC;qBAC7D,OAAO,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,GAAG,GAAG,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC;gBAE1C,0BAA0B;gBAC1B,IAAI,KAAe,CAAC;gBAEpB,IAAI;oBACF,KAAK,GAAG,WAAW,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC;iBAChC;gBAAC,OAAO,CAAC,EAAE;oBACV,OAAO,CAAC,KAAK,CAAC,gCAAgC,CAAC,CAAA;oBAC/C,SAAQ;iBACT;gBAED,iBAAiB;gBACjB,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,EAAE,KAAK,EAAE,IAAI,CAAC,CAAC;aACnC;;;;;;;;;IACH,CAAC,CAAC,CAAA;AACJ,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,112 @@
|
|
|
1
|
+
import pino from "pino";
|
|
2
|
+
import { Logtail } from "@logtail/node";
|
|
3
|
+
import { LogLevel } from "@logtail/types";
|
|
4
|
+
// Numeric log level test type
|
|
5
|
+
// type LevelTest = [number, LogLevel, LogLevelString];
|
|
6
|
+
// Sample log message
|
|
7
|
+
const message = "Something to do with something";
|
|
8
|
+
/**
|
|
9
|
+
* Create a Pino logger instance with Logtail transport
|
|
10
|
+
*
|
|
11
|
+
*/
|
|
12
|
+
function createLogger() {
|
|
13
|
+
const token = "invalid source token";
|
|
14
|
+
const logtailOptions = { ignoreExceptions: true };
|
|
15
|
+
const options = { sourceToken: token, options: logtailOptions };
|
|
16
|
+
const transport = pino.transport({
|
|
17
|
+
target: "./pino.js",
|
|
18
|
+
options: options
|
|
19
|
+
});
|
|
20
|
+
return pino(transport);
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* Test a Bunyan log level vs. a Logtail `LogLevel`
|
|
24
|
+
*
|
|
25
|
+
* @param level LogLevelString - Bunyan log level (string)
|
|
26
|
+
* @param logLevel LogLevel - Logtail log level
|
|
27
|
+
* @param cb Function - Callback to execute to signal test completion
|
|
28
|
+
*/
|
|
29
|
+
async function testLevel(level, logLevel, cb) {
|
|
30
|
+
// Logtail fixtures
|
|
31
|
+
const logtail = new Logtail("test", { batchInterval: 1 });
|
|
32
|
+
logtail.setSync(async (logs) => {
|
|
33
|
+
// Should be exactly one log
|
|
34
|
+
expect(logs.length).toBe(1);
|
|
35
|
+
// Message should match
|
|
36
|
+
expect(logs[0].message).toBe(message);
|
|
37
|
+
// Log level should be 'info'
|
|
38
|
+
expect(logs[0].level).toBe(logLevel);
|
|
39
|
+
// Signal that the test has finished
|
|
40
|
+
setImmediate(() => cb());
|
|
41
|
+
return logs;
|
|
42
|
+
});
|
|
43
|
+
// Create Bunyan logger
|
|
44
|
+
const logger = createLogger(logtail);
|
|
45
|
+
// Log out to Bunyan
|
|
46
|
+
logger[level](message);
|
|
47
|
+
}
|
|
48
|
+
describe("Bunyan tests", () => {
|
|
49
|
+
it("should log at the 'debug' level", async (done) => {
|
|
50
|
+
return testLevel("debug", LogLevel.Debug, done);
|
|
51
|
+
});
|
|
52
|
+
it("should log at the 'info' level", async (done) => {
|
|
53
|
+
return testLevel("info", LogLevel.Info, done);
|
|
54
|
+
});
|
|
55
|
+
it("should log at the 'warn' level", async (done) => {
|
|
56
|
+
return testLevel("warn", LogLevel.Warn, done);
|
|
57
|
+
});
|
|
58
|
+
it("should log at the 'error' level", async (done) => {
|
|
59
|
+
return testLevel("error", LogLevel.Error, done);
|
|
60
|
+
});
|
|
61
|
+
it("should log at the 'fatal' level", async (done) => {
|
|
62
|
+
return testLevel("fatal", LogLevel.Error, done);
|
|
63
|
+
});
|
|
64
|
+
it("should log using number levels", async (done) => {
|
|
65
|
+
// Fixtures
|
|
66
|
+
const levels = [
|
|
67
|
+
[25, LogLevel.Debug, "debug"],
|
|
68
|
+
[35, LogLevel.Info, "info"],
|
|
69
|
+
[45, LogLevel.Warn, "warn"],
|
|
70
|
+
[55, LogLevel.Error, "error"]
|
|
71
|
+
];
|
|
72
|
+
const logtail = new Logtail("test", {
|
|
73
|
+
batchInterval: 1000,
|
|
74
|
+
batchSize: levels.length
|
|
75
|
+
});
|
|
76
|
+
logtail.setSync(async (logs) => {
|
|
77
|
+
expect(logs.length).toBe(levels.length);
|
|
78
|
+
done();
|
|
79
|
+
return logs;
|
|
80
|
+
});
|
|
81
|
+
// Create Bunyan logger
|
|
82
|
+
const logger = createLogger(logtail);
|
|
83
|
+
// Cycle through levels, and log
|
|
84
|
+
levels.forEach(level => logger[level[2]](message));
|
|
85
|
+
});
|
|
86
|
+
it("should include arbitrary extra data fields", async (done) => {
|
|
87
|
+
const logtail = new Logtail("test");
|
|
88
|
+
logtail.setSync(async (logs) => {
|
|
89
|
+
expect(logs).toHaveLength(1);
|
|
90
|
+
expect(logs[0].message).toEqual("i am the message");
|
|
91
|
+
expect(logs[0].foo).toEqual("bar");
|
|
92
|
+
expect(logs[0].some).toEqual({ nested: "stuff" });
|
|
93
|
+
done();
|
|
94
|
+
return logs;
|
|
95
|
+
});
|
|
96
|
+
const logger = createLogger(logtail);
|
|
97
|
+
logger.info({ foo: "bar", some: { nested: "stuff" } }, "i am the message");
|
|
98
|
+
});
|
|
99
|
+
it("should include correct context fields", async (done) => {
|
|
100
|
+
const logtail = new Logtail("test");
|
|
101
|
+
logtail.setSync(async (logs) => {
|
|
102
|
+
const context = logs[0].context;
|
|
103
|
+
const runtime = context.runtime;
|
|
104
|
+
expect(runtime.file).toEqual("bunyan.test.ts");
|
|
105
|
+
done();
|
|
106
|
+
return logs;
|
|
107
|
+
});
|
|
108
|
+
const logger = createLogger(logtail);
|
|
109
|
+
logger.info("message with context");
|
|
110
|
+
});
|
|
111
|
+
});
|
|
112
|
+
//# sourceMappingURL=pino.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pino.test.js","sourceRoot":"","sources":["../../src/pino.test.ts"],"names":[],"mappings":"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"}
|
package/package.json
ADDED
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@logtail/pino",
|
|
3
|
+
"version": "0.0.1",
|
|
4
|
+
"description": "Logtail Pino transport by Better Stack",
|
|
5
|
+
"keywords": [
|
|
6
|
+
"Better Stack",
|
|
7
|
+
"Logtail",
|
|
8
|
+
"logger",
|
|
9
|
+
"logging",
|
|
10
|
+
"node",
|
|
11
|
+
"pino",
|
|
12
|
+
"transport"
|
|
13
|
+
],
|
|
14
|
+
"repository": "github.com/logtail/logtail-js.git",
|
|
15
|
+
"author": "Better Stack <hello@betterstack.com>",
|
|
16
|
+
"license": "ISC",
|
|
17
|
+
"main": "dist/cjs/index.js",
|
|
18
|
+
"module": "dist/es6/index.js",
|
|
19
|
+
"types": "dist/es6/index.d.ts",
|
|
20
|
+
"bugs": {
|
|
21
|
+
"url": "https://github.com/logtail/logtail-js/issues"
|
|
22
|
+
},
|
|
23
|
+
"devDependencies": {
|
|
24
|
+
"@logtail/node": "^0.1.15",
|
|
25
|
+
"npm-run-all": "^4.1.5",
|
|
26
|
+
"typescript": "^3.9.7"
|
|
27
|
+
},
|
|
28
|
+
"peerDependencies": {
|
|
29
|
+
"@logtail/node": "^0.1.0"
|
|
30
|
+
},
|
|
31
|
+
"dependencies": {
|
|
32
|
+
"@logtail/types": "^0.1.15",
|
|
33
|
+
"pino": "^8.8.0"
|
|
34
|
+
},
|
|
35
|
+
"scripts": {
|
|
36
|
+
"build:cjs": "tsc",
|
|
37
|
+
"build:es6": "tsc -p tsconfig.es6.json",
|
|
38
|
+
"build": "run-p build:*",
|
|
39
|
+
"prepublishOnly": "npm run build",
|
|
40
|
+
"test": "echo \"Error: run tests from root\" && exit 1"
|
|
41
|
+
},
|
|
42
|
+
"private": false
|
|
43
|
+
}
|
package/src/helpers.ts
ADDED
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import { LogLevel } from "@logtail/types";
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Return a Logtail `LogLevel` based on the Pino level
|
|
5
|
+
* @param level number - Pino log level
|
|
6
|
+
*/
|
|
7
|
+
export function getLogLevel(level: number): LogLevel {
|
|
8
|
+
|
|
9
|
+
// TODO: Trace 10
|
|
10
|
+
if (level <= 10) {
|
|
11
|
+
return LogLevel.Debug;
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
// Debug
|
|
15
|
+
if (level <= 20) {
|
|
16
|
+
return LogLevel.Debug;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
// Info
|
|
20
|
+
if (level <= 30) {
|
|
21
|
+
return LogLevel.Info;
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
// Warn
|
|
25
|
+
if (level <= 40) {
|
|
26
|
+
return LogLevel.Warn;
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
// Everything above this level is considered an error
|
|
30
|
+
// TODO: Fatal 60 (Error 50)
|
|
31
|
+
return LogLevel.Error;
|
|
32
|
+
}
|
package/src/index.ts
ADDED
package/src/pino.ts
ADDED
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
import build from 'pino-abstract-transport'
|
|
2
|
+
|
|
3
|
+
import { Logtail } from "@logtail/node";
|
|
4
|
+
import { Context, LogLevel, ILogtailOptions, StackContextHint } from "@logtail/types";
|
|
5
|
+
|
|
6
|
+
import { getLogLevel } from "./helpers";
|
|
7
|
+
|
|
8
|
+
// import { PinoLog, PinoLokiOptionsContract } from './Contracts'
|
|
9
|
+
// import { LogPusher } from './LogPusher'
|
|
10
|
+
|
|
11
|
+
// TODO: stackContextHint =
|
|
12
|
+
|
|
13
|
+
export interface PinoLog {
|
|
14
|
+
level: number
|
|
15
|
+
[key: string]: any
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
export interface IPinoLogtailOptions {
|
|
19
|
+
sourceToken: string,
|
|
20
|
+
options: Partial<ILogtailOptions>
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
export async function logtailTransport(options: IPinoLogtailOptions) {
|
|
24
|
+
// FIXME: error handling for no source token
|
|
25
|
+
const logtail = new Logtail(options.sourceToken)
|
|
26
|
+
|
|
27
|
+
return build(async (source: any) => {
|
|
28
|
+
for await (let obj of source) {
|
|
29
|
+
// Log should have string `msg` key, > 0 length
|
|
30
|
+
if (typeof obj.msg !== "string" || !obj.msg.length) {
|
|
31
|
+
console.error('Field "msg" has to be a non-empty string.')
|
|
32
|
+
continue
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
// Logging meta data
|
|
36
|
+
const meta: Context = {};
|
|
37
|
+
|
|
38
|
+
// Copy `time` if set
|
|
39
|
+
if (typeof obj.time === "string" || obj.time.length) {
|
|
40
|
+
const time = new Date(obj.time);
|
|
41
|
+
if (!isNaN(time.valueOf())) {
|
|
42
|
+
meta.dt = time;
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
// Carry over any additional data fields
|
|
47
|
+
Object.keys(obj)
|
|
48
|
+
.filter(key => ["time", "msg", "level", "v"].indexOf(key) < 0)
|
|
49
|
+
.forEach(key => (meta[key] = obj[key]));
|
|
50
|
+
|
|
51
|
+
// Determine the log level
|
|
52
|
+
let level: LogLevel;
|
|
53
|
+
|
|
54
|
+
try {
|
|
55
|
+
level = getLogLevel(obj.level);
|
|
56
|
+
} catch (_) {
|
|
57
|
+
console.error('Error while mapping log level.')
|
|
58
|
+
continue
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
// Log to Logtail
|
|
62
|
+
logtail.log(obj.msg, level, meta);
|
|
63
|
+
}
|
|
64
|
+
})
|
|
65
|
+
}
|
package/tsconfig.json
ADDED
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
{
|
|
2
|
+
"compilerOptions": {
|
|
3
|
+
"target": "es2017" /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017','ES2018' or 'ESNEXT'. */,
|
|
4
|
+
"module": "commonjs" /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', or 'ESNext'. */,
|
|
5
|
+
"declaration": true /* Generates corresponding '.d.ts' file. */,
|
|
6
|
+
"sourceMap": true /* Generates corresponding '.map' file. */, // "outFile": "./", /* Concatenate and emit output to single file. */
|
|
7
|
+
"outDir": "dist/cjs" /* Redirect output structure to the directory. */,
|
|
8
|
+
"strict": true /* Enable all strict type-checking options. */,
|
|
9
|
+
"esModuleInterop": true /* Enables emit interoperability between CommonJS and ES Modules via creation of namespace objects for all imports. Implies 'allowSyntheticDefaultImports'. */,
|
|
10
|
+
"moduleResolution": "node",
|
|
11
|
+
"resolveJsonModule": true
|
|
12
|
+
},
|
|
13
|
+
"include": ["./src"]
|
|
14
|
+
}
|