@litmers/cursorflow-orchestrator 0.1.20 → 0.1.26

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 (224) hide show
  1. package/CHANGELOG.md +9 -0
  2. package/commands/cursorflow-clean.md +19 -0
  3. package/commands/cursorflow-runs.md +59 -0
  4. package/commands/cursorflow-stop.md +55 -0
  5. package/dist/cli/clean.js +171 -0
  6. package/dist/cli/clean.js.map +1 -1
  7. package/dist/cli/index.js +7 -0
  8. package/dist/cli/index.js.map +1 -1
  9. package/dist/cli/init.js +1 -1
  10. package/dist/cli/init.js.map +1 -1
  11. package/dist/cli/logs.js +83 -42
  12. package/dist/cli/logs.js.map +1 -1
  13. package/dist/cli/monitor.d.ts +7 -0
  14. package/dist/cli/monitor.js +1007 -189
  15. package/dist/cli/monitor.js.map +1 -1
  16. package/dist/cli/prepare.js +4 -3
  17. package/dist/cli/prepare.js.map +1 -1
  18. package/dist/cli/resume.js +188 -236
  19. package/dist/cli/resume.js.map +1 -1
  20. package/dist/cli/run.js +8 -3
  21. package/dist/cli/run.js.map +1 -1
  22. package/dist/cli/runs.d.ts +5 -0
  23. package/dist/cli/runs.js +214 -0
  24. package/dist/cli/runs.js.map +1 -0
  25. package/dist/cli/setup-commands.js +0 -0
  26. package/dist/cli/signal.js +1 -1
  27. package/dist/cli/signal.js.map +1 -1
  28. package/dist/cli/stop.d.ts +5 -0
  29. package/dist/cli/stop.js +215 -0
  30. package/dist/cli/stop.js.map +1 -0
  31. package/dist/cli/tasks.d.ts +10 -0
  32. package/dist/cli/tasks.js +165 -0
  33. package/dist/cli/tasks.js.map +1 -0
  34. package/dist/core/auto-recovery.d.ts +212 -0
  35. package/dist/core/auto-recovery.js +737 -0
  36. package/dist/core/auto-recovery.js.map +1 -0
  37. package/dist/core/failure-policy.d.ts +156 -0
  38. package/dist/core/failure-policy.js +488 -0
  39. package/dist/core/failure-policy.js.map +1 -0
  40. package/dist/core/orchestrator.d.ts +15 -2
  41. package/dist/core/orchestrator.js +392 -15
  42. package/dist/core/orchestrator.js.map +1 -1
  43. package/dist/core/reviewer.d.ts +2 -0
  44. package/dist/core/reviewer.js +2 -0
  45. package/dist/core/reviewer.js.map +1 -1
  46. package/dist/core/runner.d.ts +33 -10
  47. package/dist/core/runner.js +321 -146
  48. package/dist/core/runner.js.map +1 -1
  49. package/dist/services/logging/buffer.d.ts +67 -0
  50. package/dist/services/logging/buffer.js +309 -0
  51. package/dist/services/logging/buffer.js.map +1 -0
  52. package/dist/services/logging/console.d.ts +89 -0
  53. package/dist/services/logging/console.js +169 -0
  54. package/dist/services/logging/console.js.map +1 -0
  55. package/dist/services/logging/file-writer.d.ts +71 -0
  56. package/dist/services/logging/file-writer.js +516 -0
  57. package/dist/services/logging/file-writer.js.map +1 -0
  58. package/dist/services/logging/formatter.d.ts +39 -0
  59. package/dist/services/logging/formatter.js +227 -0
  60. package/dist/services/logging/formatter.js.map +1 -0
  61. package/dist/services/logging/index.d.ts +11 -0
  62. package/dist/services/logging/index.js +30 -0
  63. package/dist/services/logging/index.js.map +1 -0
  64. package/dist/services/logging/parser.d.ts +31 -0
  65. package/dist/services/logging/parser.js +222 -0
  66. package/dist/services/logging/parser.js.map +1 -0
  67. package/dist/services/process/index.d.ts +59 -0
  68. package/dist/services/process/index.js +257 -0
  69. package/dist/services/process/index.js.map +1 -0
  70. package/dist/types/agent.d.ts +20 -0
  71. package/dist/types/agent.js +6 -0
  72. package/dist/types/agent.js.map +1 -0
  73. package/dist/types/config.d.ts +65 -0
  74. package/dist/types/config.js +6 -0
  75. package/dist/types/config.js.map +1 -0
  76. package/dist/types/events.d.ts +125 -0
  77. package/dist/types/events.js +6 -0
  78. package/dist/types/events.js.map +1 -0
  79. package/dist/types/index.d.ts +12 -0
  80. package/dist/types/index.js +37 -0
  81. package/dist/types/index.js.map +1 -0
  82. package/dist/types/lane.d.ts +43 -0
  83. package/dist/types/lane.js +6 -0
  84. package/dist/types/lane.js.map +1 -0
  85. package/dist/types/logging.d.ts +71 -0
  86. package/dist/types/logging.js +16 -0
  87. package/dist/types/logging.js.map +1 -0
  88. package/dist/types/review.d.ts +17 -0
  89. package/dist/types/review.js +6 -0
  90. package/dist/types/review.js.map +1 -0
  91. package/dist/types/run.d.ts +32 -0
  92. package/dist/types/run.js +6 -0
  93. package/dist/types/run.js.map +1 -0
  94. package/dist/types/task.d.ts +71 -0
  95. package/dist/types/task.js +6 -0
  96. package/dist/types/task.js.map +1 -0
  97. package/dist/ui/components.d.ts +134 -0
  98. package/dist/ui/components.js +389 -0
  99. package/dist/ui/components.js.map +1 -0
  100. package/dist/ui/log-viewer.d.ts +49 -0
  101. package/dist/ui/log-viewer.js +449 -0
  102. package/dist/ui/log-viewer.js.map +1 -0
  103. package/dist/utils/checkpoint.d.ts +87 -0
  104. package/dist/utils/checkpoint.js +317 -0
  105. package/dist/utils/checkpoint.js.map +1 -0
  106. package/dist/utils/config.d.ts +4 -0
  107. package/dist/utils/config.js +11 -2
  108. package/dist/utils/config.js.map +1 -1
  109. package/dist/utils/cursor-agent.js.map +1 -1
  110. package/dist/utils/dependency.d.ts +74 -0
  111. package/dist/utils/dependency.js +420 -0
  112. package/dist/utils/dependency.js.map +1 -0
  113. package/dist/utils/doctor.js +10 -5
  114. package/dist/utils/doctor.js.map +1 -1
  115. package/dist/utils/enhanced-logger.d.ts +10 -33
  116. package/dist/utils/enhanced-logger.js +94 -9
  117. package/dist/utils/enhanced-logger.js.map +1 -1
  118. package/dist/utils/git.d.ts +121 -0
  119. package/dist/utils/git.js +322 -2
  120. package/dist/utils/git.js.map +1 -1
  121. package/dist/utils/health.d.ts +91 -0
  122. package/dist/utils/health.js +556 -0
  123. package/dist/utils/health.js.map +1 -0
  124. package/dist/utils/lock.d.ts +95 -0
  125. package/dist/utils/lock.js +332 -0
  126. package/dist/utils/lock.js.map +1 -0
  127. package/dist/utils/log-buffer.d.ts +17 -0
  128. package/dist/utils/log-buffer.js +14 -0
  129. package/dist/utils/log-buffer.js.map +1 -0
  130. package/dist/utils/log-constants.d.ts +23 -0
  131. package/dist/utils/log-constants.js +28 -0
  132. package/dist/utils/log-constants.js.map +1 -0
  133. package/dist/utils/log-formatter.d.ts +9 -0
  134. package/dist/utils/log-formatter.js +113 -70
  135. package/dist/utils/log-formatter.js.map +1 -1
  136. package/dist/utils/log-service.d.ts +19 -0
  137. package/dist/utils/log-service.js +47 -0
  138. package/dist/utils/log-service.js.map +1 -0
  139. package/dist/utils/logger.d.ts +46 -27
  140. package/dist/utils/logger.js +82 -60
  141. package/dist/utils/logger.js.map +1 -1
  142. package/dist/utils/process-manager.d.ts +21 -0
  143. package/dist/utils/process-manager.js +138 -0
  144. package/dist/utils/process-manager.js.map +1 -0
  145. package/dist/utils/retry.d.ts +121 -0
  146. package/dist/utils/retry.js +374 -0
  147. package/dist/utils/retry.js.map +1 -0
  148. package/dist/utils/run-service.d.ts +88 -0
  149. package/dist/utils/run-service.js +412 -0
  150. package/dist/utils/run-service.js.map +1 -0
  151. package/dist/utils/state.d.ts +58 -2
  152. package/dist/utils/state.js +306 -3
  153. package/dist/utils/state.js.map +1 -1
  154. package/dist/utils/task-service.d.ts +82 -0
  155. package/dist/utils/task-service.js +348 -0
  156. package/dist/utils/task-service.js.map +1 -0
  157. package/dist/utils/types.d.ts +2 -272
  158. package/dist/utils/types.js +16 -0
  159. package/dist/utils/types.js.map +1 -1
  160. package/package.json +38 -23
  161. package/scripts/ai-security-check.js +0 -1
  162. package/scripts/local-security-gate.sh +0 -0
  163. package/scripts/monitor-lanes.sh +94 -0
  164. package/scripts/patches/test-cursor-agent.js +0 -1
  165. package/scripts/release.sh +0 -0
  166. package/scripts/setup-security.sh +0 -0
  167. package/scripts/stream-logs.sh +72 -0
  168. package/scripts/verify-and-fix.sh +0 -0
  169. package/src/cli/clean.ts +180 -0
  170. package/src/cli/index.ts +7 -0
  171. package/src/cli/init.ts +1 -1
  172. package/src/cli/logs.ts +79 -42
  173. package/src/cli/monitor.ts +1815 -899
  174. package/src/cli/prepare.ts +4 -3
  175. package/src/cli/resume.ts +220 -277
  176. package/src/cli/run.ts +9 -3
  177. package/src/cli/runs.ts +212 -0
  178. package/src/cli/setup-commands.ts +0 -0
  179. package/src/cli/signal.ts +1 -1
  180. package/src/cli/stop.ts +209 -0
  181. package/src/cli/tasks.ts +154 -0
  182. package/src/core/auto-recovery.ts +909 -0
  183. package/src/core/failure-policy.ts +592 -0
  184. package/src/core/orchestrator.ts +1131 -675
  185. package/src/core/reviewer.ts +4 -0
  186. package/src/core/runner.ts +388 -162
  187. package/src/services/logging/buffer.ts +326 -0
  188. package/src/services/logging/console.ts +193 -0
  189. package/src/services/logging/file-writer.ts +526 -0
  190. package/src/services/logging/formatter.ts +268 -0
  191. package/src/services/logging/index.ts +16 -0
  192. package/src/services/logging/parser.ts +232 -0
  193. package/src/services/process/index.ts +261 -0
  194. package/src/types/agent.ts +24 -0
  195. package/src/types/config.ts +79 -0
  196. package/src/types/events.ts +156 -0
  197. package/src/types/index.ts +29 -0
  198. package/src/types/lane.ts +56 -0
  199. package/src/types/logging.ts +96 -0
  200. package/src/types/review.ts +20 -0
  201. package/src/types/run.ts +37 -0
  202. package/src/types/task.ts +79 -0
  203. package/src/ui/components.ts +430 -0
  204. package/src/ui/log-viewer.ts +485 -0
  205. package/src/utils/checkpoint.ts +374 -0
  206. package/src/utils/config.ts +11 -2
  207. package/src/utils/cursor-agent.ts +1 -1
  208. package/src/utils/dependency.ts +482 -0
  209. package/src/utils/doctor.ts +11 -5
  210. package/src/utils/enhanced-logger.ts +108 -49
  211. package/src/utils/git.ts +374 -2
  212. package/src/utils/health.ts +596 -0
  213. package/src/utils/lock.ts +346 -0
  214. package/src/utils/log-buffer.ts +28 -0
  215. package/src/utils/log-constants.ts +26 -0
  216. package/src/utils/log-formatter.ts +120 -37
  217. package/src/utils/log-service.ts +49 -0
  218. package/src/utils/logger.ts +100 -51
  219. package/src/utils/process-manager.ts +100 -0
  220. package/src/utils/retry.ts +413 -0
  221. package/src/utils/run-service.ts +433 -0
  222. package/src/utils/state.ts +369 -3
  223. package/src/utils/task-service.ts +370 -0
  224. package/src/utils/types.ts +2 -315
