UNPKG

@tobes31415/console-logger

Version:

Formats console logs while preserving stack trace info

129 lines (128 loc) 3.91 kB
import { Subject } from "@tobes31415/basic-observables"; import { deepAssign, isNullorUndefined, nullishCoalesce } from "./util.js"; const APP_START_TIME = Date.now(); var LogLevel = /* @__PURE__ */ ((LogLevel2) => { LogLevel2["debug"] = "debug"; LogLevel2["error"] = "error"; LogLevel2["info"] = "info"; LogLevel2["warn"] = "warn"; return LogLevel2; })(LogLevel || {}); function LevelToNumber(level) { switch (level) { case "debug" /* debug */: return 0; case "info" /* info */: return 1; case "warn" /* warn */: return 2; case "error" /* error */: return 3; } } const DEFUALT_STYLE = { namespace: "color: dimgray", level: "color: dimgray", uptime: "color: darkgray", time: "color: lightgray" }; const DEFAULT_FORMAT = { namespace: "[${namespace}]", uptime: (uptime) => `${uptime / 1e3}s`, time: (time) => time.toISOString(), level: (level) => level.toUpperCase(), message: "${message}" }; const DEFAULT_CONFIG = { defaultLogLevel: "debug" /* debug */, logThreshold: "debug" /* debug */, include: ["namespace", "uptime", "-", "message"], style: Object.assign({}, DEFUALT_STYLE), format: Object.assign({}, DEFAULT_FORMAT), delimiter: " " }; const currentGlobalConfig = deepAssign({}, DEFAULT_CONFIG); const broadcastEvent = new Subject(); const onLogEvent = broadcastEvent; function customizeDefaultLogConfig(newConfig) { deepAssign(currentGlobalConfig, DEFAULT_CONFIG, currentGlobalConfig, newConfig); } function createLoggerFor(namespace, config) { let currentConfig = config; const getConfig = () => deepAssign({}, currentGlobalConfig, currentConfig); const result = handleLog.bind(this, getConfig, namespace, void 0); Object.values(LogLevel).forEach((level) => result[level] = handleLog.bind(this, getConfig, namespace, level)); result.config = (newConfig) => { let previousConfig = currentConfig; currentConfig = deepAssign({}, previousConfig, newConfig); }; return result; } function handleLog(configFn, namespace, level, message, ...extras) { const config = configFn(); const actualLevel = level || config.defaultLogLevel; if (LevelToNumber(actualLevel) < LevelToNumber(config.logThreshold)) { return []; } const time = /* @__PURE__ */ new Date(); const logEvent = { message, namespace, level: actualLevel, extras, time, uptime: time.getTime() - APP_START_TIME }; try { broadcastEvent.next(logEvent); } catch (ignored) { } return formatLog(config, logEvent); } function formatLog(config, event) { const result = []; const styles = []; let isStyleApplied = false; config.include.forEach((section) => { const value = event[section]; const interim = []; const clearStyle = () => { if (isStyleApplied) { interim.push("%c"); styles.push(""); isStyleApplied = false; } }; if (isNullorUndefined(value)) { clearStyle(); interim.push(section); } else { if (config.style && config.style[section]) { interim.push("%c"); styles.push(config.style[section]); isStyleApplied = true; } else { clearStyle(); } const formatter = config.format ? config.format[section] : void 0; if (!formatter) { interim.push("" + value); } else if (typeof formatter === "string") { interim.push(formatter.replace("${" + section + "}", "" + value)); } else if (typeof formatter === "function") { interim.push(formatter(value)); } else { console.error(formatter, config); throw new Error("Log Formatter invalid, must be string or function"); } } result.push(interim.join("")); }); return [result.join(nullishCoalesce(config.delimiter, " ")), ...styles, ...event.extras]; } export { LogLevel, createLoggerFor, customizeDefaultLogConfig, onLogEvent };