From 756ebf3c78252405fcd569feef334b075dae0956 Mon Sep 17 00:00:00 2001 From: Jonathan Bernard Date: Tue, 7 Jan 2025 08:48:37 -0600 Subject: [PATCH] Allow LogMessageFormatter to return FlattenedLogMessages. Originally the idea was that a log formatter should turn the LogMessage into a string that can be appended via a LogAppender. However, all of the default LogAppenders can handle objects. In particular, the ConsoleLogAppender writes to the browser console which offers an interactive UI experience when logging raw objects. For LogAppenders that can only manage text, it seems an acceptable design decision to require users to provide a LogMessageFormatter that returns a string, or accept some sane default like JSON.stringify if their formatter returns objects. --- src/console-log-appender.ts | 4 ++-- src/log-message.ts | 7 ++++--- 2 files changed, 6 insertions(+), 5 deletions(-) diff --git a/src/console-log-appender.ts b/src/console-log-appender.ts index 4e43c7f..8c67eea 100644 --- a/src/console-log-appender.ts +++ b/src/console-log-appender.ts @@ -1,14 +1,14 @@ import { + flattenMessage, LogLevel, LogMessage, LogMessageFormatter, - structuredLogMessageFormatter } from './log-message'; import { LogAppender } from './log-appender'; export class ConsoleLogAppender implements LogAppender { public threshold = LogLevel.ALL; - public formatter = structuredLogMessageFormatter; + public formatter: LogMessageFormatter = flattenMessage constructor(threshold?: LogLevel, formatter?: LogMessageFormatter) { if (threshold) { diff --git a/src/log-message.ts b/src/log-message.ts index 81956b6..0d6191d 100644 --- a/src/log-message.ts +++ b/src/log-message.ts @@ -50,12 +50,12 @@ export type FlattenedLogMessage = Record; * * Should result after flattening in a structured log message like: * ```json - * {"scope":"example","level":4,"foo":"bar","baz":"qux","timestamp":"2020-01-01T00:00:00.000Z"} + * {"scope":"example","level":"INFO","foo":"bar","baz":"qux","timestamp":"2020-01-01T00:00:00.000Z"} * ``` */ export function flattenMessage(msg: LogMessage): FlattenedLogMessage { if (typeof msg.message === 'string') { - return { ...msg }; + return { ...msg, level: LogLevel[msg.level] }; } else { const { message, ...rest } = msg; return { @@ -67,10 +67,11 @@ export function flattenMessage(msg: LogMessage): FlattenedLogMessage { 'timestamp', ]), ...rest, + level: LogLevel[msg.level], }; } } -export type LogMessageFormatter = (msg: LogMessage) => string; +export type LogMessageFormatter = (msg: LogMessage) => string | FlattenedLogMessage; export function structuredLogMessageFormatter(msg: LogMessage): string { return JSON.stringify(flattenMessage(msg));