@@ -1,84 +1,102 @@
1
1
  "use strict";
2
2
  /**
3
3
  * Utility for formatting log messages for console display
4
+ *
5
+ * Format: [HH:MM:SS] [lane-task] ICON TYPE content
6
+ *
7
+ * Rules:
8
+ * - Box format only for: user, assistant, system, result
9
+ * - Compact format for: tool, tool_result, thinking (gray/dim)
10
+ * - Tool names simplified: ShellToolCall → Shell
11
+ * - Lane labels max 16 chars: [01-types-tests]
4
12
  */
5
- var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
6
- if (k2 === undefined) k2 = k;
7
- var desc = Object.getOwnPropertyDescriptor(m, k);
8
- if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
9
- desc = { enumerable: true, get: function() { return m[k]; } };
10
- }
11
- Object.defineProperty(o, k2, desc);
12
- }) : (function(o, m, k, k2) {
13
- if (k2 === undefined) k2 = k;
14
- o[k2] = m[k];
15
- }));
16
- var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
17
- Object.defineProperty(o, "default", { enumerable: true, value: v });
18
- }) : function(o, v) {
19
- o["default"] = v;
20
- });
21
- var __importStar = (this && this.__importStar) || (function () {
22
- var ownKeys = function(o) {
23
- ownKeys = Object.getOwnPropertyNames || function (o) {
24
- var ar = [];
25
- for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
26
- return ar;
27
- };
28
- return ownKeys(o);
29
- };
30
- return function (mod) {
31
- if (mod && mod.__esModule) return mod;
32
- var result = {};
33
- if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
34
- __setModuleDefault(result, mod);
35
- return result;
36
- };
37
- })();
38
13
  Object.defineProperty(exports, "__esModule", { value: true });
