@ob1-sg/horizon 0.1.10 → 0.1.12

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 (157) hide show
  1. package/dist/cli.d.ts +3 -0
  2. package/dist/cli.d.ts.map +1 -0
  3. package/dist/cli.js +43 -0
  4. package/dist/cli.js.map +1 -0
  5. package/dist/config.d.ts +10 -0
  6. package/dist/config.d.ts.map +1 -0
  7. package/dist/config.js +293 -0
  8. package/dist/config.js.map +1 -0
  9. package/dist/index.d.ts +4 -0
  10. package/dist/index.d.ts.map +1 -0
  11. package/dist/index.js +635 -0
  12. package/dist/index.js.map +1 -0
  13. package/dist/lib/__tests__/attachment-downloader.test.d.ts +2 -0
  14. package/dist/lib/__tests__/attachment-downloader.test.d.ts.map +1 -0
  15. package/dist/lib/__tests__/attachment-downloader.test.js +163 -0
  16. package/dist/lib/__tests__/attachment-downloader.test.js.map +1 -0
  17. package/dist/lib/__tests__/cli-detection.test.d.ts +2 -0
  18. package/dist/lib/__tests__/cli-detection.test.d.ts.map +1 -0
  19. package/dist/lib/__tests__/cli-detection.test.js +119 -0
  20. package/dist/lib/__tests__/cli-detection.test.js.map +1 -0
  21. package/dist/lib/__tests__/config.test.d.ts +2 -0
  22. package/dist/lib/__tests__/config.test.d.ts.map +1 -0
  23. package/dist/lib/__tests__/config.test.js +291 -0
  24. package/dist/lib/__tests__/config.test.js.map +1 -0
  25. package/dist/lib/__tests__/gcp.test.d.ts +2 -0
  26. package/dist/lib/__tests__/gcp.test.d.ts.map +1 -0
  27. package/dist/lib/__tests__/gcp.test.js +104 -0
  28. package/dist/lib/__tests__/gcp.test.js.map +1 -0
  29. package/dist/lib/__tests__/git.test.d.ts +2 -0
  30. package/dist/lib/__tests__/git.test.d.ts.map +1 -0
  31. package/dist/lib/__tests__/git.test.js +62 -0
  32. package/dist/lib/__tests__/git.test.js.map +1 -0
  33. package/dist/lib/__tests__/linear-quick-check.test.d.ts +2 -0
  34. package/dist/lib/__tests__/linear-quick-check.test.d.ts.map +1 -0
  35. package/dist/lib/__tests__/linear-quick-check.test.js +152 -0
  36. package/dist/lib/__tests__/linear-quick-check.test.js.map +1 -0
  37. package/dist/lib/__tests__/loop-instance-name.test.d.ts +2 -0
  38. package/dist/lib/__tests__/loop-instance-name.test.d.ts.map +1 -0
  39. package/dist/lib/__tests__/loop-instance-name.test.js +90 -0
  40. package/dist/lib/__tests__/loop-instance-name.test.js.map +1 -0
  41. package/dist/lib/__tests__/output-logger.test.d.ts +2 -0
  42. package/dist/lib/__tests__/output-logger.test.d.ts.map +1 -0
  43. package/dist/lib/__tests__/output-logger.test.js +136 -0
  44. package/dist/lib/__tests__/output-logger.test.js.map +1 -0
  45. package/dist/lib/__tests__/prompts.test.d.ts +2 -0
  46. package/dist/lib/__tests__/prompts.test.d.ts.map +1 -0
  47. package/dist/lib/__tests__/prompts.test.js +70 -0
  48. package/dist/lib/__tests__/prompts.test.js.map +1 -0
  49. package/dist/lib/__tests__/provider.test.d.ts +2 -0
  50. package/dist/lib/__tests__/provider.test.d.ts.map +1 -0
  51. package/dist/lib/__tests__/provider.test.js +89 -0
  52. package/dist/lib/__tests__/provider.test.js.map +1 -0
  53. package/dist/lib/__tests__/rate-limit.test.d.ts +2 -0
  54. package/dist/lib/__tests__/rate-limit.test.d.ts.map +1 -0
  55. package/dist/lib/__tests__/rate-limit.test.js +275 -0
  56. package/dist/lib/__tests__/rate-limit.test.js.map +1 -0
  57. package/dist/lib/__tests__/readline.test.d.ts +2 -0
  58. package/dist/lib/__tests__/readline.test.d.ts.map +1 -0
  59. package/dist/lib/__tests__/readline.test.js +55 -0
  60. package/dist/lib/__tests__/readline.test.js.map +1 -0
  61. package/dist/lib/__tests__/stats-logger.test.d.ts +2 -0
  62. package/dist/lib/__tests__/stats-logger.test.d.ts.map +1 -0
  63. package/dist/lib/__tests__/stats-logger.test.js +297 -0
  64. package/dist/lib/__tests__/stats-logger.test.js.map +1 -0
  65. package/dist/lib/__tests__/update-checker.test.d.ts +2 -0
  66. package/dist/lib/__tests__/update-checker.test.d.ts.map +1 -0
  67. package/dist/lib/__tests__/update-checker.test.js +141 -0
  68. package/dist/lib/__tests__/update-checker.test.js.map +1 -0
  69. package/dist/lib/__tests__/version.test.d.ts +2 -0
  70. package/dist/lib/__tests__/version.test.d.ts.map +1 -0
  71. package/dist/lib/__tests__/version.test.js +51 -0
  72. package/dist/lib/__tests__/version.test.js.map +1 -0
  73. package/dist/lib/attachment-downloader.d.ts +26 -0
  74. package/dist/lib/attachment-downloader.d.ts.map +1 -0
  75. package/dist/lib/attachment-downloader.js +259 -0
  76. package/dist/lib/attachment-downloader.js.map +1 -0
  77. package/dist/lib/claude.d.ts +6 -0
  78. package/dist/lib/claude.d.ts.map +1 -0
  79. package/dist/lib/claude.js +459 -0
  80. package/dist/lib/claude.js.map +1 -0
  81. package/dist/lib/cli-detection.d.ts +25 -0
  82. package/dist/lib/cli-detection.d.ts.map +1 -0
  83. package/dist/lib/cli-detection.js +53 -0
  84. package/dist/lib/cli-detection.js.map +1 -0
  85. package/dist/lib/codex.d.ts +4 -0
  86. package/dist/lib/codex.d.ts.map +1 -0
  87. package/dist/lib/codex.js +320 -0
  88. package/dist/lib/codex.js.map +1 -0
  89. package/dist/lib/gcp.d.ts +21 -0
  90. package/dist/lib/gcp.d.ts.map +1 -0
  91. package/dist/lib/gcp.js +96 -0
  92. package/dist/lib/gcp.js.map +1 -0
  93. package/dist/lib/git.d.ts +3 -0
  94. package/dist/lib/git.d.ts.map +1 -0
  95. package/dist/lib/git.js +24 -0
  96. package/dist/lib/git.js.map +1 -0
  97. package/dist/lib/init-project.d.ts +13 -0
  98. package/dist/lib/init-project.d.ts.map +1 -0
  99. package/dist/lib/init-project.js +420 -0
  100. package/dist/lib/init-project.js.map +1 -0
  101. package/dist/lib/linear-api.d.ts +32 -0
  102. package/dist/lib/linear-api.d.ts.map +1 -0
  103. package/dist/lib/linear-api.js +267 -0
  104. package/dist/lib/linear-api.js.map +1 -0
  105. package/dist/lib/linear-quick-check.d.ts +13 -0
  106. package/dist/lib/linear-quick-check.d.ts.map +1 -0
  107. package/dist/lib/linear-quick-check.js +61 -0
  108. package/dist/lib/linear-quick-check.js.map +1 -0
  109. package/dist/lib/loop-instance-name.d.ts +29 -0
  110. package/dist/lib/loop-instance-name.d.ts.map +1 -0
  111. package/dist/lib/loop-instance-name.js +105 -0
  112. package/dist/lib/loop-instance-name.js.map +1 -0
  113. package/dist/lib/output-logger.d.ts +23 -0
  114. package/dist/lib/output-logger.d.ts.map +1 -0
  115. package/dist/lib/output-logger.js +104 -0
  116. package/dist/lib/output-logger.js.map +1 -0
  117. package/dist/lib/prompts.d.ts +17 -0
  118. package/dist/lib/prompts.d.ts.map +1 -0
  119. package/dist/lib/prompts.js +65 -0
  120. package/dist/lib/prompts.js.map +1 -0
  121. package/dist/lib/provider.d.ts +32 -0
  122. package/dist/lib/provider.d.ts.map +1 -0
  123. package/dist/lib/provider.js +27 -0
  124. package/dist/lib/provider.js.map +1 -0
  125. package/dist/lib/rate-limit.d.ts +14 -0
  126. package/dist/lib/rate-limit.d.ts.map +1 -0
  127. package/dist/lib/rate-limit.js +154 -0
  128. package/dist/lib/rate-limit.js.map +1 -0
  129. package/dist/lib/readline.d.ts +4 -0
  130. package/dist/lib/readline.d.ts.map +1 -0
  131. package/dist/lib/readline.js +39 -0
  132. package/dist/lib/readline.js.map +1 -0
  133. package/dist/lib/setup.d.ts +126 -0
  134. package/dist/lib/setup.d.ts.map +1 -0
  135. package/dist/lib/setup.js +482 -0
  136. package/dist/lib/setup.js.map +1 -0
  137. package/dist/lib/stats-logger.d.ts +92 -0
  138. package/dist/lib/stats-logger.d.ts.map +1 -0
  139. package/dist/lib/stats-logger.js +258 -0
  140. package/dist/lib/stats-logger.js.map +1 -0
  141. package/dist/lib/ui.d.ts +38 -0
  142. package/dist/lib/ui.d.ts.map +1 -0
  143. package/dist/lib/ui.js +69 -0
  144. package/dist/lib/ui.js.map +1 -0
  145. package/dist/lib/update-checker.d.ts +17 -0
  146. package/dist/lib/update-checker.d.ts.map +1 -0
  147. package/dist/lib/update-checker.js +138 -0
  148. package/dist/lib/update-checker.js.map +1 -0
  149. package/dist/lib/version.d.ts +10 -0
  150. package/dist/lib/version.d.ts.map +1 -0
  151. package/dist/lib/version.js +37 -0
  152. package/dist/lib/version.js.map +1 -0
  153. package/dist/types.d.ts +92 -0
  154. package/dist/types.d.ts.map +1 -0
  155. package/dist/types.js +3 -0
  156. package/dist/types.js.map +1 -0
  157. package/package.json +5 -2
