@mks2508/better-logger 0.14.0-alpha.2 → 1.1.0

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.
Files changed (205) hide show
  1. package/.claude/settings.local.json +2 -1
  2. package/dist/Logger.d.ts +12 -16
  3. package/dist/Logger.d.ts.map +1 -1
  4. package/dist/ScopedLogger.d.ts +1 -9
  5. package/dist/chunks/{Logger-D_p3xnbq.js → Logger-C9zTFYBh.js} +2 -2
  6. package/dist/chunks/Logger-C9zTFYBh.js.map +1 -0
  7. package/dist/chunks/{Logger-Crw1woqR.js → Logger-Th9SfADL.js} +50 -17
  8. package/dist/chunks/Logger-Th9SfADL.js.map +1 -0
  9. package/dist/chunks/ScopedLogger-HgV_J-ug.js +2 -0
  10. package/dist/chunks/ScopedLogger-HgV_J-ug.js.map +1 -0
  11. package/dist/chunks/ScopedLogger-uAAeJkfA.js +361 -0
  12. package/dist/chunks/ScopedLogger-uAAeJkfA.js.map +1 -0
  13. package/dist/chunks/environment-5I5unY89.js +4 -0
  14. package/dist/chunks/environment-5I5unY89.js.map +1 -0
  15. package/dist/chunks/{environment-Bxbnw4pd.js → environment-wXLQvk5g.js} +103 -11
  16. package/dist/chunks/environment-wXLQvk5g.js.map +1 -0
  17. package/dist/chunks/formatting-CiFnwe1I.js +2 -0
  18. package/dist/chunks/formatting-CiFnwe1I.js.map +1 -0
  19. package/dist/chunks/formatting-DIhpRCCk.js +380 -0
  20. package/dist/chunks/formatting-DIhpRCCk.js.map +1 -0
  21. package/dist/cli/CommandProcessor.d.ts +1 -4
  22. package/dist/cli/commands/ConfigCommand.d.ts +2 -5
  23. package/dist/cli/commands/ExportCommand.d.ts +2 -5
  24. package/dist/cli/commands/HistoryCommand.d.ts +2 -5
  25. package/dist/cli/commands/StatusCommand.d.ts +2 -5
  26. package/dist/cli/commands/ThemeCommand.d.ts +2 -5
  27. package/dist/cli/help.d.ts +2 -5
  28. package/dist/cli/index.d.ts +1 -1
  29. package/dist/constants.d.ts +110 -5
  30. package/dist/constants.d.ts.map +1 -1
  31. package/dist/core.cjs +1 -1
  32. package/dist/core.cjs.map +1 -1
  33. package/dist/core.d.ts +1 -8
  34. package/dist/core.d.ts.map +1 -1
  35. package/dist/core.js +281 -307
  36. package/dist/core.js.map +1 -1
  37. package/dist/exports-module.d.ts +1 -8
  38. package/dist/exports.cjs +1 -1
  39. package/dist/exports.js +2 -2
  40. package/dist/handlers/AnalyticsLogHandler.d.ts +1 -4
  41. package/dist/handlers/ExportLogHandler.d.ts +1 -4
  42. package/dist/handlers/ExportLogHandler.d.ts.map +1 -1
  43. package/dist/handlers/FileLogHandler.d.ts +1 -4
  44. package/dist/handlers/RemoteLogHandler.d.ts +1 -4
  45. package/dist/index.cjs +1 -1
  46. package/dist/index.cjs.map +1 -1
  47. package/dist/index.d.ts +8 -41
  48. package/dist/index.d.ts.map +1 -1
  49. package/dist/index.js +246 -159
  50. package/dist/index.js.map +1 -1
  51. package/dist/styling/LogStyleBuilder.d.ts +2 -5
  52. package/dist/styling/SemanticStyles.d.ts +0 -3
  53. package/dist/styling/SmartPresets.d.ts +1 -4
  54. package/dist/styling/banners.d.ts +1 -4
  55. package/dist/styling/themes.d.ts +2 -5
  56. package/dist/styling-module.d.ts +1 -8
  57. package/dist/styling.cjs +1 -1
  58. package/dist/styling.js +3 -3
  59. package/dist/types/core.d.ts +13 -0
  60. package/dist/types/core.d.ts.map +1 -1
  61. package/dist/types/handlers.d.ts +1 -4
  62. package/dist/types/index.d.ts +1 -1
  63. package/dist/types/index.d.ts.map +1 -1
  64. package/dist/utils/ansi-colors.d.ts +156 -0
  65. package/dist/utils/ansi-colors.d.ts.map +1 -0
  66. package/dist/utils/formatting.d.ts +20 -2
  67. package/dist/utils/formatting.d.ts.map +1 -1
  68. package/dist/utils/index.d.ts +1 -0
  69. package/dist/utils/index.d.ts.map +1 -1
  70. package/dist/utils/output.d.ts +1 -4
  71. package/dist/utils/stackTrace.d.ts +1 -4
  72. package/package.json +2 -1
  73. package/src/Logger.ts +102 -64
  74. package/src/constants.ts +131 -1
  75. package/src/core.ts +11 -7
  76. package/src/handlers/ExportLogHandler.ts +2 -1
  77. package/src/index.ts +62 -27
  78. package/src/styling/SemanticStyles.ts +1 -1
  79. package/src/types/core.ts +15 -1
  80. package/src/types/index.ts +1 -0
  81. package/src/utils/ansi-colors.ts +333 -0
  82. package/src/utils/formatting.ts +196 -6
  83. package/src/utils/index.ts +23 -11
  84. package/vite.config.ts +1 -1
  85. package/dist/.tsbuildinfo +0 -1
  86. package/dist/Logger.js +0 -1124
  87. package/dist/ScopedLogger.js +0 -426
  88. package/dist/chunks/Logger-Crw1woqR.js.map +0 -1
  89. package/dist/chunks/Logger-D_p3xnbq.js.map +0 -1
  90. package/dist/chunks/environment-Bxbnw4pd.js.map +0 -1
  91. package/dist/chunks/environment-Dm66zOML.js +0 -4
  92. package/dist/chunks/environment-Dm66zOML.js.map +0 -1
  93. package/dist/chunks/formatting-C0riPC5_.js +0 -95
  94. package/dist/chunks/formatting-C0riPC5_.js.map +0 -1
  95. package/dist/chunks/formatting-DNCAV66-.js +0 -2
  96. package/dist/chunks/formatting-DNCAV66-.js.map +0 -1
  97. package/dist/cli/CommandProcessor.js +0 -184
  98. package/dist/cli/commands/ConfigCommand.js +0 -88
  99. package/dist/cli/commands/ExportCommand.js +0 -243
  100. package/dist/cli/commands/HistoryCommand.js +0 -96
  101. package/dist/cli/commands/StatusCommand.js +0 -93
  102. package/dist/cli/commands/ThemeCommand.js +0 -79
  103. package/dist/cli/help.js +0 -118
  104. package/dist/cli/index.js +0 -46
  105. package/dist/constants.js +0 -159
  106. package/dist/example.js +0 -154
  107. package/dist/exports-module.js +0 -260
  108. package/dist/handlers/AnalyticsLogHandler.js +0 -19
  109. package/dist/handlers/ExportLogHandler.js +0 -516
  110. package/dist/handlers/FileLogHandler.js +0 -156
  111. package/dist/handlers/RemoteLogHandler.js +0 -37
  112. package/dist/handlers/index.js +0 -7
  113. package/dist/main.js +0 -139
  114. package/dist/styling/LogStyleBuilder.js +0 -289
  115. package/dist/styling/SemanticStyles.js +0 -339
  116. package/dist/styling/SmartPresets.js +0 -276
  117. package/dist/styling/StyleBuilder.js +0 -280
  118. package/dist/styling/banners.js +0 -155
  119. package/dist/styling/index.js +0 -9
  120. package/dist/styling/themes.js +0 -231
  121. package/dist/styling-module.js +0 -199
  122. package/dist/types/Logger.d.ts +0 -700
  123. package/dist/types/Logger.d.ts.map +0 -1
  124. package/dist/types/ScopedLogger.d.ts +0 -310
  125. package/dist/types/ScopedLogger.d.ts.map +0 -1
  126. package/dist/types/cli/CommandProcessor.d.ts +0 -100
  127. package/dist/types/cli/CommandProcessor.d.ts.map +0 -1
  128. package/dist/types/cli/commands/ConfigCommand.d.ts +0 -14
  129. package/dist/types/cli/commands/ConfigCommand.d.ts.map +0 -1
  130. package/dist/types/cli/commands/ExportCommand.d.ts +0 -48
  131. package/dist/types/cli/commands/ExportCommand.d.ts.map +0 -1
  132. package/dist/types/cli/commands/HistoryCommand.d.ts +0 -47
  133. package/dist/types/cli/commands/HistoryCommand.d.ts.map +0 -1
  134. package/dist/types/cli/commands/StatusCommand.d.ts +0 -30
  135. package/dist/types/cli/commands/StatusCommand.d.ts.map +0 -1
  136. package/dist/types/cli/commands/ThemeCommand.d.ts +0 -30
  137. package/dist/types/cli/commands/ThemeCommand.d.ts.map +0 -1
  138. package/dist/types/cli/help.d.ts +0 -12
  139. package/dist/types/cli/help.d.ts.map +0 -1
  140. package/dist/types/cli/index.d.ts +0 -15
  141. package/dist/types/cli/index.d.ts.map +0 -1
  142. package/dist/types/constants.d.ts +0 -119
  143. package/dist/types/constants.d.ts.map +0 -1
  144. package/dist/types/core.js +0 -28
  145. package/dist/types/example.d.ts +0 -18
  146. package/dist/types/example.d.ts.map +0 -1
  147. package/dist/types/exports-module.d.ts +0 -196
  148. package/dist/types/exports-module.d.ts.map +0 -1
  149. package/dist/types/handlers/AnalyticsLogHandler.d.ts +0 -8
  150. package/dist/types/handlers/AnalyticsLogHandler.d.ts.map +0 -1
  151. package/dist/types/handlers/ExportLogHandler.d.ts +0 -100
  152. package/dist/types/handlers/ExportLogHandler.d.ts.map +0 -1
  153. package/dist/types/handlers/FileLogHandler.d.ts +0 -33
  154. package/dist/types/handlers/FileLogHandler.d.ts.map +0 -1
  155. package/dist/types/handlers/RemoteLogHandler.d.ts +0 -11
  156. package/dist/types/handlers/RemoteLogHandler.d.ts.map +0 -1
  157. package/dist/types/handlers/index.d.ts +0 -8
  158. package/dist/types/handlers/index.d.ts.map +0 -1
  159. package/dist/types/handlers.js +0 -4
  160. package/dist/types/index.js +0 -4
  161. package/dist/types/main.d.ts +0 -2
  162. package/dist/types/main.d.ts.map +0 -1
  163. package/dist/types/styling/LogStyleBuilder.d.ts +0 -146
  164. package/dist/types/styling/LogStyleBuilder.d.ts.map +0 -1
  165. package/dist/types/styling/SemanticStyles.d.ts +0 -178
  166. package/dist/types/styling/SemanticStyles.d.ts.map +0 -1
  167. package/dist/types/styling/SmartPresets.d.ts +0 -22
  168. package/dist/types/styling/SmartPresets.d.ts.map +0 -1
  169. package/dist/types/styling/StyleBuilder.d.ts +0 -140
  170. package/dist/types/styling/StyleBuilder.d.ts.map +0 -1
  171. package/dist/types/styling/banners.d.ts +0 -42
  172. package/dist/types/styling/banners.d.ts.map +0 -1
  173. package/dist/types/styling/index.d.ts +0 -10
  174. package/dist/types/styling/index.d.ts.map +0 -1
  175. package/dist/types/styling/themes.d.ts +0 -7
  176. package/dist/types/styling/themes.d.ts.map +0 -1
  177. package/dist/types/styling-module.d.ts +0 -178
  178. package/dist/types/styling-module.d.ts.map +0 -1
  179. package/dist/types/types/core.d.ts +0 -221
  180. package/dist/types/types/core.d.ts.map +0 -1
  181. package/dist/types/types/handlers.d.ts +0 -85
  182. package/dist/types/types/handlers.d.ts.map +0 -1
  183. package/dist/types/types/index.d.ts +0 -7
  184. package/dist/types/types/index.d.ts.map +0 -1
  185. package/dist/types/utils/environment.d.ts +0 -47
  186. package/dist/types/utils/environment.d.ts.map +0 -1
  187. package/dist/types/utils/formatting.d.ts +0 -37
  188. package/dist/types/utils/formatting.d.ts.map +0 -1
  189. package/dist/types/utils/index.d.ts +0 -7
  190. package/dist/types/utils/index.d.ts.map +0 -1
  191. package/dist/types/utils/opentui-detection.d.ts +0 -34
  192. package/dist/types/utils/opentui-detection.d.ts.map +0 -1
  193. package/dist/types/utils/output.d.ts +0 -41
  194. package/dist/types/utils/output.d.ts.map +0 -1
  195. package/dist/types/utils/stackTrace.d.ts +0 -6
  196. package/dist/types/utils/stackTrace.d.ts.map +0 -1
  197. package/dist/types/utils/timestamps.d.ts +0 -20
  198. package/dist/types/utils/timestamps.d.ts.map +0 -1
  199. package/dist/utils/environment.js +0 -85
  200. package/dist/utils/formatting.js +0 -117
  201. package/dist/utils/index.js +0 -6
  202. package/dist/utils/opentui-detection.js +0 -116
  203. package/dist/utils/output.js +0 -150
  204. package/dist/utils/stackTrace.js +0 -81
  205. package/dist/utils/timestamps.js +0 -71
