unrip/src/core/log.mjs

55 lines
1.4 KiB
JavaScript

import process from 'node:process';
export function logJson(event) {
process.stdout.write(`${JSON.stringify(compact({
ts: new Date().toISOString(),
...event,
}))}\n`);
}
export function createLogger(bindings = {}) {
const base = compact(bindings);
return {
child(extraBindings = {}) {
return createLogger({ ...base, ...extraBindings });
},
info(event, fields = {}) {
logJson({ level: 'info', ...base, event, ...compact(fields) });
},
warn(event, fields = {}) {
logJson({ level: 'warn', ...base, event, ...compact(fields) });
},
error(event, fields = {}) {
logJson({ level: 'error', ...base, event, ...compact(fields) });
},
};
}
export function serializeError(error) {
if (!error) return null;
if (error instanceof Error) {
return compact({
name: error.name,
message: error.message,
stack: error.stack,
code: error.code,
});
}
if (typeof error === 'object') return compact(error);
return { message: String(error) };
}
function compact(value) {
if (Array.isArray(value)) {
return value.map((item) => compact(item));
}
if (!value || typeof value !== 'object') return value;
const entries = Object.entries(value)
.filter(([, entry]) => entry !== undefined)
.map(([key, entry]) => [key, compact(entry)]);
return Object.fromEntries(entries);
}