@@ -0,0 +1,459 @@
1
+ import { spawn } from 'child_process';
2
+ import { existsSync } from 'fs';
3
+ import { join } from 'path';
4
+ import { parseRateLimitReset, isRateLimitError } from './rate-limit.js';
5
+ import { getConfig, getRepoRoot } from '../config.js';
6
+ import { logAgentOutput, logTerminalOutput } from './output-logger.js';
7
+ import { registerClaudeProvider } from './provider.js';
8
+ import { BOLD, DIM, YELLOW, GREEN, BLUE, RESET, box, renderMarkdown } from './ui.js';
9
+ // Track subagent ID -> description mapping
10
+ const subagentMap = new Map();
11
+ // Track the last main-agent tool_use ID for correlating tool results
12
+ let lastMainToolUseId = null;
13
+ // MCP tool call collapsing state
14
+ let mcpConsecutiveCount = 0;
15
+ const MCP_SHOW_LIMIT = 3;
16
+ // Dimmed compact format for MCP calls beyond the show limit
17
+ function formatMcpCompact(name, input) {
18
+ const short = name.replace(/^mcp__/, '').replace(/__/, ':');
19
+ const sig = input ? formatToolSignature(short, input) : short;
20
+ return `${DIM} ○ ${sig}${RESET}`;
21
+ }
22
+ // Helper: Extract short model name
23
+ function modelName(model) {
24
+ if (!model)
25
+ return '?';
26
+ if (model.includes('opus'))
27
+ return 'opus';
28
+ if (model.includes('sonnet'))
29
+ return 'sonnet';
30
+ if (model.includes('haiku'))
31
+ return 'haiku';
32
+ return model;
33
+ }
34
+ // Helper: Calculate context usage percentage (168K effective limit)
35
+ function contextPct(usage) {
36
+ const total = (usage.cache_creation_input_tokens || 0) + (usage.cache_read_input_tokens || 0);
37
+ return Math.floor((total * 100) / 168000);
38
+ }
39
+ // Helper: Clean up file paths for display
40
+ function cleanPath(path) {
41
+ return path
42
+ .replace(/\/home\/ubuntu\/repos\/[^/]+\//g, '')
43
+ .replace(/\/Users\/[^/]+\/repos\/[^/]+\//g, '');
44
+ }
45
+ // Helper: Extract the most useful value from tool input
46
+ function extractToolValue(input) {
47
+ if (input.file_path)
48
+ return cleanPath(String(input.file_path));
49
+ if (input.path && input.pattern)
50
+ return `${input.pattern} in ${cleanPath(String(input.path))}`;
51
+ if (input.pattern)
52
+ return String(input.pattern);
53
+ if (input.command)
54
+ return String(input.command).substring(0, 80).replace(/\n/g, ' ');
55
+ if (input.query)
56
+ return String(input.query).substring(0, 80);
57
+ if (input.content)
58
+ return '(content)';
59
+ if (input.todos)
60
+ return '(todos)';
61
+ return JSON.stringify(input).substring(0, 80).replace(/\n/g, ' ');
62
+ }
63
+ // Format numbers with commas
64
+ function formatNumber(num) {
65
+ return num.toLocaleString();
66
+ }
67
+ // Truncate string to max length
68
+ function truncate(str, maxLen = 120) {
69
+ if (str.length <= maxLen)
70
+ return str;
71
+ return str.substring(0, maxLen) + '...';
72
+ }
73
+ // Format tool calls as function signatures: Read(file_path="src/file.ts", offset=1)
74
+ function formatToolSignature(name, input) {
75
+ const params = Object.entries(input)
76
+ .filter(([, v]) => v !== undefined && v !== null)
77
+ .map(([k, v]) => {
78
+ if (typeof v === 'string')
79
+ return `${k}="${truncate(cleanPath(v), 60)}"`;
80
+ if (typeof v === 'object')
81
+ return `${k}={...}`;
82
+ return `${k}=${v}`;
83
+ })
84
+ .join(', ');
85
+ return `${name}(${truncate(params, 120)})`;
86
+ }
87
+ // Format tool results with tree connector, capped at 3 lines
88
+ function formatToolResult(toolUseResult) {
89
+ let text = '';
90
+ if (toolUseResult.file && typeof toolUseResult.file.content === 'string') {
91
+ text = toolUseResult.file.content;
92
+ }
93
+ else if (typeof toolUseResult.stdout === 'string') {
94
+ text = toolUseResult.stdout;
95
+ }
96
+ else if (typeof toolUseResult.content === 'string') {
97
+ text = toolUseResult.content;
98
+ }
99
+ if (!text.trim())
100
+ return null;
101
+ const lines = text.split('\n').filter(l => l.trim());
102
+ const preview = lines.slice(0, 3);
103
+ const more = lines.length > 3;
104
+ return preview.map((line, i) => {
105
+ const prefix = i === 0 ? '└ ' : ' ';
106
+ return `${DIM} ${prefix}${truncate(line, 100)}${RESET}`;
107
+ }).join('\n') + (more ? `\n${DIM} ...${RESET}` : '');
108
+ }
109
+ // Process a single JSON line and return formatted output
110
+ function processJsonLine(json) {
111
+ // System init
112
+ if (json.type === 'system' && json.subtype === 'init') {
113
+ const tools = Array.isArray(json.tools) ? json.tools.length : 0;
114
+ return '\n' + box([` Model: ${json.model} | Tools: ${tools} available `], { title: 'SESSION START', color: BLUE, width: 60 });
115
+ }
116
+ // System status
117
+ if (json.type === 'system' && json.subtype === 'status') {
118
+ return `${BLUE}${DIM}≡ Working...${RESET}`;
119
+ }
120
+ // Context compaction
121
+ if (json.type === 'system' && json.subtype === 'compact_boundary') {
122
+ const metadata = json.compact_metadata;
123
+ const preTokens = metadata?.pre_tokens ? Math.floor(metadata.pre_tokens / 1000) : '?';
124
+ return `${DIM}~ Context compacted (was ${preTokens}k tokens)${RESET}`;
125
+ }
126
+ // Task notification
127
+ if (json.type === 'system' && json.subtype === 'task_notification') {
128
+ return `${GREEN}✓ Done: ${json.summary}${RESET}`;
129
+ }
130
+ // Tool results (type: "user" with tool_use_result)
131
+ if (json.type === 'user') {
132
+ const message = json.message;
133
+ const content = message?.content;
134
+ if (Array.isArray(content)) {
135
+ const lines = [];
136
+ for (const item of content) {
137
+ if (item.type === 'tool_result' && item.tool_use_id === lastMainToolUseId) {
138
+ const resultContent = item.content;
139
+ if (item.is_error && typeof resultContent === 'string') {
140
+ lines.push(`${YELLOW} └ Error: ${truncate(resultContent, 100)}${RESET}`);
141
+ }
142
+ else if (Array.isArray(resultContent)) {
143
+ // tool_result content can be an array of content blocks
144
+ for (const block of resultContent) {
145
+ if (typeof block === 'object' && block !== null) {
146
+ const result = formatToolResult(block);
147
+ if (result)
148
+ lines.push(result);
149
+ }
150
+ }
151
+ }
152
+ else if (typeof resultContent === 'object' && resultContent !== null) {
153
+ const result = formatToolResult(resultContent);
154
+ if (result)
155
+ lines.push(result);
156
+ }
157
+ }
158
+ }
159
+ return lines.length > 0 ? lines.join('\n') : null;
160
+ }
161
+ return null;
162
+ }
163
+ // Result (session end)
164
+ if (json.type === 'result') {
165
+ const modelUsage = json.modelUsage;
166
+ let totalIn = 0, totalOut = 0, totalCacheRead = 0, totalCacheWrite = 0;
167
+ const modelBreakdown = [];
168
+ if (modelUsage) {
169
+ for (const [model, usage] of Object.entries(modelUsage)) {
170
+ const inTokens = usage.inputTokens || 0;
171
+ const outTokens = usage.outputTokens || 0;
172
+ const cacheRead = usage.cacheReadInputTokens || 0;
173
+ const cacheWrite = usage.cacheCreationInputTokens || 0;
174
+ const cost = usage.costUSD || 0;
175
+ totalIn += inTokens;
176
+ totalOut += outTokens;
177
+ totalCacheRead += cacheRead;
178
+ totalCacheWrite += cacheWrite;
179
+ const shortModel = model.split('-')[1] || model;
180
+ modelBreakdown.push(`${shortModel}: in=${formatNumber(inTokens)} out=${formatNumber(outTokens)} ` +
181
+ `cache_read=${formatNumber(cacheRead)} cache_write=${formatNumber(cacheWrite)} $${cost.toFixed(2)}`);
182
+ }
183
+ }
184
+ const durationSec = Math.floor((json.duration_ms || 0) / 1000);
185
+ const totalCost = (json.total_cost_usd || 0).toFixed(2);
186
+ const numTurns = json.num_turns || 0;
187
+ const endLines = [
188
+ ` Duration: ${durationSec}s | Cost: $${totalCost} | Turns: ${numTurns} `,
189
+ ...modelBreakdown.map(l => ` ${l} `),
190
+ ` TOTAL: in=${formatNumber(totalIn)} out=${formatNumber(totalOut)} cache_read=${formatNumber(totalCacheRead)} cache_write=${formatNumber(totalCacheWrite)} `,
191
+ ];
192
+ return '\n' + box(endLines, { title: 'SESSION END', color: BLUE, width: 80, dividerAfter: [0] });
193
+ }
194
+ // Assistant messages
195
+ if (json.type === 'assistant') {
196
+ const message = json.message;
197
+ const model = modelName(message?.model);
198
+ const pct = message?.usage ? contextPct(message.usage) : 0;
199
+ const parentId = json.parent_tool_use_id;
200
+ const content = message?.content || [];
201
+ const tag = `${DIM}[${model}/${pct}%]${RESET}`;
202
+ // Detect if all tool_use items at top level are MCP calls
203
+ const toolUseItems = content.filter(i => i.type === 'tool_use' && parentId === null);
204
+ const allMcp = toolUseItems.length > 0 && toolUseItems.every(i => (i.name || '').startsWith('mcp__'));
205
+ if (allMcp) {
206
+ mcpConsecutiveCount++;
207
+ if (mcpConsecutiveCount > MCP_SHOW_LIMIT) {
208
+ // Show dimmed compact line instead of full green-dot format
209
+ const compactLines = toolUseItems.map(i => formatMcpCompact(i.name || 'unknown', i.input || {}));
210
+ return compactLines.join('\n');
211
+ }
212
+ }
213
+ const lines = [];
214
+ // Reset MCP count when a non-MCP message arrives
215
+ if (!allMcp) {
216
+ mcpConsecutiveCount = 0;
217
+ }
218
+ for (const item of content) {
219
+ if (item.name === 'Task') {
220
+ // Main agent spawning a subagent
221
+ const input = item.input;
222
+ const desc = input?.description || 'unknown';
223
+ // Store mapping for later
224
+ if (item.id) {
225
+ subagentMap.set(item.id, desc);
226
+ }
227
+ lines.push(`${YELLOW}▸ Spawn: ${desc} ${tag}${RESET}`);
228
+ }
229
+ else if (item.name === 'TaskOutput') {
230
+ continue;
231
+ }
232
+ else if (item.type === 'tool_use') {
233
+ if (parentId === null) {
234
+ // Main agent tool call - green dot + function signature
235
+ const sig = item.input ? formatToolSignature(item.name || 'unknown', item.input) : (item.name || 'unknown');
236
+ lines.push(`${GREEN}${BOLD}●${RESET} ${sig} ${tag}`);
237
+ // Track for tool result correlation
238
+ if (item.id)
239
+ lastMainToolUseId = item.id;
240
+ }
241
+ else {
242
+ // Subagent tool call - indented with arrow
243
+ const parentDesc = subagentMap.get(parentId) || parentId;
244
+ const value = item.input ? extractToolValue(item.input) : '';
245
+ lines.push(`${DIM} ${parentDesc} ▸ ${item.name}: ${value}${RESET}`);
246
+ }
247
+ }
248
+ else if (item.type === 'thinking') {
249
+ // Thinking indicator
250
+ lines.push(`${DIM}* Thinking...${RESET}`);
251
+ }
252
+ else if (item.type === 'text' && item.text) {
253
+ if (parentId === null) {
254
+ // Main agent text - clean without emoji prefix
255
+ lines.push(`${renderMarkdown(item.text)} ${tag}`);
256
+ }
257
+ // Skip subagent text to reduce noise
258
+ }
259
+ }
260
+ return lines.length > 0 ? lines.join('\n') : null;
261
+ }
262
+ return null;
263
+ }
264
+ // Legacy function for backwards compatibility
265
+ export async function spawnClaude(options, agentNumber) {
266
+ // Clear state for new session
267
+ subagentMap.clear();
268
+ lastMainToolUseId = null;
269
+ mcpConsecutiveCount = 0;
270
+ return new Promise((resolve, reject) => {
271
+ const config = getConfig();
272
+ const args = [
273
+ '-p',
274
+ '--dangerously-skip-permissions',
275
+ '--output-format=stream-json',
276
+ '--model', options.model,
277
+ '--verbose',
278
+ ];
279
+ // Add MCP config if it exists in .horizon/mcp.json
280
+ const mcpConfigPath = join(getRepoRoot(), '.horizon', 'mcp.json');
281
+ if (existsSync(mcpConfigPath)) {
282
+ args.push('--mcp-config', mcpConfigPath);
283
+ }
284
+ // Add allowed tools restriction if specified
285
+ if (options.allowedTools && options.allowedTools.length > 0) {
286
+ args.push('--allowedTools', options.allowedTools.join(','));
287
+ }
288
+ const spawnMsg = `${DIM} spawning claude --model ${options.model} --verbose ...${RESET}`;
289
+ console.log(spawnMsg);
290
+ if (agentNumber !== undefined) {
291
+ logTerminalOutput(agentNumber, spawnMsg).catch(() => { });
292
+ }
293
+ const proc = spawn('claude', args, {
294
+ stdio: ['pipe', 'pipe', 'pipe'],
295
+ cwd: config.workingDirectory,
296
+ });
297
+ proc.stdin.write(options.prompt);
298
+ proc.stdin.end();
299
+ let output = '';
300
+ let rateLimited = false;
301
+ let retryAfterMs;
302
+ let cost = 0;
303
+ let duration = 0;
304
+ proc.stdout.on('data', (chunk) => {
305
+ const text = chunk.toString();
306
+ output += text;
307
+ // Parse streaming JSON output
308
+ for (const line of text.split('\n')) {
309
+ if (!line.trim())
310
+ continue;
311
+ // Persist raw line to output log file if agent number provided
312
+ if (agentNumber !== undefined) {
313
+ logAgentOutput(agentNumber, line).catch(() => {
314
+ // Silently ignore logging errors
315
+ });
316
+ }
317
+ try {
318
+ const json = JSON.parse(line);
319
+ // Check for rate limits
320
+ if (json.error === 'rate_limit') {
321
+ rateLimited = true;
322
+ retryAfterMs = parseRateLimitReset(json);
323
+ }
324
+ if (json.type === 'result' && json.is_error) {
325
+ const resultText = String(json.result || '');
326
+ if (isRateLimitError(resultText)) {
327
+ rateLimited = true;
328
+ retryAfterMs = parseRateLimitReset(json);
329
+ }
330
+ }
331
+ // Capture final stats
332
+ if (json.type === 'result') {
333
+ cost = json.total_cost_usd || 0;
334
+ duration = json.duration_ms || 0;
335
+ }
336
+ // Process and log the line
337
+ const formatted = processJsonLine(json);
338
+ if (formatted) {
339
+ console.log(formatted);
340
+ // Persist formatted terminal output to separate log file
341
+ if (agentNumber !== undefined) {
342
+ logTerminalOutput(agentNumber, formatted).catch(() => {
343
+ // Silently ignore logging errors
344
+ });
345
+ }
346
+ }
347
+ }
348
+ catch {
349
+ // Not JSON or parse error, ignore
350
+ }
351
+ }
352
+ });
353
+ proc.stderr.on('data', (chunk) => {
354
+ const text = chunk.toString().trim();
355
+ if (text) {
356
+ const stderrMsg = `${DIM}stderr: ${text}${RESET}`;
357
+ console.error(stderrMsg);
358
+ // Log stderr to terminal log
359
+ if (agentNumber !== undefined) {
360
+ logTerminalOutput(agentNumber, stderrMsg).catch(() => { });
361
+ }
362
+ }
363
+ });
364
+ proc.on('close', (code) => {
365
+ resolve({
366
+ output,
367
+ rateLimited,
368
+ retryAfterMs,
369
+ cost,
370
+ duration,
371
+ exitCode: code || 0,
372
+ });
373
+ });
374
+ proc.on('error', (err) => {
375
+ reject(new Error(`Failed to spawn claude: ${err.message}`));
376
+ });
377
+ });
378
+ }
379
+ // Extract the final text output from Claude's streaming JSON
380
+ export function extractFinalOutput(streamOutput) {
381
+ const lines = streamOutput.split('\n');
382
+ let lastTextContent = '';
383
+ for (const line of lines) {
384
+ if (!line.trim())
385
+ continue;
386
+ try {
387
+ const json = JSON.parse(line);
388
+ // Look for assistant messages at the top level (not subagent)
389
+ if (json.type === 'assistant' && !json.parent_tool_use_id) {
390
+ const content = json.message?.content;
391
+ if (Array.isArray(content)) {
392
+ for (const item of content) {
393
+ if (item.type === 'text' && item.text) {
394
+ lastTextContent = item.text;
395
+ }
396
+ }
397
+ }
398
+ }
399
+ // Also check result type for final output
400
+ if (json.type === 'result' && !json.is_error && json.result) {
401
+ lastTextContent = String(json.result);
402
+ }
403
+ }
404
+ catch {
405
+ // Not JSON, ignore
406
+ }
407
+ }
408
+ return lastTextContent;
409
+ }
410
+ // Claude provider implementation
411
+ class ClaudeProvider {
412
+ name = 'claude';
413
+ async spawn(options, agentNumber) {
414
+ // Map model string to ClaudeModel type
415
+ const model = options.model || getConfig().claudeModel;
416
+ const result = await spawnClaude({
417
+ prompt: options.prompt,
418
+ model,
419
+ allowedTools: options.allowedTools,
420
+ }, agentNumber);
421
+ // Extract token usage from the output
422
+ const tokenUsage = { input: 0, output: 0, cached: 0 };
423
+ for (const line of result.output.split('\n')) {
424
+ if (!line.trim())
425
+ continue;
426
+ try {
427
+ const json = JSON.parse(line);
428
+ if (json.type === 'result' && json.modelUsage) {
429
+ for (const usage of Object.values(json.modelUsage)) {
430
+ tokenUsage.input += usage.inputTokens || 0;
431
+ tokenUsage.output += usage.outputTokens || 0;
432
+ tokenUsage.cached += usage.cacheReadInputTokens || 0;
433
+ }
434
+ }
435
+ }
436
+ catch {
437
+ // Ignore parse errors
438
+ }
439
+ }
440
+ return {
441
+ output: result.output,
442
+ finalOutput: extractFinalOutput(result.output),
443
+ rateLimited: result.rateLimited,
444
+ retryAfterMs: result.retryAfterMs,
445
+ cost: result.cost,
446
+ costEstimated: false, // Claude provides exact cost
447
+ duration: result.duration,
448
+ exitCode: result.exitCode,
449
+ tokenUsage,
450
+ };
451
+ }
452
+ }
453
+ // Factory function
454
+ export function createClaudeProvider() {
455
+ return new ClaudeProvider();
456
+ }
457
+ // Register the Claude provider
458
+ registerClaudeProvider(createClaudeProvider);
459
+ //# sourceMappingURL=claude.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"claude.js","sourceRoot":"","sources":["../../src/lib/claude.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,25 @@
1
+ export interface CliAvailability {
2
+ claude: boolean;
3
+ codex: boolean;
4
+ }
5
+ /**
6
+ * Checks if Claude Code CLI is installed.
7
+ * Uses `claude --version` to verify the binary exists.
8
+ */
9
+ export declare function isClaudeCliInstalled(): boolean;
10
+ /**
11
+ * Checks if Codex CLI is installed.
12
+ * Uses `codex --version` to verify the binary exists.
13
+ */
14
+ export declare function isCodexCliInstalled(): boolean;
15
+ /**
16
+ * Detects which coding CLIs are available on the system.
17
+ * Returns an object indicating availability of each CLI.
18
+ */
19
+ export declare function detectAvailableClis(): CliAvailability;
20
+ /**
21
+ * Checks if at least one coding CLI is available.
22
+ * Returns true if either Claude or Codex CLI is installed.
23
+ */
24
+ export declare function hasAnyCli(availability: CliAvailability): boolean;
25
+ //# sourceMappingURL=cli-detection.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli-detection.d.ts","sourceRoot":"","sources":["../../src/lib/cli-detection.ts"],"names":[],"mappings":"AAGA,MAAM,WAAW,eAAe;IAC9B,MAAM,EAAE,OAAO,CAAC;IAChB,KAAK,EAAE,OAAO,CAAC;CAChB;AAED;;;GAGG;AACH,wBAAgB,oBAAoB,IAAI,OAAO,CAW9C;AAED;;;GAGG;AACH,wBAAgB,mBAAmB,IAAI,OAAO,CAW7C;AAED;;;GAGG;AACH,wBAAgB,mBAAmB,IAAI,eAAe,CAKrD;AAED;;;GAGG;AACH,wBAAgB,SAAS,CAAC,YAAY,EAAE,eAAe,GAAG,OAAO,CAEhE"}
@@ -0,0 +1,53 @@
1
+ import { execSync } from 'child_process';
2
+ /**
3
+ * Checks if Claude Code CLI is installed.
4
+ * Uses `claude --version` to verify the binary exists.
5
+ */
6
+ export function isClaudeCliInstalled() {
7
+ try {
8
+ execSync('claude --version', {
9
+ encoding: 'utf-8',
10
+ timeout: 5000,
11
+ stdio: ['pipe', 'pipe', 'pipe'],
12
+ });
13
+ return true;
14
+ }
15
+ catch {
16
+ return false;
17
+ }
18
+ }
19
+ /**
20
+ * Checks if Codex CLI is installed.
21
+ * Uses `codex --version` to verify the binary exists.
22
+ */
23
+ export function isCodexCliInstalled() {
24
+ try {
25
+ execSync('codex --version', {
26
+ encoding: 'utf-8',
27
+ timeout: 5000,
28
+ stdio: ['pipe', 'pipe', 'pipe'],
29
+ });
30
+ return true;
31
+ }
32
+ catch {
33
+ return false;
34
+ }
35
+ }
36
+ /**
37
+ * Detects which coding CLIs are available on the system.
38
+ * Returns an object indicating availability of each CLI.
39
+ */
40
+ export function detectAvailableClis() {
41
+ return {
42
+ claude: isClaudeCliInstalled(),
43
+ codex: isCodexCliInstalled(),
44
+ };
45
+ }
46
+ /**
47
+ * Checks if at least one coding CLI is available.
48
+ * Returns true if either Claude or Codex CLI is installed.
49
+ */
50
+ export function hasAnyCli(availability) {
51
+ return availability.claude || availability.codex;
52
+ }
53
+ //# sourceMappingURL=cli-detection.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli-detection.js","sourceRoot":"","sources":["../../src/lib/cli-detection.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAQzC;;;GAGG;AACH,MAAM,UAAU,oBAAoB;IAClC,IAAI,CAAC;QACH,QAAQ,CAAC,kBAAkB,EAAE;YAC3B,QAAQ,EAAE,OAAO;YACjB,OAAO,EAAE,IAAI;YACb,KAAK,EAAE,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,CAAC;SAChC,CAAC,CAAC;QACH,OAAO,IAAI,CAAC;IACd,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,KAAK,CAAC;IACf,CAAC;AACH,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,mBAAmB;IACjC,IAAI,CAAC;QACH,QAAQ,CAAC,iBAAiB,EAAE;YAC1B,QAAQ,EAAE,OAAO;YACjB,OAAO,EAAE,IAAI;YACb,KAAK,EAAE,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,CAAC;SAChC,CAAC,CAAC;QACH,OAAO,IAAI,CAAC;IACd,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,KAAK,CAAC;IACf,CAAC;AACH,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,mBAAmB;IACjC,OAAO;QACL,MAAM,EAAE,oBAAoB,EAAE;QAC9B,KAAK,EAAE,mBAAmB,EAAE;KAC7B,CAAC;AACJ,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,SAAS,CAAC,YAA6B;IACrD,OAAO,YAAY,CAAC,MAAM,IAAI,YAAY,CAAC,KAAK,CAAC;AACnD,CAAC"}
@@ -0,0 +1,4 @@
1
+ import { LLMProvider } from './provider.js';
2
+ export declare function createCodexProvider(): LLMProvider;
3
+ export declare function checkCodexLinearMcpConfigured(): boolean;
4
+ //# sourceMappingURL=codex.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"codex.d.ts","sourceRoot":"","sources":["../../src/lib/codex.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,WAAW,EAAgF,MAAM,eAAe,CAAC;AA4X1H,wBAAgB,mBAAmB,IAAI,WAAW,CAEjD;AAGD,wBAAgB,6BAA6B,IAAI,OAAO,CAOvD"}