package/src/core.ts CHANGED
@@ -25,10 +25,13 @@ import {
25
25
  // Universal formatting and environment detection
26
26
  import {
27
27
  createPlainOutput,
28
+ createOutput,
28
29
  getConsoleMethod,
29
30
  createLogEntry,
30
31
  formatTablePlain,
31
- safeSerialize
32
+ safeSerialize,
33
+ detectOptimalFormat,
34
+ type OutputFormat
32
35
  } from './utils/formatting.js';
33
36
 
34
37
  import {
@@ -75,7 +78,8 @@ export class CoreLogger {
75
78
  enableColors: config.enableColors ?? (isBrowser ? true : false),
76
79
  enableTimestamps: config.enableTimestamps ?? true,
77
80
  enableStackTrace: config.enableStackTrace ?? false,
78
- autoDetectTheme: config.autoDetectTheme ?? true
81
+ autoDetectTheme: config.autoDetectTheme ?? true,
82
+ outputFormat: config.outputFormat ?? 'auto'
79
83
  };
80
84
  }
81
85
 
@@ -148,7 +152,7 @@ export class CoreLogger {
148
152
  const message = String(args[0] || '');
149
153
  const stackInfo = this.config.enableStackTrace ? parseStackTrace() : null;
150
154
  const consoleMethod = getConsoleMethod(level);
151
-
155
+
152
156
  // Choose formatting based on environment and configuration
153
157
  if (isBrowser && this.config.enableColors && supportsCSSColors()) {
154
158
  // Browser with CSS styling
@@ -163,14 +167,14 @@ export class CoreLogger {
163
167
  );
164
168
  console[consoleMethod](format, ...styles, ...args.slice(1));
165
169
  } catch (error) {
166
- // Fallback to plain text if CSS fails
167
- const output = createPlainOutput(level, message, prefix, stackInfo);
170
+ // Fallback to universal formatting if CSS fails
171
+ const output = createOutput(level, message, prefix, stackInfo, this.config.outputFormat);
168
172
  console[consoleMethod](output, ...args.slice(1));
169
173
  }
170
174
  } else {
171
- // Node.js or browser without colors - use plain text
175
+ // Node.js or browser without colors - use universal formatting
172
176
  const groupIndent = ' '.repeat(this.groupDepth);
173
- const output = groupIndent + createPlainOutput(level, message, prefix, stackInfo);
177
+ const output = groupIndent + createOutput(level, message, prefix, stackInfo, this.config.outputFormat);
174
178
  console[consoleMethod](output, ...args.slice(1));
175
179
  }
176
180
 
@@ -13,7 +13,8 @@ import type {
13
13
  BufferStats,
14
14
  ExportFormat
15
15
  } from '../types/index.js';
16
- import { parseTimeInput, formatDisplayTime, safeStringify, escapeHtml, generateLogId } from '../utils/index.js';
16
+ import { parseTimeInput, formatDisplayTime } from '../utils/timestamps.js';
17
+ import { safeStringify, escapeHtml, generateLogId } from '../utils/output.js';
17
18
  import { BUFFER_LIMITS } from '../constants.js';
18
19
 
19
20
  /**
package/src/index.ts CHANGED
@@ -21,8 +21,15 @@ import type {
21
21
  ILogHandler
22
22
  } from './types/index.js';
23
23
 
24
- // Create singleton instance with all features enabled
25
- const logger = new Logger();
24
+ // Lazy singleton - se inicializa solo cuando se necesita
25
+ let _logger: Logger | null = null;
26
+
27
+ function getLogger(): Logger {
28
+ if (!_logger) {
29
+ _logger = new Logger();
30
+ }
31
+ return _logger;
32
+ }
26
33
 
27
34
  /**
28
35
  * Clase principal Logger con conjunto completo de características
@@ -63,7 +70,7 @@ export { Logger };
63
70
  * logger.warn('Memoria al 80%');
64
71
  * logger.error('Fallo en conexión');
65
72
  */
66
- export default logger;
73
+ export default getLogger();
67
74
 
68
75
  /**
69
76
  * Métodos de logging individuales (enlazados al singleton)
@@ -78,30 +85,30 @@ export default logger;
78
85
  *
79
86
  * @since 0.3.0
80
87
  */
81
- export const debug = (...args: any[]) => logger.debug(...args);
82
- export const info = (...args: any[]) => logger.info(...args);
83
- export const warn = (...args: any[]) => logger.warn(...args);
84
- export const error = (...args: any[]) => logger.error(...args);
85
- export const success = (...args: any[]) => logger.success(...args);
86
- export const critical = (...args: any[]) => logger.critical(...args);
87
- export const trace = (...args: any[]) => logger.trace(...args);
88
- export const table = (data: any, columns?: string[]) => logger.table(data, columns);
89
- export const group = (label: string, collapsed?: boolean) => logger.group(label, collapsed);
90
- export const groupEnd = () => logger.groupEnd();
91
- export const time = (label: string) => logger.time(label);
92
- export const timeEnd = (label: string) => logger.timeEnd(label);
93
- export const setGlobalPrefix = (prefix: string) => logger.setGlobalPrefix(prefix);
94
- export const scope = (prefix: string) => logger.scope(prefix);
95
- export const setVerbosity = (level: Verbosity) => logger.setVerbosity(level);
96
- export const addHandler = (handler: ILogHandler) => logger.addHandler(handler);
97
- export const setTheme = (theme: ThemeVariant) => logger.setTheme(theme);
98
- export const setBannerType = (bannerType: BannerType) => logger.setBannerType(bannerType);
99
- export const showBanner = (bannerType?: BannerType) => logger.showBanner(bannerType);
88
+ export const debug = (...args: any[]) => getLogger().debug(...args);
89
+ export const info = (...args: any[]) => getLogger().info(...args);
90
+ export const warn = (...args: any[]) => getLogger().warn(...args);
91
+ export const error = (...args: any[]) => getLogger().error(...args);
92
+ export const success = (...args: any[]) => getLogger().success(...args);
93
+ export const critical = (...args: any[]) => getLogger().critical(...args);
94
+ export const trace = (...args: any[]) => getLogger().trace(...args);
95
+ export const table = (data: any, columns?: string[]) => getLogger().table(data, columns);
96
+ export const group = (label: string, collapsed?: boolean) => getLogger().group(label, collapsed);
97
+ export const groupEnd = () => getLogger().groupEnd();
98
+ export const time = (label: string) => getLogger().time(label);
99
+ export const timeEnd = (label: string) => getLogger().timeEnd(label);
100
+ export const setGlobalPrefix = (prefix: string) => getLogger().setGlobalPrefix(prefix);
101
+ export const scope = (prefix: string) => getLogger().scope(prefix);
102
+ export const setVerbosity = (level: Verbosity) => getLogger().setVerbosity(level);
103
+ export const addHandler = (handler: ILogHandler) => getLogger().addHandler(handler);
104
+ export const setTheme = (theme: ThemeVariant) => getLogger().setTheme(theme);
105
+ export const setBannerType = (bannerType: BannerType) => getLogger().setBannerType(bannerType);
106
+ export const showBanner = (bannerType?: BannerType) => getLogger().showBanner(bannerType);
100
107
  export const logWithSVG = (message: string, svgContent?: string, options?: StyleOptions) =>
101
- logger.logWithSVG(message, svgContent, options);
108
+ getLogger().logWithSVG(message, svgContent, options);
102
109
  export const logAnimated = (message: string, duration?: number) =>
103
- logger.logAnimated(message, duration);
104
- export const cli = (command: string) => logger.cli(command);
110
+ getLogger().logAnimated(message, duration);
111
+ export const cli = (command: string) => getLogger().cli(command);
105
112
 
106
113
  // Type exports
107
114
  export type {
@@ -114,7 +121,8 @@ export type {
114
121
  LoggerConfig,
115
122
  LogMetadata,
116
123
  StackInfo,
117
- TimerEntry
124
+ TimerEntry,
125
+ OutputFormat
118
126
  } from './types/index.js';
119
127
 
120
128
  // Styling utilities
@@ -139,9 +147,36 @@ export { DEFAULT_CONFIG } from './constants.js';
139
147
  // Utility exports
140
148
  export {
141
149
  parseStackTrace,
142
- formatTimestamp
150
+ formatTimestamp,
151
+ detectOptimalFormat,
152
+ createOutput,
153
+ createANSIOutput,
154
+ createBuildOutput,
155
+ createCIOutput
143
156
  } from './utils/index.js';
144
157
 
158
+ // ANSI color utilities
159
+ export {
160
+ ansiStyle,
161
+ ansiColor,
162
+ ansiBackground,
163
+ ansiBold,
164
+ ansiDim,
165
+ ansiUnderline,
166
+ formatLogLevelANSI,
167
+ formatSuccessANSI,
168
+ BUILD_FORMATTERS,
169
+ sanitizeEmojis
170
+ } from './utils/ansi-colors.js';
171
+
172
+ // Environment detection and presets
173
+ export {
174
+ BUILD_PRESETS,
175
+ ENVIRONMENT_DETECTION,
176
+ detectEnvironmentPreset,
177
+ getOptimalConfig
178
+ } from './constants.js';
179
+
145
180
  /**
146
181
  * Utilidades de estilo para crear estilos personalizados de consola
147
182
  *
@@ -5,7 +5,7 @@
5
5
  import { StyleBuilder } from './StyleBuilder.js';
6
6
  import type { AdaptiveColors } from '../types/index.js';
7
7
  import { ADAPTIVE_COLORS } from '../constants.js';
8
- import { getAdaptiveColor } from '../utils/index.js';
8
+ import { getAdaptiveColor } from '../utils/output.js';
9
9
 
10
10
  /**
11
11
  * Base semantic styler with common style methods
package/src/types/core.ts CHANGED
@@ -77,7 +77,7 @@ export type BannerType = 'simple' | 'ascii' | 'unicode' | 'svg' | 'animated';
77
77
  /**
78
78
  * Formatos de exportación para datos de log
79
79
  * @typedef {'json' | 'csv' | 'markdown' | 'plain' | 'html'} ExportFormat
80
- *
80
+ *
81
81
  * @description
82
82
  * - json: Formato JSON estructurado
83
83
  * - csv: Valores separados por comas para Excel/Sheets
@@ -87,6 +87,19 @@ export type BannerType = 'simple' | 'ascii' | 'unicode' | 'svg' | 'animated';
87
87
  */
88
88
  export type ExportFormat = 'json' | 'csv' | 'markdown' | 'plain' | 'html';
89
89
 
90
+ /**
91
+ * Formatos de salida para diferentes entornos
92
+ * @typedef {'auto' | 'plain' | 'ansi' | 'build' | 'ci'} OutputFormat
93
+ *
94
+ * @description
95
+ * - auto: Detección automática basada en entorno (recomendado)
96
+ * - plain: Texto plano sin colores (máxima compatibilidad)
97
+ * - ansi: Colores ANSI para terminales modernos
98
+ * - build: Formato optimizado para builds (Next.js, webpack, etc.)
99
+ * - ci: Formato optimizado para CI/CD (sin emojis, texto simple)
100
+ */
101
+ export type OutputFormat = 'auto' | 'plain' | 'ansi' | 'build' | 'ci';
102
+
90
103
  /**
91
104
  * Interfaz de configuración para instancias del logger
92
105
  *
@@ -116,6 +129,7 @@ export interface LoggerConfig {
116
129
  bannerType?: BannerType;
117
130
  bufferSize?: number;
118
131
  autoDetectTheme?: boolean;
132
+ outputFormat?: OutputFormat;
119
133
  }
120
134
 
121
135
  /**
@@ -10,6 +10,7 @@ export type {
10
10
  DevToolsTheme,
11
11
  BannerType,
12
12
  ExportFormat,
13
+ OutputFormat,
13
14
  LoggerConfig,
14
15
  StackInfo,
15
16
  TimerEntry,
@@ -0,0 +1,333 @@
1
+ /**
2
+ * @fileoverview ANSI color utilities for terminal environments
3
+ * @since 1.0.0
4
+ */
5
+
6
+ import type { LogLevel } from '../types/index.js';
7
+ import { supportsANSIColors } from './environment.js';
8
+
9
+ /**
10
+ * ANSI color codes for terminal styling
11
+ */
12
+ export const ANSI_CODES = {
13
+ // Colors
14
+ black: 30,
15
+ red: 31,
16
+ green: 32,
17
+ yellow: 33,
18
+ blue: 34,
19
+ magenta: 35,
20
+ cyan: 36,
21
+ white: 37,
22
+
23
+ // Bright colors
24
+ brightBlack: 90,
25
+ brightRed: 91,
26
+ brightGreen: 92,
27
+ brightYellow: 93,
28
+ brightBlue: 94,
29
+ brightMagenta: 95,
30
+ brightCyan: 96,
31
+ brightWhite: 97,
32
+
33
+ // Background colors
34
+ bgBlack: 40,
35
+ bgRed: 41,
36
+ bgGreen: 42,
37
+ bgYellow: 43,
38
+ bgBlue: 44,
39
+ bgMagenta: 45,
40
+ bgCyan: 46,
41
+ bgWhite: 47,
42
+
43
+ // Background bright colors
44
+ bgBrightBlack: 100,
45
+ bgBrightRed: 101,
46
+ bgBrightGreen: 102,
47
+ bgBrightYellow: 103,
48
+ bgBrightBlue: 104,
49
+ bgBrightMagenta: 105,
50
+ bgBrightCyan: 106,
51
+ bgBrightWhite: 107,
52
+
53
+ // Styles
54
+ reset: 0,
55
+ bold: 1,
56
+ dim: 2,
57
+ italic: 3,
58
+ underline: 4,
59
+ blink: 5,
60
+ inverse: 7,
61
+ hidden: 8,
62
+ strikethrough: 9,
63
+
64
+ // Reset specific
65
+ resetBold: 22,
66
+ resetDim: 22,
67
+ resetItalic: 23,
68
+ resetUnderline: 24,
69
+ resetBlink: 25,
70
+ resetInverse: 27,
71
+ resetHidden: 28,
72
+ resetStrikethrough: 29
73
+ } as const;
74
+
75
+ /**
76
+ * ANSI color presets for different log levels
77
+ */
78
+ export const ANSI_LEVEL_STYLES: Record<LogLevel | 'success', {
79
+ color: number;
80
+ background?: number;
81
+ styles: number[];
82
+ emoji: string;
83
+ }> = {
84
+ debug: {
85
+ color: ANSI_CODES.brightBlack,
86
+ styles: [ANSI_CODES.dim],
87
+ emoji: '🔍'
88
+ },
89
+ info: {
90
+ color: ANSI_CODES.blue,
91
+ styles: [ANSI_CODES.bold],
92
+ emoji: 'ℹ️'
93
+ },
94
+ warn: {
95
+ color: ANSI_CODES.yellow,
96
+ background: ANSI_CODES.bgYellow,
97
+ styles: [ANSI_CODES.bold, ANSI_CODES.black],
98
+ emoji: '⚠️'
99
+ },
100
+ error: {
101
+ color: ANSI_CODES.red,
102
+ background: ANSI_CODES.bgRed,
103
+ styles: [ANSI_CODES.bold],
104
+ emoji: '❌'
105
+ },
106
+ critical: {
107
+ color: ANSI_CODES.white,
108
+ background: ANSI_CODES.bgRed,
109
+ styles: [ANSI_CODES.bold, ANSI_CODES.blink],
110
+ emoji: '🚨'
111
+ },
112
+ success: {
113
+ color: ANSI_CODES.green,
114
+ background: ANSI_CODES.bgGreen,
115
+ styles: [ANSI_CODES.bold],
116
+ emoji: '✅'
117
+ }
118
+ };
119
+
120
+ /**
121
+ * Creates an ANSI escape sequence
122
+ */
123
+ function ansi(code: number | number[]): string {
124
+ const codes = Array.isArray(code) ? code : [code];
125
+ return `\x1b[${codes.join(';')}m`;
126
+ }
127
+
128
+ /**
129
+ * Applies ANSI styling to text
130
+ */
131
+ export function ansiStyle(text: string, codes: number[]): string {
132
+ if (!supportsANSIColors()) return text;
133
+ return `${ansi(codes)}${text}${ansi(ANSI_CODES.reset)}`;
134
+ }
135
+
136
+ /**
137
+ * Applies color to text
138
+ */
139
+ export function ansiColor(text: string, color: number): string {
140
+ return ansiStyle(text, [color]);
141
+ }
142
+
143
+ /**
144
+ * Applies background color to text
145
+ */
146
+ export function ansiBackground(text: string, bg: number, color?: number): string {
147
+ if (color) {
148
+ return ansiStyle(text, [color, bg]);
149
+ }
150
+ return ansiStyle(text, [bg]);
151
+ }
152
+
153
+ /**
154
+ * Makes text bold
155
+ */
156
+ export function ansiBold(text: string): string {
157
+ return ansiStyle(text, [ANSI_CODES.bold]);
158
+ }
159
+
160
+ /**
161
+ * Makes text dim
162
+ */
163
+ export function ansiDim(text: string): string {
164
+ return ansiStyle(text, [ANSI_CODES.dim]);
165
+ }
166
+
167
+ /**
168
+ * Underlines text
169
+ */
170
+ export function ansiUnderline(text: string): string {
171
+ return ansiStyle(text, [ANSI_CODES.underline]);
172
+ }
173
+
174
+ /**
175
+ * Specialized formatters for different contexts
176
+ */
177
+
178
+ /**
179
+ * Format timestamp for terminal
180
+ */
181
+ export function formatTimestampANSI(timestamp: string): string {
182
+ return ansiColor(timestamp, ANSI_CODES.brightBlack);
183
+ }
184
+
185
+ /**
186
+ * Format log level for terminal
187
+ */
188
+ export function formatLogLevelANSI(level: LogLevel, useEmojis: boolean = true): string {
189
+ const style = ANSI_LEVEL_STYLES[level];
190
+ const emoji = useEmojis ? style.emoji : '';
191
+ const label = level.toUpperCase().padEnd(8);
192
+
193
+ if (!supportsANSIColors()) {
194
+ return `${emoji} ${label}`;
195
+ }
196
+
197
+ let codes = [style.color, ...style.styles];
198
+ if (style.background) {
199
+ codes.push(style.background);
200
+ }
201
+
202
+ return ansiStyle(`${emoji} ${label}`, codes);
203
+ }
204
+
205
+ /**
206
+ * Format success message for terminal
207
+ */
208
+ export function formatSuccessANSI(message: string, useEmojis: boolean = true): string {
209
+ const style = ANSI_LEVEL_STYLES.success;
210
+ const emoji = useEmojis ? style.emoji : '';
211
+
212
+ if (!supportsANSIColors()) {
213
+ return `${emoji} SUCCESS: ${message}`;
214
+ }
215
+
216
+ const prefix = ansiStyle(`${emoji} SUCCESS:`, [style.color, ...style.styles]);
217
+ return `${prefix} ${message}`;
218
+ }
219
+
220
+ /**
221
+ * Format prefix for terminal
222
+ */
223
+ export function formatPrefixANSI(prefix: string): string {
224
+ if (!supportsANSIColors()) {
225
+ return `[${prefix}]`;
226
+ }
227
+
228
+ return ansiStyle(`[${prefix}]`, [ANSI_CODES.cyan, ANSI_CODES.bold]);
229
+ }
230
+
231
+ /**
232
+ * Format file location for terminal
233
+ */
234
+ export function formatLocationANSI(location: string): string {
235
+ if (!supportsANSIColors()) {
236
+ return `(${location})`;
237
+ }
238
+
239
+ return ansiColor(`(${location})`, ANSI_CODES.brightBlack);
240
+ }
241
+
242
+ /**
243
+ * Format build-specific messages
244
+ */
245
+ export const BUILD_FORMATTERS = {
246
+ /**
247
+ * Format compilation step
248
+ */
249
+ compilation: (step: string, status: 'starting' | 'completed' | 'failed' = 'starting') => {
250
+ const stepText = ansiBold(step);
251
+
252
+ switch (status) {
253
+ case 'starting':
254
+ return `${ansiColor('⚙️', ANSI_CODES.blue)} ${stepText}...`;
255
+ case 'completed':
256
+ return `${ansiColor('✓', ANSI_CODES.green)} ${stepText} ${ansiColor('completed', ANSI_CODES.green)}`;
257
+ case 'failed':
258
+ return `${ansiColor('✗', ANSI_CODES.red)} ${stepText} ${ansiColor('failed', ANSI_CODES.red)}`;
259
+ default:
260
+ return stepText;
261
+ }
262
+ },
263
+
264
+ /**
265
+ * Format warning message
266
+ */
267
+ warning: (message: string) => {
268
+ return `${ansiColor('⚠', ANSI_CODES.yellow)} ${ansiStyle('Warning:', [ANSI_CODES.yellow, ANSI_CODES.bold])} ${message}`;
269
+ },
270
+
271
+ /**
272
+ * Format error message
273
+ */
274
+ error: (message: string) => {
275
+ return `${ansiColor('✗', ANSI_CODES.red)} ${ansiStyle('Error:', [ANSI_CODES.red, ANSI_CODES.bold])} ${message}`;
276
+ },
277
+
278
+ /**
279
+ * Format success message
280
+ */
281
+ success: (message: string) => {
282
+ return `${ansiColor('✓', ANSI_CODES.green)} ${ansiColor(message, ANSI_CODES.green)}`;
283
+ },
284
+
285
+ /**
286
+ * Format info message
287
+ */
288
+ info: (message: string) => {
289
+ return `${ansiColor('ℹ', ANSI_CODES.blue)} ${message}`;
290
+ }
291
+ };
292
+
293
+ /**
294
+ * Terminal-friendly emoji alternatives for environments that don't support them
295
+ */
296
+ export const EMOJI_ALTERNATIVES = {
297
+ '🔍': '[DEBUG]',
298
+ 'ℹ️': '[INFO]',
299
+ '⚠️': '[WARN]',
300
+ '❌': '[ERROR]',
301
+ '🚨': '[CRITICAL]',
302
+ '✅': '[OK]',
303
+ '✓': '[OK]',
304
+ '✗': '[FAIL]',
305
+ '⚙️': '[BUILD]',
306
+ '📦': '[PKG]'
307
+ };
308
+
309
+ /**
310
+ * Replace emojis with text alternatives for non-emoji terminals
311
+ */
312
+ export function sanitizeEmojis(text: string): string {
313
+ // Check if we're in a terminal that likely supports emojis
314
+ const isModernTerminal = process.env.TERM &&
315
+ (process.env.TERM.includes('xterm') ||
316
+ process.env.TERM.includes('screen') ||
317
+ process.env.TERM.includes('tmux'));
318
+
319
+ const isCI = process.env.CI || process.env.GITHUB_ACTIONS || process.env.JENKINS_URL;
320
+
321
+ // Use emojis if we have a modern terminal and not in CI
322
+ if (isModernTerminal && !isCI) {
323
+ return text;
324
+ }
325
+
326
+ // Replace emojis with text alternatives
327
+ let result = text;
328
+ Object.entries(EMOJI_ALTERNATIVES).forEach(([emoji, alt]) => {
329
+ result = result.replace(new RegExp(emoji, 'g'), alt);
330
+ });
331
+
332
+ return result;
333
+ }