39
14
  exports.formatMessageForConsole = formatMessageForConsole;
40
15
  exports.formatPotentialJsonMessage = formatPotentialJsonMessage;
41
- const logger = __importStar(require("./logger"));
16
+ const log_constants_1 = require("./log-constants");
42
17
  const enhanced_logger_1 = require("./enhanced-logger");
18
+ // Types that should use box format
19
+ const BOX_TYPES = new Set(['user', 'assistant', 'system', 'result']);
20
+ /**
21
+ * Simplify tool names (ShellToolCall → Shell, etc.)
22
+ */
23
+ function simplifyToolName(name) {
24
+ // Remove common suffixes
25
+ return name
26
+ .replace(/ToolCall$/i, '')
27
+ .replace(/Tool$/i, '')
28
+ .replace(/^run_terminal_cmd$/i, 'shell')
29
+ .replace(/^search_replace$/i, 'edit');
30
+ }
43
31
  /**
44
32
  * Format a single parsed message into a human-readable string (compact or multi-line)
45
33
  */
46
34
  function formatMessageForConsole(msg, options = {}) {
47
- const { includeTimestamp = true, laneLabel = '', compact = false } = options;
35
+ const { includeTimestamp = true, laneLabel = '', compact = false, context = '' } = options;
48
36
  const ts = includeTimestamp ? new Date(msg.timestamp).toLocaleTimeString('en-US', { hour12: false }) : '';
49
- const tsPrefix = ts ? `${logger.COLORS.gray}[${ts}]${logger.COLORS.reset} ` : '';
50
- const labelPrefix = laneLabel ? `${logger.COLORS.magenta}${laneLabel.padEnd(12)}${logger.COLORS.reset} ` : '';
37
+ const tsPrefix = ts ? `${log_constants_1.COLORS.gray}[${ts}]${log_constants_1.COLORS.reset} ` : '';
38
+ // Handle context (e.g. from logger.info) - max 16 chars
39
+ const effectiveLaneLabel = laneLabel || (context ? `[${context}]` : '');
40
+ const truncatedLabel = effectiveLaneLabel.length > 16
41
+ ? effectiveLaneLabel.substring(0, 16)
42
+ : effectiveLaneLabel;
43
+ const labelPrefix = truncatedLabel ? `${log_constants_1.COLORS.magenta}${truncatedLabel.padEnd(16)}${log_constants_1.COLORS.reset} ` : '';
51
44
  let typePrefix = '';
52
45
  let content = msg.content;
46
+ // Determine if we should use box format
47
+ // Box format only for: user, assistant, system, result (and only when not compact)
48
+ const useBox = !compact && BOX_TYPES.has(msg.type);
49
+ // Clean up wrapped prompts for user messages to hide internal instructions
50
+ if (msg.type === 'user') {
51
+ const contextMarker = '### 🛠 Environment & Context';
52
+ const instructionsMarker = '### 📝 Final Instructions';
53
+ if (content.includes(contextMarker)) {
54
+ const parts = content.split('---\n');
55
+ if (parts.length >= 3) {
56
+ content = parts[1].trim();
57
+ }
58
+ else {
59
+ content = content.split(contextMarker).pop() || content;
60
+ content = content.split(instructionsMarker)[0] || content;
61
+ content = content.replace(/^.*---\n/s, '').trim();
62
+ }
63
+ }
64
+ }
65
+ // For thinking: collapse multiple newlines into single space
66
+ if (msg.type === 'thinking') {
67
+ content = content.replace(/\n\s*\n/g, ' ').replace(/\n/g, ' ').trim();
68
+ }
53
69
  switch (msg.type) {
54
70
  case 'user':
55
- typePrefix = `${logger.COLORS.cyan}🧑 USER${logger.COLORS.reset}`;
56
- if (compact)
71
+ typePrefix = `${log_constants_1.COLORS.cyan}🧑 USER${log_constants_1.COLORS.reset}`;
72
+ if (!useBox)
57
73
  content = content.replace(/\n/g, ' ').substring(0, 100) + (content.length > 100 ? '...' : '');
58
74
  break;
59
75
  case 'assistant':
60
- typePrefix = `${logger.COLORS.green}🤖 ASST${logger.COLORS.reset}`;
61
- if (compact)
76
+ typePrefix = `${log_constants_1.COLORS.green}🤖 ASST${log_constants_1.COLORS.reset}`;
77
+ if (!useBox)
62
78
  content = content.replace(/\n/g, ' ').substring(0, 100) + (content.length > 100 ? '...' : '');
63
79
  break;
64
80
  case 'tool':
65
- typePrefix = `${logger.COLORS.yellow}🔧 TOOL${logger.COLORS.reset}`;
81
+ // Tool calls are always compact and gray
82
+ typePrefix = `${log_constants_1.COLORS.gray}🔧 TOOL${log_constants_1.COLORS.reset}`;
66
83
  const toolMatch = content.match(/\[Tool: ([^\]]+)\] (.*)/);
67
84
  if (toolMatch) {
68
- const [, name, args] = toolMatch;
85
+ const [, rawName, args] = toolMatch;
86
+ const name = simplifyToolName(rawName);
69
87
  try {
70
88
  const parsedArgs = JSON.parse(args);
71
89
  let argStr = '';
72
- if (name === 'read_file' && parsedArgs.target_file) {
90
+ if (rawName === 'read_file' && parsedArgs.target_file) {
73
91
  argStr = parsedArgs.target_file;
74
92
  }
75
- else if (name === 'run_terminal_cmd' && parsedArgs.command) {
93
+ else if (rawName === 'run_terminal_cmd' && parsedArgs.command) {
76
94
  argStr = parsedArgs.command;
77
95
  }
78
- else if (name === 'write' && parsedArgs.file_path) {
96
+ else if (rawName === 'write' && parsedArgs.file_path) {
79
97
  argStr = parsedArgs.file_path;
80
98
  }
81
- else if (name === 'search_replace' && parsedArgs.file_path) {
99
+ else if (rawName === 'search_replace' && parsedArgs.file_path) {
82
100
  argStr = parsedArgs.file_path;
83
101
  }
84
102
  else {
@@ -87,45 +105,69 @@ function formatMessageForConsole(msg, options = {}) {
87
105
  argStr = String(parsedArgs[keys[0]]).substring(0, 50);
88
106
  }
89
107
  }
90
- content = `${logger.COLORS.bold}${name}${logger.COLORS.reset}(${argStr})`;
108
+ content = `${log_constants_1.COLORS.gray}${name}${log_constants_1.COLORS.reset}(${log_constants_1.COLORS.gray}${argStr}${log_constants_1.COLORS.reset})`;
91
109
  }
92
110
  catch {
93
- content = `${logger.COLORS.bold}${name}${logger.COLORS.reset}: ${args}`;
111
+ content = `${log_constants_1.COLORS.gray}${name}${log_constants_1.COLORS.reset}: ${args}`;
94
112
  }
95
113
  }
96
114
  break;
97
115
  case 'tool_result':
98
- typePrefix = `${logger.COLORS.gray}📄 RESL${logger.COLORS.reset}`;
116
+ // Tool results are always compact and gray
117
+ typePrefix = `${log_constants_1.COLORS.gray}📄 RESL${log_constants_1.COLORS.reset}`;
99
118
  const resMatch = content.match(/\[Tool Result: ([^\]]+)\]/);
100
- content = resMatch ? `${resMatch[1]} OK` : 'result';
119
+ if (resMatch) {
120
+ const simpleName = simplifyToolName(resMatch[1]);
121
+ content = `${log_constants_1.COLORS.gray}${simpleName} OK${log_constants_1.COLORS.reset}`;
122
+ }
123
+ else {
124
+ content = `${log_constants_1.COLORS.gray}result${log_constants_1.COLORS.reset}`;
125
+ }
101
126
  break;
102
127
  case 'result':
103
- typePrefix = `${logger.COLORS.green}✅ DONE${logger.COLORS.reset}`;
128
+ case 'success':
129
+ typePrefix = `${log_constants_1.COLORS.green}✅ DONE${log_constants_1.COLORS.reset}`;
104
130
  break;
105
131
  case 'system':
106
- typePrefix = `${logger.COLORS.gray}⚙️ SYS${logger.COLORS.reset}`;
132
+ typePrefix = `${log_constants_1.COLORS.gray}⚙️ SYS${log_constants_1.COLORS.reset}`;
107
133
  break;
108
134
  case 'thinking':
109
- typePrefix = `${logger.COLORS.gray}🤔 THNK${logger.COLORS.reset}`;
110
- if (compact)
111
- content = content.replace(/\n/g, ' ').substring(0, 100) + (content.length > 100 ? '...' : '');
135
+ // Thinking is always compact and gray
136
+ typePrefix = `${log_constants_1.COLORS.gray}🤔 THNK${log_constants_1.COLORS.reset}`;
137
+ content = `${log_constants_1.COLORS.gray}${content.substring(0, 100)}${content.length > 100 ? '...' : ''}${log_constants_1.COLORS.reset}`;
138
+ break;
139
+ case 'info':
140
+ typePrefix = `${log_constants_1.COLORS.cyan}ℹ️ INFO${log_constants_1.COLORS.reset}`;
141
+ break;
142
+ case 'warn':
143
+ typePrefix = `${log_constants_1.COLORS.yellow}⚠️ WARN${log_constants_1.COLORS.reset}`;
144
+ break;
145
+ case 'error':
146
+ typePrefix = `${log_constants_1.COLORS.red}❌ ERR${log_constants_1.COLORS.reset}`;
112
147
  break;
113
148
  }
114
149
  if (!typePrefix)
115
150
  return `${tsPrefix}${labelPrefix}${content}`;
116
- if (compact) {
117
- return `${tsPrefix}${labelPrefix}${typePrefix} ${content}`;
151
+ // Compact format (single line)
152
+ if (!useBox) {
153
+ return `${tsPrefix}${labelPrefix}${typePrefix.padEnd(12)} ${content}`;
118
154
  }
119
- // Multi-line box format (as seen in orchestrator)
155
+ // Multi-line box format (only for user, assistant, system, result)
156
+ // Emoji width is 2, so we need to account for that in indent calculation
120
157
  const lines = content.split('\n');
121
158
  const fullPrefix = `${tsPrefix}${labelPrefix}`;
122
- const header = `${typePrefix} ┌${'─'.repeat(60)}`;
159
+ const strippedPrefix = (0, enhanced_logger_1.stripAnsi)(typePrefix);
160
+ // Count emojis (they take 2 terminal columns but 1-2 chars in string)
161
+ const emojiCount = (strippedPrefix.match(/[\u{1F300}-\u{1F9FF}]|[\u{2600}-\u{26FF}]|[\u{2700}-\u{27BF}]|[\u{1F600}-\u{1F64F}]|[\u{1F680}-\u{1F6FF}]|[\u{1F1E0}-\u{1F1FF}]|[\u{2300}-\u{23FF}]|[\u{2B50}-\u{2B55}]|[\u{231A}-\u{231B}]|[\u{23E9}-\u{23F3}]|[\u{23F8}-\u{23FA}]|✅|❌|⚙️|ℹ️|⚠️|🔧|📄|🤔|🧑|🤖/gu) || []).length;
162
+ const visualWidth = strippedPrefix.length + emojiCount; // emoji adds 1 extra width
163
+ const boxWidth = 60;
164
+ const header = `${typePrefix}┌${'─'.repeat(boxWidth)}`;
123
165
  let result = `${fullPrefix}${header}\n`;
124
- const indent = ' '.repeat((0, enhanced_logger_1.stripAnsi)(typePrefix).length);
166
+ const indent = ' '.repeat(visualWidth);
125
167
  for (const line of lines) {
126
- result += `${fullPrefix}${indent} │ ${line}\n`;
168
+ result += `${fullPrefix}${indent}│ ${line}\n`;
127
169
  }
128
- result += `${fullPrefix}${indent} └${'─'.repeat(60)}`;
170
+ result += `${fullPrefix}${indent}└${'─'.repeat(boxWidth)}`;
129
171
  return result;
130
172
  }
131
173
  /**
@@ -141,8 +183,8 @@ function formatPotentialJsonMessage(message) {
141
183
  if (!json.type)
142
184
  return message;
143
185
  // Convert JSON to a ParsedMessage-like structure for formatting
144
- let content = trimmed;
145
- let type = 'system';
186
+ let content;
187
+ let type;
146
188
  if (json.type === 'thinking' && json.text) {
147
189
  content = json.text;
148
190
  type = 'thinking';
@@ -162,14 +204,15 @@ function formatPotentialJsonMessage(message) {
162
204
  type = 'user';
163
205
  }
164
206
  else if (json.type === 'tool_call' && json.subtype === 'started') {
165
- const toolName = Object.keys(json.tool_call)[0] || 'unknown';
166
- const args = json.tool_call[toolName]?.args || {};
167
- content = `[Tool: ${toolName}] ${JSON.stringify(args)}`;
207
+ const rawToolName = Object.keys(json.tool_call)[0] || 'unknown';
208
+ const args = json.tool_call[rawToolName]?.args || {};
209
+ // Tool name will be simplified in formatMessageForConsole
210
+ content = `[Tool: ${rawToolName}] ${JSON.stringify(args)}`;
168
211
  type = 'tool';
169
212
  }
170
213
  else if (json.type === 'tool_call' && json.subtype === 'completed') {
171
- const toolName = Object.keys(json.tool_call)[0] || 'unknown';
172
- content = `[Tool Result: ${toolName}]`;
214
+ const rawToolName = Object.keys(json.tool_call)[0] || 'unknown';
215
+ content = `[Tool Result: ${rawToolName}]`;
173
216
  type = 'tool_result';
174
217
  }
175
218
  else if (json.type === 'result') {
@@ -1 +1 @@
1
- {"version":3,"file":"log-formatter.js","sourceRoot":"","sources":["../../src/utils/log-formatter.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"log-formatter.js","sourceRoot":"","sources":["../../src/utils/log-formatter.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,19 @@
1
+ /**
2
+ * Log Service - Helpers for log processing and filtering
3
+ */
4
+ import { JsonLogEntry } from './enhanced-logger';
5
+ import { LogImportance } from './types';
6
+ export interface MergedLogEntry extends JsonLogEntry {
7
+ laneName: string;
8
+ laneColor: string;
9
+ }
10
+ export declare class LogService {
11
+ /**
12
+ * Determine importance level of a log entry
13
+ */
14
+ static getLogImportance(entry: JsonLogEntry): LogImportance;
15
+ /**
16
+ * Check if an entry meets the minimum importance level
17
+ */
18
+ static meetsImportanceLevel(entry: JsonLogEntry, minLevel: LogImportance): boolean;
19
+ }
@@ -0,0 +1,47 @@
1
+ "use strict";
2
+ /**
3
+ * Log Service - Helpers for log processing and filtering
4
+ */
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.LogService = void 0;
7
+ const types_1 = require("./types");
8
+ class LogService {
9
+ /**
10
+ * Determine importance level of a log entry
11
+ */
12
+ static getLogImportance(entry) {
13
+ if (entry.level === 'error')
14
+ return types_1.LogImportance.CRITICAL;
15
+ if (entry.level === 'stderr')
16
+ return types_1.LogImportance.HIGH;
17
+ const msg = (entry.message || '').toLowerCase();
18
+ if (msg.includes('error') || msg.includes('fail'))
19
+ return types_1.LogImportance.HIGH;
20
+ if (msg.includes('warn'))
21
+ return types_1.LogImportance.MEDIUM;
22
+ if (msg.includes('success') || msg.includes('done') || msg.includes('completed'))
23
+ return types_1.LogImportance.LOW;
24
+ if (entry.level === 'debug')
25
+ return types_1.LogImportance.DEBUG;
26
+ return types_1.LogImportance.INFO;
27
+ }
28
+ /**
29
+ * Check if an entry meets the minimum importance level
30
+ */
31
+ static meetsImportanceLevel(entry, minLevel) {
32
+ const entryLevel = this.getLogImportance(entry);
33
+ const levels = [
34
+ types_1.LogImportance.DEBUG,
35
+ types_1.LogImportance.INFO,
36
+ types_1.LogImportance.LOW,
37
+ types_1.LogImportance.MEDIUM,
38
+ types_1.LogImportance.HIGH,
39
+ types_1.LogImportance.CRITICAL
40
+ ];
41
+ const entryIdx = levels.indexOf(entryLevel);
42
+ const minIdx = levels.indexOf(minLevel);
43
+ return entryIdx >= minIdx;
44
+ }
45
+ }
46
+ exports.LogService = LogService;
47
+ //# sourceMappingURL=log-service.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"log-service.js","sourceRoot":"","sources":["../../src/utils/log-service.ts"],"names":[],"mappings":";AAAA;;GAEG;;;AAGH,mCAAwC;AAOxC,MAAa,UAAU;IACrB;;OAEG;IACH,MAAM,CAAC,gBAAgB,CAAC,KAAmB;QACzC,IAAI,KAAK,CAAC,KAAK,KAAK,OAAO;YAAE,OAAO,qBAAa,CAAC,QAAQ,CAAC;QAC3D,IAAI,KAAK,CAAC,KAAK,KAAK,QAAQ;YAAE,OAAO,qBAAa,CAAC,IAAI,CAAC;QAExD,MAAM,GAAG,GAAG,CAAC,KAAK,CAAC,OAAO,IAAI,EAAE,CAAC,CAAC,WAAW,EAAE,CAAC;QAChD,IAAI,GAAG,CAAC,QAAQ,CAAC,OAAO,CAAC,IAAI,GAAG,CAAC,QAAQ,CAAC,MAAM,CAAC;YAAE,OAAO,qBAAa,CAAC,IAAI,CAAC;QAC7E,IAAI,GAAG,CAAC,QAAQ,CAAC,MAAM,CAAC;YAAE,OAAO,qBAAa,CAAC,MAAM,CAAC;QACtD,IAAI,GAAG,CAAC,QAAQ,CAAC,SAAS,CAAC,IAAI,GAAG,CAAC,QAAQ,CAAC,MAAM,CAAC,IAAI,GAAG,CAAC,QAAQ,CAAC,WAAW,CAAC;YAAE,OAAO,qBAAa,CAAC,GAAG,CAAC;QAE3G,IAAI,KAAK,CAAC,KAAK,KAAK,OAAO;YAAE,OAAO,qBAAa,CAAC,KAAK,CAAC;QACxD,OAAO,qBAAa,CAAC,IAAI,CAAC;IAC5B,CAAC;IAED;;OAEG;IACH,MAAM,CAAC,oBAAoB,CAAC,KAAmB,EAAE,QAAuB;QACtE,MAAM,UAAU,GAAG,IAAI,CAAC,gBAAgB,CAAC,KAAK,CAAC,CAAC;QAChD,MAAM,MAAM,GAAG;YACb,qBAAa,CAAC,KAAK;YACnB,qBAAa,CAAC,IAAI;YAClB,qBAAa,CAAC,GAAG;YACjB,qBAAa,CAAC,MAAM;YACpB,qBAAa,CAAC,IAAI;YAClB,qBAAa,CAAC,QAAQ;SACvB,CAAC;QAEF,MAAM,QAAQ,GAAG,MAAM,CAAC,OAAO,CAAC,UAAU,CAAC,CAAC;QAC5C,MAAM,MAAM,GAAG,MAAM,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;QAExC,OAAO,QAAQ,IAAI,MAAM,CAAC;IAC5B,CAAC;CACF;AApCD,gCAoCC"}
@@ -1,68 +1,87 @@
1
1
  /**
2
2
  * Logging utilities for CursorFlow
3
+ *
4
+ * 통일된 로그 형식: [HH:MM:SS] emoji TYPE message
5
+ * 컨텍스트 포함 시: [HH:MM:SS] [context] emoji TYPE message
3
6
  */
4
- export declare enum LogLevel {
5
- error = 0,
6
- warn = 1,
7
- info = 2,
8
- debug = 3
9
- }
10
- export declare const COLORS: {
11
- reset: string;
12
- red: string;
13
- yellow: string;
14
- green: string;
15
- blue: string;
16
- cyan: string;
17
- magenta: string;
18
- gray: string;
19
- bold: string;
20
- };
7
+ import { COLORS, LogLevel } from './log-constants';
8
+ export { COLORS, LogLevel };
21
9
  /**
22
10
  * Set log level
23
11
  */
24
12
  export declare function setLogLevel(level: string | number): void;
13
+ /**
14
+ * Get current log level
15
+ */
16
+ export declare function getLogLevel(): number;
17
+ /**
18
+ * Log options interface for contextual logging
19
+ */
20
+ export interface LogOptions {
21
+ /** Context label (e.g., lane name) */
22
+ context?: string;
23
+ /** Custom emoji override */
24
+ emoji?: string;
25
+ /** Skip timestamp */
26
+ noTimestamp?: boolean;
27
+ /** Custom color */
28
+ color?: string;
29
+ /** Use box format */
30
+ box?: boolean;
31
+ }
25
32
  /**
26
33
  * Error log
27
34
  */
28
- export declare function error(message: string, emoji?: string): void;
35
+ export declare function error(message: string, options?: LogOptions | string): void;
29
36
  /**
30
37
  * Warning log
31
38
  */
32
- export declare function warn(message: string, emoji?: string): void;
39
+ export declare function warn(message: string, options?: LogOptions | string): void;
33
40
  /**
34
41
  * Info log
35
42
  */
36
- export declare function info(message: string, emoji?: string): void;
43
+ export declare function info(message: string, options?: LogOptions | string): void;
37
44
  /**
38
45
  * Success log
39
46
  */
40
- export declare function success(message: string, emoji?: string): void;
47
+ export declare function success(message: string, options?: LogOptions | string): void;
41
48
  /**
42
49
  * Debug log
43
50
  */
44
- export declare function debug(message: string, emoji?: string): void;
51
+ export declare function debug(message: string, options?: LogOptions | string): void;
45
52
  /**
46
53
  * Progress log
47
54
  */
48
- export declare function progress(message: string, emoji?: string): void;
55
+ export declare function progress(message: string, options?: LogOptions | string): void;
56
+ /**
57
+ * Create a context-bound logger
58
+ */
59
+ export declare function withContext(context: string): {
60
+ error: (message: string, options?: Omit<LogOptions, "context">) => void;
61
+ warn: (message: string, options?: Omit<LogOptions, "context">) => void;
62
+ info: (message: string, options?: Omit<LogOptions, "context">) => void;
63
+ success: (message: string, options?: Omit<LogOptions, "context">) => void;
64
+ debug: (message: string, options?: Omit<LogOptions, "context">) => void;
65
+ progress: (message: string, options?: Omit<LogOptions, "context">) => void;
66
+ };
49
67
  /**
50
68
  * Section header
51
69
  */
52
70
  export declare function section(message: string): void;
53
71
  /**
54
- * Simple log without formatting
72
+ * Raw output (direct to stdout)
55
73
  */
56
- export declare function log(message: string | any): void;
74
+ export declare function raw(message: string): void;
57
75
  /**
58
- * Log JSON data (pretty print in debug mode)
76
+ * Simple log without formatting
59
77
  */
60
- export declare function json(data: any): void;
78
+ export declare function log(message: string): void;
61
79
  export interface Spinner {
62
80
  start(): void;
63
81
  stop(finalMessage?: string | null): void;
64
82
  succeed(message: string): void;
65
83
  fail(message: string): void;
84
+ update(message: string): void;
66
85
  }
67
86
  /**
68
87
  * Create spinner (simple implementation)