@ecopages/logger
Advanced tools
+20
-5
@@ -31,9 +31,15 @@ declare const Level: { | ||
| /** | ||
| * Format of the timestamp. Possible values: | ||
| * - 'full' = 'YYYY-MM-DD HH:mm:ss' | ||
| * - 'time' = 'HH:mm:ss' | ||
| * - 'short' = 'MM-DD HH:mm:ss' | ||
| * Format of the timestamp. | ||
| * Possible values: | ||
| * - 'full' = date + time | ||
| * - 'time' = time only | ||
| * - 'short' = short date + time | ||
| */ | ||
| timestampFormat?: 'full' | 'time' | 'short'; | ||
| /** | ||
| * Locale used by timestamp formatting. | ||
| * Defaults to 'en-US' for deterministic output. | ||
| */ | ||
| locale?: string | string[]; | ||
| /** | ||
| * Custom colors for different log levels. | ||
@@ -74,5 +80,8 @@ * In browser: use CSS color values (e.g., '#00ff00', 'red', etc.) | ||
| * Logs an error message. | ||
| * Accepts unknown values (e.g. strict TypeScript catch variables). | ||
| * When an {@link Error} is provided, its stack (or name/message fallback) | ||
| * is logged so stack traces remain visible. | ||
| * @param args The arguments to be logged. | ||
| */ | ||
| error(...args: LogArgument[]): this; | ||
| error(...args: unknown[]): this; | ||
| /** | ||
@@ -86,2 +95,5 @@ * Logs a debug message. | ||
| * Starts a timer with a label. | ||
| * Timer behavior is unified across color modes: | ||
| * - with `color: true`, output is colorized | ||
| * - with `color: false`, output is plain text | ||
| * @param label The label for the timer. | ||
@@ -92,2 +104,3 @@ */ | ||
| * Ends a timer with a label. | ||
| * Logs a warning if the timer label was not started. | ||
| * @param label The label for the timer. | ||
@@ -99,2 +112,4 @@ */ | ||
| private getFormatSpecifier; | ||
| private normalizeLogArgs; | ||
| private getConsoleMethod; | ||
| private logInternal; | ||
@@ -101,0 +116,0 @@ /** |
+1
-1
@@ -1,1 +0,1 @@ | ||
| var q={INFO:"INFO",ERROR:"ERROR",WARN:"WARN",DEBUG:"DEBUG",TIMER:"TIMER"},V={level:q.INFO},X={level:q.ERROR},Y={level:q.WARN},Z={level:q.DEBUG},J=typeof window!=="undefined",_={INFO:"color: #00ff00",ERROR:"color: #ff0000",WARN:"color: #ffff00",DEBUG:"color: #00ffff",TIMER:"color: #ff00ff"},$={INFO:"\x1B[32m",ERROR:"\x1B[31m",WARN:"\x1B[33m",DEBUG:"\x1B[36m",TIMER:"\x1B[35m"};class A{prefix;colors;options={debug:!1,color:!0,timestampFormat:"time",verboseTimer:!1};timers=new Map;constructor(j,k){if(this.prefix=j,k)this.options={...this.options,...k};this.colors={...J?_:$,...k?.colors}}info(...j){return this.logInternal(V,...j),this}warn(...j){return this.logInternal(Y,...j),this}error(...j){return this.logInternal(X,...j),this}debug(...j){if(this.options.debug)this.logInternal(Z,...j);return this}time(j,k=q.TIMER){if(!this.options.color){console.time(`${this.prefix} ${j}`);return}if(this.timers.set(j,performance.now()),this.options.verboseTimer)if(J)console.log(`%c${this.prefix} ${j}: start`,this.getColor(k));else{let H=this.getColor(k);console.log(`${H}${this.prefix} ${j}: start\x1B[0m`)}}timeEnd(j,k=q.TIMER){if(!this.options.color){console.timeEnd(`${this.prefix} ${j}`);return}let H=this.timers.get(j);if(H===void 0){console.warn(`Timer '${this.prefix} ${j}' does not exist`);return}let z=performance.now()-H;if(this.timers.delete(j),J)console.log(`%c${this.prefix} ${j}: ${z.toFixed(2)}ms`,this.getColor(k));else{let K=this.getColor(k);console.log(`${K}${this.prefix} ${j}: ${z.toFixed(2)}ms\x1B[0m`)}}getTimestamp(){if(!this.options.timestamp)return"";let j=new Date,k;switch(this.options.timestampFormat){case"full":k={year:"numeric",month:"2-digit",day:"2-digit",hour:"2-digit",minute:"2-digit",second:"2-digit",hour12:!1};break;case"short":k={month:"2-digit",day:"2-digit",hour:"2-digit",minute:"2-digit",second:"2-digit",hour12:!1};break;default:k={hour:"2-digit",minute:"2-digit",second:"2-digit",hour12:!1}}return`[${j.toLocaleString("en-US",k)}] `}getColor(j){return this.colors[j]??""}getFormatSpecifier(j){if(j===null)return"%s";if(j===void 0)return"%s";switch(typeof j){case"object":return"%o";case"number":return"%d";case"boolean":return"%s";default:return"%s"}}logInternal(j,...k){let z=this.getTimestamp()+this.prefix;if(!this.options.color){console.log(z,...k);return}if(J){let P=j?this.getColor(j.level):"",Q=k.map((S)=>this.getFormatSpecifier(S));console.log(`%c${z} ${Q.join(" ")}`,P,...k);return}let K=j?this.getColor(j.level):"",M="\x1B[0m";console.log(`${K}${z}`,...k,M)}isDebugEnabled(){return!!this.options.debug}debugTime(j){if(this.isDebugEnabled())this.time(j,q.DEBUG)}debugTimeEnd(j){if(this.isDebugEnabled())this.timeEnd(j,q.DEBUG)}}export{A as Logger}; | ||
| var H={INFO:"INFO",ERROR:"ERROR",WARN:"WARN",DEBUG:"DEBUG",TIMER:"TIMER"},_={level:H.INFO},$={level:H.ERROR},D={level:H.WARN},F={level:H.DEBUG},P=typeof window<"u",G={INFO:"color: #00ff00",ERROR:"color: #ff0000",WARN:"color: #ffff00",DEBUG:"color: #00ffff",TIMER:"color: #ff00ff"},I={INFO:"\x1B[32m",ERROR:"\x1B[31m",WARN:"\x1B[33m",DEBUG:"\x1B[36m",TIMER:"\x1B[35m"};class U{prefix;colors;options={debug:!1,color:!0,timestampFormat:"time",verboseTimer:!1};timers=new Map;constructor(j,k){if(this.prefix=j,k)this.options={...this.options,...k};this.colors={...P?G:I,...k?.colors}}info(...j){return this.logInternal(_,...j),this}warn(...j){return this.logInternal(D,...j),this}error(...j){return this.logInternal($,...j),this}debug(...j){if(this.options.debug)this.logInternal(F,...j);return this}time(j,k=H.TIMER){if(this.timers.set(j,performance.now()),this.options.verboseTimer)if(P)if(this.options.color)console.log(`%c${this.prefix} ${j}: start`,this.getColor(k));else console.log(`${this.prefix} ${j}: start`);else if(this.options.color){let q=this.getColor(k);console.log(`${q}${this.prefix} ${j}: start\x1B[0m`)}else console.log(`${this.prefix} ${j}: start`)}timeEnd(j,k=H.TIMER){let q=this.timers.get(j);if(q===void 0){console.warn(`Timer '${this.prefix} ${j}' does not exist`);return}let J=performance.now()-q;if(this.timers.delete(j),P)if(this.options.color)console.log(`%c${this.prefix} ${j}: ${J.toFixed(2)}ms`,this.getColor(k));else console.log(`${this.prefix} ${j}: ${J.toFixed(2)}ms`);else if(this.options.color){let K=this.getColor(k);console.log(`${K}${this.prefix} ${j}: ${J.toFixed(2)}ms\x1B[0m`)}else console.log(`${this.prefix} ${j}: ${J.toFixed(2)}ms`)}getTimestamp(){if(!this.options.timestamp)return"";let j=new Date,k;switch(this.options.timestampFormat){case"full":k={year:"numeric",month:"2-digit",day:"2-digit",hour:"2-digit",minute:"2-digit",second:"2-digit",hour12:!1};break;case"short":k={month:"2-digit",day:"2-digit",hour:"2-digit",minute:"2-digit",second:"2-digit",hour12:!1};break;default:k={hour:"2-digit",minute:"2-digit",second:"2-digit",hour12:!1}}let q=this.options.locale??"en-US";return`[${j.toLocaleString(q,k)}] `}getColor(j){return this.colors[j]??""}getFormatSpecifier(j){if(j===null)return"%s";if(j===void 0)return"%s";switch(typeof j){case"object":return"%o";case"number":return"%d";case"boolean":return"%s";default:return"%s"}}normalizeLogArgs(j,k){if(j!==H.ERROR)return k;return k.map((q)=>{if(q instanceof Error)return q.stack??`${q.name}: ${q.message}`;return q})}getConsoleMethod(j){switch(j){case H.ERROR:return console.error.bind(console);case H.WARN:return console.warn.bind(console);default:return console.log.bind(console)}}logInternal(j,...k){let J=this.getTimestamp()+this.prefix,K=this.normalizeLogArgs(j?.level,k),Q=this.getConsoleMethod(j?.level);if(!this.options.color){Q(J,...K);return}if(P){let X=j?this.getColor(j.level):"",Y=K.map((Z)=>this.getFormatSpecifier(Z));Q(`%c${J} ${Y.join(" ")}`,X,...K);return}let S=j?this.getColor(j.level):"",V="\x1B[0m";Q(`${S}${J}`,...K,V)}isDebugEnabled(){return!!this.options.debug}debugTime(j){if(this.isDebugEnabled())this.time(j,H.DEBUG)}debugTimeEnd(j){if(this.isDebugEnabled())this.timeEnd(j,H.DEBUG)}}export{U as Logger}; |
+4
-3
| { | ||
| "name": "@ecopages/logger", | ||
| "version": "0.2.2", | ||
| "version": "0.2.3", | ||
| "license": "MIT", | ||
@@ -17,4 +17,4 @@ "main": "./dist/logger.js", | ||
| "build:types": "tsc -p tsconfig.build.json", | ||
| "format": "bunx @biomejs/biome format --write .", | ||
| "lint": "bunx @biomejs/biome check --apply .", | ||
| "format": "biome format --write .", | ||
| "lint": "biome check --write .", | ||
| "lint-staged": "lint-staged", | ||
@@ -29,2 +29,3 @@ "prepare": "husky", | ||
| "devDependencies": { | ||
| "@biomejs/biome": "^1.9.4", | ||
| "@changesets/changelog-github": "^0.5.0", | ||
@@ -31,0 +32,0 @@ "@changesets/cli": "^2.27.5", |
+33
-4
@@ -51,2 +51,3 @@ # @ecopages/logger | ||
| timestampFormat: "full", // Configure timestamp format | ||
| locale: "de-DE", // Optional locale for timestamps | ||
| verboseTimer: true, // Show timer start messages | ||
@@ -69,2 +70,3 @@ colors: { | ||
| | `timestampFormat` | "full" \| "time" \| "short" | "time" | Timestamp format | | ||
| | `locale` | string \| string[] | "en-US" | Locale used for timestamps | | ||
| | `verboseTimer` | boolean | `false` | Show timer start messages | | ||
@@ -75,8 +77,35 @@ | `colors` | Partial<ColorConfig> | - | Custom colors for log levels | | ||
| - `full`: `YYYY-MM-DD HH:mm:ss` | ||
| - `time`: `HH:mm:ss` | ||
| - `short`: `MM-DD HH:mm:ss` | ||
| - `full`: full date and time | ||
| - `time`: time only | ||
| - `short`: short date and time | ||
| Timestamp output is generated via `toLocaleString(locale, ...)`. | ||
| By default, locale is `en-US`; set `locale` to customize it. | ||
| ## Error Stack Traces | ||
| To keep stack traces, pass the actual `Error` object to `logger.error`: | ||
| ```ts | ||
| try { | ||
| throw new Error("Something failed"); | ||
| } catch (error: unknown) { | ||
| if (error instanceof Error) { | ||
| logger.error(error); // preserves stack output | ||
| } else { | ||
| logger.error(new Error(String(error))); | ||
| } | ||
| } | ||
| ``` | ||
| If you pass `error.message` (string) instead, the stack trace is not available. | ||
| ## Timer Functionality | ||
| Timer behavior is consistent whether colors are enabled or disabled: | ||
| - `color: true` → colorized timer output | ||
| - `color: false` → plain timer output | ||
| - `verboseTimer: true` → logs `start` message before duration output | ||
| ```ts | ||
@@ -150,3 +179,3 @@ // Start a timer | ||
| logger.info("Application started"); | ||
| // Output: [2024-02-16 15:30:45] [my-app] Application started | ||
| // Output: [02/16/2024, 15:30:45] [my-app] Application started | ||
| ``` | ||
@@ -153,0 +182,0 @@ |
15028
15.64%140
13.82%213
15.76%7
16.67%