indusagi-coding-agent 0.1.23 → 0.1.24

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 (213) hide show
  1. package/CHANGELOG.md +65 -0
  2. package/README.md +2 -0
  3. package/dist/cli/args.d.ts +117 -1
  4. package/dist/cli/args.d.ts.map +1 -1
  5. package/dist/cli/args.js +221 -52
  6. package/dist/cli/args.js.map +1 -1
  7. package/dist/cli/config-selector.d.ts +58 -2
  8. package/dist/cli/config-selector.d.ts.map +1 -1
  9. package/dist/cli/config-selector.js +130 -12
  10. package/dist/cli/config-selector.js.map +1 -1
  11. package/dist/cli/file-processor.d.ts +70 -2
  12. package/dist/cli/file-processor.d.ts.map +1 -1
  13. package/dist/cli/file-processor.js +240 -15
  14. package/dist/cli/file-processor.js.map +1 -1
  15. package/dist/cli/list-models.d.ts +63 -3
  16. package/dist/cli/list-models.d.ts.map +1 -1
  17. package/dist/cli/list-models.js +202 -27
  18. package/dist/cli/list-models.js.map +1 -1
  19. package/dist/cli/login-handler.d.ts +82 -8
  20. package/dist/cli/login-handler.d.ts.map +1 -1
  21. package/dist/cli/login-handler.js +410 -77
  22. package/dist/cli/login-handler.js.map +1 -1
  23. package/dist/cli/session-picker.d.ts +74 -2
  24. package/dist/cli/session-picker.d.ts.map +1 -1
  25. package/dist/cli/session-picker.js +236 -12
  26. package/dist/cli/session-picker.js.map +1 -1
  27. package/dist/core/agent-session.d.ts +214 -9
  28. package/dist/core/agent-session.d.ts.map +1 -1
  29. package/dist/core/agent-session.js +214 -9
  30. package/dist/core/agent-session.js.map +1 -1
  31. package/dist/core/bash-executor.d.ts +302 -12
  32. package/dist/core/bash-executor.d.ts.map +1 -1
  33. package/dist/core/bash-executor.js +302 -12
  34. package/dist/core/bash-executor.js.map +1 -1
  35. package/dist/core/diagnostics.d.ts +191 -0
  36. package/dist/core/diagnostics.d.ts.map +1 -1
  37. package/dist/core/diagnostics.js +142 -0
  38. package/dist/core/diagnostics.js.map +1 -1
  39. package/dist/core/event-bus.d.ts +146 -0
  40. package/dist/core/event-bus.d.ts.map +1 -1
  41. package/dist/core/event-bus.js +93 -0
  42. package/dist/core/event-bus.js.map +1 -1
  43. package/dist/core/export-html/ansi-to-html.d.ts +4 -0
  44. package/dist/core/export-html/ansi-to-html.d.ts.map +1 -1
  45. package/dist/core/export-html/ansi-to-html.js +4 -0
  46. package/dist/core/export-html/ansi-to-html.js.map +1 -1
  47. package/dist/core/export-html/index.d.ts +128 -0
  48. package/dist/core/export-html/index.d.ts.map +1 -1
  49. package/dist/core/export-html/index.js +128 -0
  50. package/dist/core/export-html/index.js.map +1 -1
  51. package/dist/core/export-html/tool-renderer.d.ts +4 -0
  52. package/dist/core/export-html/tool-renderer.d.ts.map +1 -1
  53. package/dist/core/export-html/tool-renderer.js +4 -0
  54. package/dist/core/export-html/tool-renderer.js.map +1 -1
  55. package/dist/core/keybindings.d.ts +142 -0
  56. package/dist/core/keybindings.d.ts.map +1 -1
  57. package/dist/core/keybindings.js +142 -0
  58. package/dist/core/keybindings.js.map +1 -1
  59. package/dist/core/model-registry.d.ts +98 -1
  60. package/dist/core/model-registry.d.ts.map +1 -1
  61. package/dist/core/model-registry.js +98 -1
  62. package/dist/core/model-registry.js.map +1 -1
  63. package/dist/core/model-resolver.d.ts +99 -1
  64. package/dist/core/model-resolver.d.ts.map +1 -1
  65. package/dist/core/model-resolver.js +99 -1
  66. package/dist/core/model-resolver.js.map +1 -1
  67. package/dist/core/prompt-templates.js.map +1 -1
  68. package/dist/core/session-manager.d.ts +127 -0
  69. package/dist/core/session-manager.d.ts.map +1 -1
  70. package/dist/core/session-manager.js +125 -0
  71. package/dist/core/session-manager.js.map +1 -1
  72. package/dist/core/skills.js.map +1 -1
  73. package/dist/core/subagents.js.map +1 -1
  74. package/dist/core/tools/bash.d.ts +391 -11
  75. package/dist/core/tools/bash.d.ts.map +1 -1
  76. package/dist/core/tools/bash.js +269 -2
  77. package/dist/core/tools/bash.js.map +1 -1
  78. package/dist/core/tools/edit.d.ts +284 -6
  79. package/dist/core/tools/edit.d.ts.map +1 -1
  80. package/dist/core/tools/edit.js +238 -0
  81. package/dist/core/tools/edit.js.map +1 -1
  82. package/dist/core/tools/find.d.ts +169 -5
  83. package/dist/core/tools/find.d.ts.map +1 -1
  84. package/dist/core/tools/find.js +136 -0
  85. package/dist/core/tools/find.js.map +1 -1
  86. package/dist/core/tools/grep.d.ts +285 -5
  87. package/dist/core/tools/grep.d.ts.map +1 -1
  88. package/dist/core/tools/grep.js +247 -0
  89. package/dist/core/tools/grep.js.map +1 -1
  90. package/dist/core/tools/ls.d.ts +6 -0
  91. package/dist/core/tools/ls.d.ts.map +1 -1
  92. package/dist/core/tools/ls.js +6 -0
  93. package/dist/core/tools/ls.js.map +1 -1
  94. package/dist/core/tools/read.d.ts +308 -7
  95. package/dist/core/tools/read.d.ts.map +1 -1
  96. package/dist/core/tools/read.js +231 -0
  97. package/dist/core/tools/read.js.map +1 -1
  98. package/dist/core/tools/webfetch.d.ts +118 -3
  99. package/dist/core/tools/webfetch.d.ts.map +1 -1
  100. package/dist/core/tools/webfetch.js +118 -3
  101. package/dist/core/tools/webfetch.js.map +1 -1
  102. package/dist/core/tools/websearch.d.ts +130 -3
  103. package/dist/core/tools/websearch.d.ts.map +1 -1
  104. package/dist/core/tools/websearch.js +130 -3
  105. package/dist/core/tools/websearch.js.map +1 -1
  106. package/dist/core/tools/write.d.ts +251 -5
  107. package/dist/core/tools/write.d.ts.map +1 -1
  108. package/dist/core/tools/write.js +210 -0
  109. package/dist/core/tools/write.js.map +1 -1
  110. package/dist/modes/interactive/components/assistant-message.d.ts +164 -1
  111. package/dist/modes/interactive/components/assistant-message.d.ts.map +1 -1
  112. package/dist/modes/interactive/components/assistant-message.js +164 -1
  113. package/dist/modes/interactive/components/assistant-message.js.map +1 -1
  114. package/dist/modes/interactive/components/bash-execution.d.ts +297 -1
  115. package/dist/modes/interactive/components/bash-execution.d.ts.map +1 -1
  116. package/dist/modes/interactive/components/bash-execution.js +297 -1
  117. package/dist/modes/interactive/components/bash-execution.js.map +1 -1
  118. package/dist/modes/interactive/components/tool-execution.d.ts.map +1 -1
  119. package/dist/modes/interactive/components/tool-execution.js +251 -1
  120. package/dist/modes/interactive/components/tool-execution.js.map +1 -1
  121. package/dist/modes/interactive/components/user-message.d.ts +186 -1
  122. package/dist/modes/interactive/components/user-message.d.ts.map +1 -1
  123. package/dist/modes/interactive/components/user-message.js +186 -1
  124. package/dist/modes/interactive/components/user-message.js.map +1 -1
  125. package/dist/modes/interactive/interactive-mode.d.ts +1567 -13
  126. package/dist/modes/interactive/interactive-mode.d.ts.map +1 -1
  127. package/dist/modes/interactive/interactive-mode.js +1567 -13
  128. package/dist/modes/interactive/interactive-mode.js.map +1 -1
  129. package/dist/modes/interactive/theme/theme.d.ts +422 -0
  130. package/dist/modes/interactive/theme/theme.d.ts.map +1 -1
  131. package/dist/modes/interactive/theme/theme.js +422 -0
  132. package/dist/modes/interactive/theme/theme.js.map +1 -1
  133. package/dist/modes/print-mode.d.ts +538 -5
  134. package/dist/modes/print-mode.d.ts.map +1 -1
  135. package/dist/modes/print-mode.js +538 -5
  136. package/dist/modes/print-mode.js.map +1 -1
  137. package/dist/modes/rpc/rpc-client.d.ts +921 -8
  138. package/dist/modes/rpc/rpc-client.d.ts.map +1 -1
  139. package/dist/modes/rpc/rpc-client.js +921 -8
  140. package/dist/modes/rpc/rpc-client.js.map +1 -1
  141. package/dist/modes/rpc/rpc-mode.d.ts +802 -9
  142. package/dist/modes/rpc/rpc-mode.d.ts.map +1 -1
  143. package/dist/modes/rpc/rpc-mode.js +802 -9
  144. package/dist/modes/rpc/rpc-mode.js.map +1 -1
  145. package/dist/modes/rpc/rpc-types.d.ts +356 -3
  146. package/dist/modes/rpc/rpc-types.d.ts.map +1 -1
  147. package/dist/modes/rpc/rpc-types.js +356 -3
  148. package/dist/modes/rpc/rpc-types.js.map +1 -1
  149. package/dist/modes/shared.d.ts +386 -0
  150. package/dist/modes/shared.d.ts.map +1 -0
  151. package/dist/modes/shared.js +543 -0
  152. package/dist/modes/shared.js.map +1 -0
  153. package/dist/utils/array.d.ts +389 -0
  154. package/dist/utils/array.d.ts.map +1 -0
  155. package/dist/utils/array.js +585 -0
  156. package/dist/utils/array.js.map +1 -0
  157. package/dist/utils/color-formatter.d.ts +318 -0
  158. package/dist/utils/color-formatter.d.ts.map +1 -0
  159. package/dist/utils/color-formatter.js +442 -0
  160. package/dist/utils/color-formatter.js.map +1 -0
  161. package/dist/utils/data-transformer.d.ts +326 -0
  162. package/dist/utils/data-transformer.d.ts.map +1 -0
  163. package/dist/utils/data-transformer.js +512 -0
  164. package/dist/utils/data-transformer.js.map +1 -0
  165. package/dist/utils/date-formatter.d.ts +281 -0
  166. package/dist/utils/date-formatter.d.ts.map +1 -0
  167. package/dist/utils/date-formatter.js +503 -0
  168. package/dist/utils/date-formatter.js.map +1 -0
  169. package/dist/utils/error-handler.d.ts +541 -0
  170. package/dist/utils/error-handler.d.ts.map +1 -0
  171. package/dist/utils/error-handler.js +726 -0
  172. package/dist/utils/error-handler.js.map +1 -0
  173. package/dist/utils/file-operations.d.ts +297 -0
  174. package/dist/utils/file-operations.d.ts.map +1 -0
  175. package/dist/utils/file-operations.js +505 -0
  176. package/dist/utils/file-operations.js.map +1 -0
  177. package/dist/utils/frontmatter.d.ts +268 -6
  178. package/dist/utils/frontmatter.d.ts.map +1 -1
  179. package/dist/utils/frontmatter.js +500 -21
  180. package/dist/utils/frontmatter.js.map +1 -1
  181. package/dist/utils/json-formatter.d.ts +259 -0
  182. package/dist/utils/json-formatter.d.ts.map +1 -0
  183. package/dist/utils/json-formatter.js +517 -0
  184. package/dist/utils/json-formatter.js.map +1 -0
  185. package/dist/utils/logger.d.ts +176 -0
  186. package/dist/utils/logger.d.ts.map +1 -0
  187. package/dist/utils/logger.js +346 -0
  188. package/dist/utils/logger.js.map +1 -0
  189. package/dist/utils/markdown-formatter.d.ts +211 -0
  190. package/dist/utils/markdown-formatter.d.ts.map +1 -0
  191. package/dist/utils/markdown-formatter.js +482 -0
  192. package/dist/utils/markdown-formatter.js.map +1 -0
  193. package/dist/utils/path-validator.d.ts +603 -0
  194. package/dist/utils/path-validator.d.ts.map +1 -0
  195. package/dist/utils/path-validator.js +870 -0
  196. package/dist/utils/path-validator.js.map +1 -0
  197. package/dist/utils/string-formatter.d.ts +609 -0
  198. package/dist/utils/string-formatter.d.ts.map +1 -0
  199. package/dist/utils/string-formatter.js +806 -0
  200. package/dist/utils/string-formatter.js.map +1 -0
  201. package/dist/utils/type-guards.d.ts +629 -0
  202. package/dist/utils/type-guards.d.ts.map +1 -0
  203. package/dist/utils/type-guards.js +662 -0
  204. package/dist/utils/type-guards.js.map +1 -0
  205. package/docs/COMPLETE-GUIDE.md +300 -0
  206. package/docs/MODES-ARCHITECTURE.md +565 -0
  207. package/docs/PRINT-MODE-GUIDE.md +456 -0
  208. package/docs/RPC-GUIDE.md +705 -0
  209. package/docs/UTILS-IMPLEMENTATION-SUMMARY.md +647 -0
  210. package/docs/UTILS-MODULE-OVERVIEW.md +1480 -0
  211. package/docs/UTILS-QA-CHECKLIST.md +1061 -0
  212. package/docs/UTILS-USAGE-GUIDE.md +1419 -0
  213. package/package.json +1 -1
@@ -1,6 +1,167 @@
1
1
  /**
2
- * Interactive mode for the coding agent.
3
- * Handles TUI rendering and user interaction, delegating business logic to AgentSession.
2
+ * Interactive Mode - Terminal-based UI for interactive agent use
3
+ *
4
+ * ============================================================================
5
+ * PURPOSE
6
+ * ============================================================================
7
+ *
8
+ * Provides a full-featured terminal UI for interactive use of the coding agent.
9
+ * Handles rendering, keyboard input, session management, and real-time updates.
10
+ * This is the primary mode for direct user interaction with the agent.
11
+ *
12
+ * ============================================================================
13
+ * ARCHITECTURE
14
+ * ============================================================================
15
+ *
16
+ * Initialization Phase:
17
+ * - Create AgentSession with language model and tools
18
+ * - Load theme system and keyboard bindings
19
+ * - Initialize TUI (terminal user interface) library
20
+ * - Set up extension system with UI context
21
+ * - Load autocomplete provider with fd tool for file paths
22
+ *
23
+ * Rendering Phase:
24
+ * - Terminal layout: Header (logo/changelog) → Chat → Pending → Status → Widgets → Editor → Footer
25
+ * - Live rendering of agent messages with syntax highlighting
26
+ * - Real-time tool execution display with collapsible output
27
+ * - Thinking block display (can be toggled via settings)
28
+ * - Auto-scrolling to latest message
29
+ *
30
+ * Input Phase:
31
+ * - Keyboard event handling via TUI key system
32
+ * - Command parsing (/command format)
33
+ * - Slash command autocomplete with fuzzy filtering
34
+ * - File path completion via fd tool
35
+ * - Multi-line editor support with Ctrl+J to continue
36
+ *
37
+ * State Management:
38
+ * - Subscribe to AgentSession events (messages, tools, compaction)
39
+ * - Update display on each event
40
+ * - Maintain streaming component state for incremental rendering
41
+ * - Track tool execution components for expansion control
42
+ *
43
+ * ============================================================================
44
+ * DATA FLOW
45
+ * ============================================================================
46
+ *
47
+ * User Input Flow:
48
+ * User Input (keyboard)
49
+ * ↓
50
+ * TUI Key Handler (in setupKeyHandlers)
51
+ * ↓
52
+ * Command Parser (parseSlashCommand or plain text)
53
+ * ↓
54
+ * Command Handler or session.prompt()
55
+ * ↓
56
+ * AgentSession.prompt() executes agent loop
57
+ * ↓
58
+ * Agent emits AgentSessionEvent (message, tool, etc.)
59
+ * ↓
60
+ * Event Subscriber in InteractiveMode (subscribeToAgent)
61
+ * ↓
62
+ * Display Update (render message, tool, status)
63
+ * ↓
64
+ * TUI Invalidate → requestRender()
65
+ * ↓
66
+ * Terminal Output Rendered
67
+ *
68
+ * Event Processing Flow:
69
+ * agent_start → Show loading animation
70
+ * message_streamed → Stream text to AssistantMessageComponent
71
+ * tool_call → Create ToolExecutionComponent, show in pending area
72
+ * tool_output → Update tool component with result
73
+ * message_complete → Move message to chat, hide loading
74
+ * compaction_start → Show compaction loader
75
+ * compaction_complete → Update with summary message
76
+ *
77
+ * ============================================================================
78
+ * KEY COMPONENTS
79
+ * ============================================================================
80
+ *
81
+ * Renderer:
82
+ * - TUI: Core terminal rendering library (from indusagi/tui)
83
+ * - Components: Markdown, Text, Container, ProcessTerminal, etc.
84
+ * - Handles ANSI codes for colors, styles, and terminal control
85
+ * - Manages viewport size and automatic text wrapping
86
+ *
87
+ * InputHandler:
88
+ * - CustomEditor: Multi-line editor with autocomplete
89
+ * - KeybindingsManager: Keyboard shortcut configuration
90
+ * - Autocomplete: Slash commands, file paths, templates
91
+ * - Command Parser: Processes /settings, /model, /fork, etc.
92
+ *
93
+ * DisplayManager:
94
+ * - InteractiveMode class: Orchestrates all display updates
95
+ * - Container hierarchy: ChatContainer, PendingMessagesContainer, StatusContainer
96
+ * - Session display: Shows messages, tools, thinking blocks
97
+ * - Component tracking: streamingComponent, pendingTools, etc.
98
+ *
99
+ * ThemeManager:
100
+ * - Theme system: Colors, styles, layout options
101
+ * - EditorTheme: Syntax highlighting for code
102
+ * - MarkdownTheme: Rendering options for markdown
103
+ * - Theme switching: Hot reload on theme file changes
104
+ * - Custom themes: Load from .indusagi/themes/*.json
105
+ *
106
+ * Extension System:
107
+ * - ExtensionRunner: Manages registered extensions
108
+ * - ExtensionUIContext: TUI-based UI for extensions
109
+ * - Extension shortcuts: Keyboard shortcuts from extensions
110
+ * - Extension widgets: Custom UI above/below editor
111
+ * - Extension commands: Custom slash commands
112
+ *
113
+ * SessionManager:
114
+ * - Session state tracking: Model, messages, tools
115
+ * - Session persistence: Save/load from disk
116
+ * - Branching: Create branches from previous messages
117
+ * - Tree navigation: Switch between branches
118
+ *
119
+ * ============================================================================
120
+ * KEY FEATURES
121
+ * ============================================================================
122
+ *
123
+ * Real-time Streaming:
124
+ * - Stream agent responses token-by-token
125
+ * - Show tool execution in real-time
126
+ * - Display thinking blocks (if enabled)
127
+ * - Syntax highlighting for code blocks
128
+ *
129
+ * Interactive Commands:
130
+ * - /settings: Open settings menu
131
+ * - /model: Select language model
132
+ * - /fork: Create branch from previous message
133
+ * - /tree: Navigate session tree
134
+ * - /export: Export to HTML
135
+ * - /compact: Manually compact session
136
+ * - /new: Start new session
137
+ *
138
+ * Session Management:
139
+ * - Save/load sessions from disk
140
+ * - Branch creation and navigation
141
+ * - Automatic context compaction
142
+ * - Session switching
143
+ *
144
+ * Customization:
145
+ * - Custom themes
146
+ * - Keyboard bindings
147
+ * - Settings (quiet startup, collapse changelog, etc.)
148
+ * - Editor options (padding, tab width, etc.)
149
+ *
150
+ * ============================================================================
151
+ * BASED ON INDUSAGI VENDOR
152
+ * ============================================================================
153
+ *
154
+ * This interactive mode implementation is based on indusagi, a terminal UI
155
+ * toolkit and agent framework maintained at:
156
+ * https://github.com/varunisrani/indusagi-ts
157
+ *
158
+ * Vendor packages used:
159
+ * - indusagi/tui: Terminal UI components and rendering
160
+ * - indusagi/ai: AI model interfaces and chat protocol
161
+ * - indusagi/agent: Core agent session and event system
162
+ *
163
+ * Attribution: Builds on proven TUI patterns and architectural decisions
164
+ * from the original indusagi implementation.
4
165
  */
5
166
  import { type ImageContent } from "indusagi/ai";
6
167
  import { type AgentSession } from "../../core/agent-session.js";
@@ -21,6 +182,357 @@ export interface InteractiveModeOptions {
21
182
  /** Force verbose startup (overrides quietStartup setting) */
22
183
  verbose?: boolean;
23
184
  }
185
+ /**
186
+ * ============================================================================
187
+ * INTERACTIVE MODE - RENDERING ORCHESTRATION & PIPELINE
188
+ * ============================================================================
189
+ *
190
+ * COMPREHENSIVE RENDERING DOCUMENTATION:
191
+ * ============================================================================
192
+ *
193
+ * This section documents the complete rendering pipeline from session state
194
+ * to terminal output. The InteractiveMode class manages the TUI layout,
195
+ * message rendering, and real-time updates for the interactive agent interface.
196
+ *
197
+ * RENDERING PIPELINE OVERVIEW:
198
+ * ============================================================================
199
+ * End-to-End Flow (from user input to terminal display):
200
+ *
201
+ * User Input (keyboard event)
202
+ * ↓
203
+ * TUI key handler → setupKeyHandlers()
204
+ * ↓
205
+ * Command parser (parseSlashCommand or plaintext)
206
+ * ↓
207
+ * Handler: session.prompt(text) or special command
208
+ * ↓
209
+ * AgentSession processes (calls LLM, tools, etc.)
210
+ * ↓
211
+ * Agent emits events: message_streamed, tool_output, etc.
212
+ * ↓
213
+ * Event handler: subscribeToAgent() listeners
214
+ * ↓
215
+ * Display update: addMessageToChat() or component.updateResult()
216
+ * ↓
217
+ * TUI invalidate() → ui.requestRender()
218
+ * ↓
219
+ * TUI render() → compute layout (width, height, wrapping)
220
+ * ↓
221
+ * Terminal output: ANSI codes to terminal device
222
+ * ↓
223
+ * User sees updated chat with new message
224
+ *
225
+ * LAYOUT STRUCTURE:
226
+ * ============================================================================
227
+ * Terminal Layout (top to bottom):
228
+ *
229
+ * ┌─────────────────────────────────────────────────────┐
230
+ * │ [Logo/Changelog] (conditionally shown at startup) │ 1-10 lines
231
+ * ├─────────────────────────────────────────────────────┤
232
+ * │ │
233
+ * │ Chat Messages (scrollable, grows downward) │ N lines
234
+ * │ ├─ User message (background colored) │
235
+ * │ ├─ Assistant message │
236
+ * │ ├─ Tool execution (pending or complete) │
237
+ * │ └─ ...more messages... │
238
+ * │ │
239
+ * ├─────────────────────────────────────────────────────┤
240
+ * │ Pending Messages (tools being executed) │ 1-20 lines
241
+ * │ ├─ Tool call (pending background) │
242
+ * │ └─ ...more pending tools... │
243
+ * ├─────────────────────────────────────────────────────┤
244
+ * │ Status Line (operation status) │ 1 line
245
+ * │ "Thinking..." or "Reading files..." or "Complete" │
246
+ * ├─────────────────────────────────────────────────────┤
247
+ * │ [Widgets] (optional, from extensions) │ 0-5 lines
248
+ * ├─────────────────────────────────────────────────────┤
249
+ * │ [Editor] (multi-line input) │ 3-10 lines
250
+ * │ > User typing here... │
251
+ * │ > Can span multiple lines │
252
+ * ├─────────────────────────────────────────────────────┤
253
+ * │ [Footer] (status, model, etc.) │ 1 line
254
+ * │ Model: GPT-4 | Tokens: 4,251 | Compaction: ... │
255
+ * └─────────────────────────────────────────────────────┘
256
+ *
257
+ * Container Hierarchy:
258
+ * - mainContainer: Root container for entire UI
259
+ * ├── logoContainer: Logo/changelog (conditional)
260
+ * ├── chatContainer: All completed messages
261
+ * ├── pendingMessagesContainer: Tools being executed
262
+ * ├── statusContainer: Status line
263
+ * ├── widgetsContainer: Extension widgets
264
+ * ├── editorContainer: Multi-line input
265
+ * └── footerComponent: Status bar at bottom
266
+ *
267
+ * RENDERING MODES:
268
+ * ============================================================================
269
+ *
270
+ * 1. INITIAL LOAD (renderInitialMessages):
271
+ * Purpose: Display all messages when session loads
272
+ * Process:
273
+ * a. Session manager builds aligned message context
274
+ * b. Iterate through all messages (oldest to newest)
275
+ * c. For each assistant message:
276
+ * - Create AssistantMessageComponent
277
+ * - For each tool call in message:
278
+ * - Create ToolExecutionComponent (no result yet)
279
+ * - Render to chatContainer
280
+ * d. For each tool result message:
281
+ * - Find matching pending tool
282
+ * - Call component.updateResult()
283
+ * - Remove from pending map
284
+ * e. Update footer (token count, context info)
285
+ * f. Add user messages to editor history (for Up arrow)
286
+ * g. Call ui.requestRender()
287
+ *
288
+ * 2. STREAMING UPDATES (handleEvent):
289
+ * Purpose: Update display as agent processes real-time
290
+ * Process:
291
+ * a. Agent emits message_streamed event
292
+ * b. Extract message from event.message
293
+ * c. Create/update component:
294
+ * - First event: Create AssistantMessageComponent
295
+ * - Subsequent events: Call component.updateContent()
296
+ * d. Add to chatContainer if first event
297
+ * e. Update footer status (show operation in progress)
298
+ * f. TUI invalidate() and requestRender()
299
+ * Optimization:
300
+ * - Streaming component cached (one per assistant message)
301
+ * - Only call updateContent() on new content (not full rebuild)
302
+ * - Markdown rendering is lazy-cached by TUI library
303
+ *
304
+ * 3. TOOL EXECUTION (handleEvent + renderSessionContext):
305
+ * Purpose: Show tool calls and their results
306
+ * Process:
307
+ * a. Agent emits message_update (tool call started)
308
+ * b. Render tool call with pending background
309
+ * c. Tool executes (could take seconds/minutes)
310
+ * d. Agent emits tool_output event
311
+ * e. Find tool component in pendingTools map
312
+ * f. Call component.updateResult()
313
+ * g. Pending background changes to success/error
314
+ * h. Remove from pendingTools (completed)
315
+ * i. User can expand/collapse output via toolOutputExpanded setting
316
+ *
317
+ * 4. REAL-TIME BASH (handleBashCommand):
318
+ * Purpose: Stream bash output line-by-line
319
+ * Process:
320
+ * a. User types !! command
321
+ * b. Create BashExecutionComponent
322
+ * c. Start bash execution (async)
323
+ * d. Agent streams stdout chunks
324
+ * e. For each chunk:
325
+ * - Call component.appendOutput()
326
+ * - Component appends to outputLines
327
+ * - Call updateDisplay() and requestRender()
328
+ * f. When done, call component.setComplete()
329
+ * g. Show exit code or cancellation message
330
+ *
331
+ * 5. REBUILD (rebuildChatFromMessages):
332
+ * Purpose: Clear and re-render after settings change or recovery
333
+ * Process:
334
+ * a. Clear chatContainer
335
+ * b. Call renderInitialMessages()
336
+ * c. All messages re-created with new settings
337
+ * d. Useful for: thinking block toggle, theme change, etc.
338
+ *
339
+ * STYLING & COLOR SCHEME:
340
+ * ============================================================================
341
+ * Message Type Colors:
342
+ * - User message: userMessageBg + userMessageText (background + text)
343
+ * - Assistant: Normal markdown colors (no background)
344
+ * - Tool pending: toolPendingBg (neutral during execution)
345
+ * - Tool success: toolSuccessBg (green tint after success)
346
+ * - Tool error: toolErrorBg (red tint after error)
347
+ * - Bash: bashMode color (border + command)
348
+ * - Error: theme.fg("error", text) (red)
349
+ * - Warning: theme.fg("warning", text) (yellow)
350
+ * - Muted: theme.fg("muted", text) (dim/gray)
351
+ *
352
+ * Code Highlighting:
353
+ * - Markdown: Full markdown with syntax-highlighted code blocks
354
+ * - Code inline: Monospace with color
355
+ * - Code block: Full syntax highlighting via highlight.js
356
+ * - Languages detected from file extensions
357
+ * - Theme provides editor theme for highlighting
358
+ *
359
+ * Spacing & Layout:
360
+ * - Line height: 1 logical line per message (no double spacing)
361
+ * - Margins: Spacer(1) before each message type
362
+ * - Padding: 1 char left/right within backgrounds
363
+ * - Terminal width: Auto-wrap text to terminal width
364
+ * - Viewport: Scrollable (auto-scroll to bottom on new message)
365
+ *
366
+ * PERFORMANCE CONSIDERATIONS:
367
+ * ============================================================================
368
+ *
369
+ * Streaming Performance:
370
+ * - Streaming component cached: Only one active at a time
371
+ * - Markdown incremental: TUI library caches rendering
372
+ * - Invalidate efficient: Only re-renders changed container
373
+ * - Suitable for: 100+ stream updates without lag
374
+ *
375
+ * Large Conversations:
376
+ * - Tool caching: pendingTools map (fast lookup by ID)
377
+ * - Lazy rendering: Messages only rendered when visible
378
+ * - No 1000+ message overhead with proper viewport management
379
+ * - Compaction system: Auto-summarizes old messages to save memory
380
+ *
381
+ * Image Handling:
382
+ * - Async conversion: Non-blocking PNG conversion for Kitty protocol
383
+ * - Lazy loading: Images loaded when result arrives
384
+ * - Format detection: MIME type checked, converted if needed
385
+ * - Display control: showImages setting filters images
386
+ *
387
+ * Diff Computation:
388
+ * - Async preview: Edit diff computed before tool runs
389
+ * - Result override: Post-execution diff takes priority
390
+ * - Caching: Results cached to avoid re-computation
391
+ * - Race handling: File modifications between preview/execution
392
+ *
393
+ * INTERACTIVE FEATURES:
394
+ * ============================================================================
395
+ *
396
+ * Keyboard Controls:
397
+ * - Enter: Send message
398
+ * - Ctrl-J: Continue multi-line message
399
+ * - Arrow Up: Recall previous message from history
400
+ * - /settings: Open settings dialog
401
+ * - /model: Select language model
402
+ * - Tab: Autocomplete
403
+ * - Ctrl-C: Cancel current operation or exit
404
+ *
405
+ * Expandable Elements:
406
+ * - Tool output: Expand to see full output (toolOutputExpanded setting)
407
+ * - Code blocks: Expand long code to show all lines
408
+ * - Tool list: Expand to show all matching tools
409
+ * - Bash output: Expand from preview (20 lines) to full
410
+ *
411
+ * Real-time Status:
412
+ * - Status line: Shows current operation (thinking, reading, writing)
413
+ * - Footer: Token count, model name, session info
414
+ * - Loader: Animated spinner for long operations
415
+ * - Progress: Some operations show progress indicator
416
+ *
417
+ * Session Management:
418
+ * - Fork: Create branch from previous message
419
+ * - Tree: Navigate between branches
420
+ * - Save: Auto-save to .indusagi/sessions/
421
+ * - Resume: Load previous session on startup
422
+ *
423
+ * EXAMPLE RENDERING SEQUENCES:
424
+ * ============================================================================
425
+ *
426
+ * Sequence 1: User Prompt → Assistant Response
427
+ * ─────────────────────────────────────────────
428
+ *
429
+ * 1. User types "read src/main.ts" and presses Enter
430
+ * 2. CustomEditor captures text and clears
431
+ * 3. session.prompt(text) called
432
+ * 4. Agent starts processing
433
+ * 5. Agent emits message_streamed with assistant message (empty)
434
+ * → CreateAssistantMessageComponent, add to chatContainer
435
+ * → Show status "Thinking..."
436
+ * 6. Agent streams text tokens "I'll read the file..."
437
+ * → component.updateContent(), add text to message
438
+ * → invalidate() and requestRender()
439
+ * 7. Agent detects tool call (read)
440
+ * → Emit message_update with tool call
441
+ * → CreateToolExecutionComponent, add to chatContainer
442
+ * → pendingTools["id"] = component
443
+ * 8. Tool executes on server
444
+ * 9. Agent emits tool_output with result
445
+ * → Find component in pendingTools["id"]
446
+ * → component.updateResult(result)
447
+ * → Remove from pendingTools
448
+ * → Background changes from pending to success
449
+ * 10. Agent completes
450
+ * → Hide status line
451
+ * → Show footer with token count
452
+ * 11. Entire sequence rendered to terminal
453
+ *
454
+ * Sequence 2: Real-time Bash Output
455
+ * ──────────────────────────────────
456
+ *
457
+ * 1. User types "!!ls -la /src" and presses Enter
458
+ * 2. handleBashCommand() parses and creates BashExecutionComponent
459
+ * 3. Component shows header and loader
460
+ * 4. Shell command starts (async)
461
+ * 5. Shell outputs "total 128\ndrwx..." chunk 1
462
+ * → component.appendOutput(chunk)
463
+ * → outputLines = ["total 128", "drwx..."]
464
+ * → updateDisplay() and requestRender()
465
+ * 6. Shell outputs "-rw-r--..." chunk 2
466
+ * → component.appendOutput(chunk)
467
+ * → outputLines += ["-rw-r--..."]
468
+ * → updateDisplay() and requestRender()
469
+ * 7. Shell outputs "(exit 0)" and completes
470
+ * → component.setComplete(0, false, ...)
471
+ * → Loader stops, exit code shown
472
+ * → updateDisplay() and requestRender()
473
+ * 8. Final output rendered to terminal
474
+ *
475
+ * TERMINAL DIMENSIONS & WRAPPING:
476
+ * ============================================================================
477
+ *
478
+ * Width Handling:
479
+ * - Terminal width from ui.terminal.columns
480
+ * - TUI library auto-wraps text at this width
481
+ * - Code blocks may overflow (user can scroll horizontally)
482
+ * - Table rendering respects width (may abbreviate cells)
483
+ *
484
+ * Height Handling:
485
+ * - Terminal height from ui.terminal.rows
486
+ * - mainContainer grows as needed (scrollable)
487
+ * - Chat area expands to fill available space
488
+ * - Footer always at bottom (fixed)
489
+ * - Editor always above footer (fixed)
490
+ *
491
+ * Dynamic Resizing:
492
+ * - TUI detects terminal resize (SIGWINCH)
493
+ * - All components re-render with new dimensions
494
+ * - invalidate() called on all containers
495
+ * - Visual line truncation recached (width-aware)
496
+ * - Auto-scroll adjusted to show latest message
497
+ *
498
+ * Text Truncation:
499
+ * - Long lines: Wrapped automatically by TUI
500
+ * - Visual truncation: truncateToVisualLines() respects width
501
+ * - Ellipsis: "..." used to indicate truncation
502
+ * - Hints: Show "(to expand)" for cut-off content
503
+ *
504
+ * INTEGRATION WITH EXTENSIONS:
505
+ * ============================================================================
506
+ *
507
+ * Custom Renderers:
508
+ * - Extension provides renderCall() and renderResult()
509
+ * - Called from ToolExecutionComponent.updateDisplay()
510
+ * - Custom components rendered within tool box
511
+ * - Falls back to built-in rendering if custom fails
512
+ *
513
+ * Custom Commands:
514
+ * - Extension registers slash command handler
515
+ * - Command handler called from InteractiveMode.handleCommand()
516
+ * - Can show dialogs, update display, etc.
517
+ * - Can access session and TUI for rendering
518
+ *
519
+ * Widgets:
520
+ * - Extension provides widget component
521
+ * - Rendered in widgetsContainer above editor
522
+ * - Can show status, buttons, controls, etc.
523
+ * - Multiple widgets stack vertically
524
+ *
525
+ * SEE ALSO:
526
+ * ============================================================================
527
+ * - AssistantMessageComponent: Text/thinking rendering
528
+ * - UserMessageComponent: User prompt rendering
529
+ * - ToolExecutionComponent: Tool call/result rendering
530
+ * - BashExecutionComponent: Real-time bash output
531
+ * - renderInitialMessages(): Full session rendering
532
+ * - renderSessionContext(): Message-by-message rendering
533
+ * - handleEvent(): Real-time event processing
534
+ * - subscribeToAgent(): Event subscription setup
535
+ */
24
536
  export declare class InteractiveMode {
25
537
  private options;
26
538
  private session;
@@ -79,14 +591,89 @@ export declare class InteractiveMode {
79
591
  constructor(session: AgentSession, options?: InteractiveModeOptions);
80
592
  private setupAutocomplete;
81
593
  private rebuildAutocomplete;
594
+ /**
595
+ * Initialize the interactive mode UI and extensions.
596
+ *
597
+ * PURPOSE:
598
+ * Sets up the terminal UI, keyboard handlers, event subscriptions, and extension system.
599
+ * This prepares the interactive mode for user interaction. Must be called before run().
600
+ *
601
+ * PROCESS:
602
+ * 1. Load changelog entries and check for initial messages
603
+ * 2. Ensure fd tool is available for file path autocomplete
604
+ * 3. Build autocomplete provider (slash commands, templates, extensions, skills)
605
+ * 4. Initialize TUI with header (logo, keybinding hints, changelog)
606
+ * 5. Add layout components (chat, pending, status, widgets, editor, footer)
607
+ * 6. Set up keyboard handlers (key bindings, editor events)
608
+ * 7. Start the TUI (terminal raw mode, enable mouse, etc.)
609
+ * 8. Initialize extension system with TUI-based UI context
610
+ * 9. Subscribe to agent events (messages, tools, compaction, retry)
611
+ * 10. Set up theme file watcher for hot reload
612
+ * 11. Set up git branch watcher for footer
613
+ * 12. Initialize available provider count for display
614
+ *
615
+ * PARAMETERS:
616
+ * None - uses constructor options for initial messages and warnings
617
+ *
618
+ * RETURNS:
619
+ * Promise<void> - resolves when initialization is complete
620
+ *
621
+ * STATE CHANGES:
622
+ * - Sets isInitialized flag to true
623
+ * - Starts TUI (terminal is in raw mode after this)
624
+ * - Sets terminal title with session name
625
+ * - Subscribes to agent events and theme changes
626
+ *
627
+ * NOTES:
628
+ * - Must be idempotent (calling twice does nothing on second call)
629
+ * - Extension system is fully initialized here
630
+ * - Changelog is only shown for new sessions, not resumed ones
631
+ */
82
632
  init(): Promise<void>;
83
633
  /**
84
634
  * Update terminal title with session name and cwd.
85
635
  */
86
636
  private updateTerminalTitle;
87
637
  /**
88
- * Run the interactive mode. This is the main entry point.
89
- * Initializes the UI, shows warnings, processes initial messages, and starts the interactive loop.
638
+ * Run the interactive mode main loop.
639
+ *
640
+ * PURPOSE:
641
+ * Main entry point for interactive mode. Initializes UI, displays startup info,
642
+ * processes initial messages, and enters the interactive user input loop.
643
+ * Never returns under normal operation (runs until user exits with /quit, Ctrl+D, etc.).
644
+ *
645
+ * PROCESS:
646
+ * 1. Call init() to set up UI, keyboard handlers, extensions
647
+ * 2. Start version check asynchronously (shows notification if newer version available)
648
+ * 3. Render initial session messages from previous session (if resumed)
649
+ * 4. Show startup warnings:
650
+ * - Migrated provider credentials
651
+ * - models.json parsing errors
652
+ * - Model fallback message (if model couldn't be restored)
653
+ * 5. Process initial messages from options (--message, --initial-message):
654
+ * - Send each via session.prompt()
655
+ * - Catch and display errors
656
+ * 6. Start interactive loop:
657
+ * a. Wait for user input (getUserInput waits for editor.onSubmit)
658
+ * b. Send input to session.prompt()
659
+ * c. Loop continues until shutdown (process.exit)
660
+ *
661
+ * PARAMETERS:
662
+ * None - uses constructor options for initial messages and warnings
663
+ *
664
+ * RETURNS:
665
+ * Promise<void> - never resolves (runs until process.exit is called)
666
+ *
667
+ * STATE CHANGES:
668
+ * - Initializes all UI components
669
+ * - Starts the interactive input loop
670
+ * - Updates footer/display as agent processes messages
671
+ * - May create new sessions, fork, navigate tree, etc. based on commands
672
+ *
673
+ * NOTES:
674
+ * - Must call init() first
675
+ * - Handles all errors from session.prompt() and displays them
676
+ * - Runs forever - shutdown happens via /quit, Ctrl+D, or extension shutdown signal
90
677
  */
91
678
  run(): Promise<void>;
92
679
  /**
@@ -126,6 +713,63 @@ export declare class InteractiveMode {
126
713
  private showLoadedResources;
127
714
  /**
128
715
  * Initialize the extension system with TUI-based UI context.
716
+ *
717
+ * PURPOSE:
718
+ * Set up extensions with UI capabilities. Creates ExtensionUIContext for
719
+ * extensions to use for dialogs, widgets, status messages, etc.
720
+ * Binds command context actions, error handlers, and shutdown handler.
721
+ *
722
+ * PROCESS:
723
+ * 1. If no extension runner: show loaded resources and return
724
+ * 2. Create ExtensionUIContext with:
725
+ * a. Dialog methods (select, confirm, input, notify)
726
+ * b. Status/title setters
727
+ * c. Widget and footer/header setters
728
+ * d. Editor interaction methods
729
+ * e. Theme access and switching
730
+ * 3. Call session.bindExtensions() with:
731
+ * a. uiContext - for TUI dialogs
732
+ * b. commandContextActions - for /fork, /tree, /new actions
733
+ * c. shutdownHandler - called when extension wants to exit
734
+ * d. Error handlers - for extension and hook errors
735
+ * 4. Set up extension shortcuts (keyboard bindings from extensions)
736
+ * 5. Show loaded resources (extensions, skills, prompts, themes)
737
+ *
738
+ * EXTENSION CAPABILITIES:
739
+ * - Show dialogs (selectors, confirmations, inputs)
740
+ * - Display persistent widgets above/below editor
741
+ * - Set custom footer and header
742
+ * - Customize editor component
743
+ * - Register keyboard shortcuts
744
+ * - Request shutdown
745
+ * - Access theme system
746
+ *
747
+ * COMMAND CONTEXT ACTIONS:
748
+ * - waitForIdle(): Wait until agent is idle
749
+ * - newSession(): Start a new session
750
+ * - fork(): Create branch from previous message
751
+ * - navigateTree(): Switch to different point in tree
752
+ *
753
+ * PARAMETERS:
754
+ * None
755
+ *
756
+ * RETURNS:
757
+ * Promise<void> - completes when extensions are initialized
758
+ *
759
+ * STATE CHANGES:
760
+ * - Binds extensions to session
761
+ * - Sets up shortcuts on defaultEditor
762
+ * - Displays loaded resources in chat
763
+ *
764
+ * NOTES:
765
+ * - Called from init() after TUI is started
766
+ * - Extensions can't affect UI until this completes
767
+ * - Error/hook errors displayed but don't stop initialization
768
+ * - Resources shown only if verbose or not quietStartup
769
+ *
770
+ * SEE ALSO:
771
+ * - createExtensionUIContext() for UI API details
772
+ * - setupExtensionShortcuts() for keyboard bindings
129
773
  */
130
774
  private initExtensions;
131
775
  /**
@@ -211,10 +855,312 @@ export declare class InteractiveMode {
211
855
  * Show a hook error in the UI.
212
856
  */
213
857
  private showHookError;
858
+ /**
859
+ * Set up keyboard event handlers for all key bindings.
860
+ *
861
+ * PURPOSE:
862
+ * Registers all keyboard shortcuts and special key handlers on the editor.
863
+ * Handles direct key events (Escape, Ctrl+D, etc.) and action dispatching
864
+ * for keybinding-mapped actions (clear, suspend, cycle models, etc.).
865
+ *
866
+ * KEY BINDINGS CONFIGURED:
867
+ *
868
+ * **Escape**:
869
+ * - If loading: restore queued messages and abort agent
870
+ * - Else if bash running: abort bash
871
+ * - Else if bash mode (!): clear input and exit bash mode
872
+ * - Else if editor has text: clear editor
873
+ * - Else double-escape with empty: open tree selector or fork selector
874
+ * (based on settings.doubleEscapeAction)
875
+ *
876
+ * **Ctrl+C** (mapped to "clear" action):
877
+ * - First press: clear editor
878
+ * - Second press within 500ms: exit application
879
+ *
880
+ * **Ctrl+D** (mapped via onCtrlD):
881
+ * - Only when editor is empty
882
+ * - Exit application immediately
883
+ *
884
+ * **Ctrl+Z** (mapped to "suspend" action):
885
+ * - Suspend terminal to background
886
+ * - Set up SIGCONT handler to restore TUI on resume
887
+ *
888
+ * **Ctrl+M** (mapped to "cycleThinkingLevel" action):
889
+ * - Cycle thinking level: off → low → medium → high → off
890
+ * - Update border color and footer
891
+ * - Show status message
892
+ *
893
+ * **Ctrl+N** (mapped to "cycleModelForward" action):
894
+ * - Cycle to next model in scope or registry
895
+ * - Update footer and border color
896
+ * - Show status with new model name
897
+ *
898
+ * **Ctrl+P** (mapped to "cycleModelBackward" action):
899
+ * - Cycle to previous model
900
+ *
901
+ * **Ctrl+L** (mapped to "selectModel" action):
902
+ * - Open model selector dialog
903
+ *
904
+ * **Ctrl+E** (mapped to "expandTools" action):
905
+ * - Toggle expansion state of all tool output components
906
+ * - Affects current and future tool displays
907
+ *
908
+ * **Ctrl+K** (mapped to "toggleThinking" action):
909
+ * - Toggle visibility of thinking blocks in all messages
910
+ * - Rebuild chat with updated visibility
911
+ *
912
+ * **Ctrl+X** (mapped to "externalEditor" action):
913
+ * - Open current editor content in $VISUAL or $EDITOR
914
+ * - Replace content on save
915
+ *
916
+ * **Alt+Enter** (mapped to "followUp" action):
917
+ * - If streaming: queue message to send after agent finishes
918
+ * - If idle: acts like regular Enter (trigger onSubmit)
919
+ *
920
+ * **Ctrl+J** (mapped to "dequeue" action):
921
+ * - Restore all queued messages back to editor
922
+ * - Show count of restored messages
923
+ *
924
+ * **Alt+Debug** (global on TUI, not editor):
925
+ * - Write debug log with terminal render state and agent messages
926
+ *
927
+ * **onChange**:
928
+ * - Track if text starts with ! to enter bash mode
929
+ * - Update editor border color (blue for bash, accent for thinking)
930
+ *
931
+ * **onPasteImage**:
932
+ * - Handle Ctrl+V clipboard image paste
933
+ * - Write to temp file, insert path in editor
934
+ *
935
+ * PARAMETERS:
936
+ * None - configures this.defaultEditor handlers
937
+ *
938
+ * RETURNS:
939
+ * void - side effects only
940
+ *
941
+ * STATE CHANGES:
942
+ * - Sets this.defaultEditor.onEscape, onSubmit, onChange, onCtrlD, onPasteImage
943
+ * - Sets this.defaultEditor action handlers (clear, suspend, etc.)
944
+ * - Sets this.ui.onDebug for global debug shortcut
945
+ *
946
+ * NOTES:
947
+ * - Handlers use this.editor (which may be custom from extension)
948
+ * - All handlers use updateEditorBorderColor() to reflect state
949
+ * - Extension shortcuts can override action handlers via registerShortcut()
950
+ * - Most handlers call updatePendingMessagesDisplay() to sync UI
951
+ */
214
952
  private setupKeyHandlers;
215
953
  private handleClipboardImagePaste;
954
+ /**
955
+ * Set up the editor submit handler for user input.
956
+ *
957
+ * PURPOSE:
958
+ * Configures the editor's onSubmit callback to process user input.
959
+ * This is called when the user presses Enter in the editor.
960
+ * Handles command parsing, slash commands, bash execution, and message queuing.
961
+ *
962
+ * INPUT TYPES PROCESSED:
963
+ *
964
+ * **Slash Commands** (commands starting with /):
965
+ * - /settings: Open settings selector menu
966
+ * - /scoped-models: Open model scoping selector
967
+ * - /model [search]: Open model selector or find exact match
968
+ * - /export [path]: Export session to HTML file
969
+ * - /share: Share session as secret GitHub gist
970
+ * - /copy: Copy last agent message to clipboard
971
+ * - /name [name]: Set or display session name
972
+ * - /session: Show session info and stats (messages, tokens, cost)
973
+ * - /changelog: Show full changelog entries
974
+ * - /hotkeys: Show all keyboard shortcuts
975
+ * - /fork: Show fork selector (pick message to branch from)
976
+ * - /tree: Show tree selector (navigate session DAG)
977
+ * - /login: Open OAuth or API key login selector
978
+ * - /logout: Open logout selector for saved credentials
979
+ * - /new, /clear: Start a new session
980
+ * - /compact [instructions]: Manually compact context
981
+ * - /reload: Reload extensions, skills, prompts, themes
982
+ * - /resume: Show session selector to switch sessions
983
+ * - /quit, /exit: Exit the application
984
+ *
985
+ * **Bash Commands** (text starting with ! or !!):
986
+ * - !command: Execute bash command, include output in context
987
+ * - !!command: Execute bash command, exclude from context (use !!)
988
+ * - Shows BashExecutionComponent with real-time output
989
+ * - Can be queued during streaming (moved to chat on next submit)
990
+ *
991
+ * **Prompt Templates** (custom /name commands):
992
+ * - Registered template names become slash commands
993
+ * - Can have placeholders and argument completion
994
+ * - Expanded and sent as regular messages
995
+ *
996
+ * **Extension Commands**:
997
+ * - Custom commands registered by extensions
998
+ * - Execute immediately even during streaming
999
+ * - Can provide argument completion
1000
+ *
1001
+ * **Regular Messages**:
1002
+ * - If streaming: queue with streaming behavior (steer/followUp)
1003
+ * - "steer": interrupt immediately
1004
+ * - "followUp": wait until response finishes
1005
+ * - If compacting: queue in compactionQueuedMessages
1006
+ * - If idle: send immediately
1007
+ * - Can include @file references for context injection
1008
+ *
1009
+ * COMMAND PARSING:
1010
+ * 1. Trim whitespace
1011
+ * 2. Check if it's a slash command (/command or /command arg)
1012
+ * 3. Check if it's a bash command (!cmd or !!cmd)
1013
+ * 4. Otherwise treat as regular message
1014
+ *
1015
+ * QUEUEING BEHAVIOR:
1016
+ * - During streaming: prompt() with streamingBehavior option
1017
+ * - During compaction: compactionQueuedMessages array
1018
+ * - Queued messages shown in pendingMessagesContainer
1019
+ * - Can be dequeued with Ctrl+J and edited
1020
+ *
1021
+ * PARAMETERS:
1022
+ * @param text - The submitted editor text (trimmed)
1023
+ *
1024
+ * RETURNS:
1025
+ * void - async, calls callbacks but doesn't return a value
1026
+ *
1027
+ * STATE CHANGES:
1028
+ * - Clears editor text on submit
1029
+ * - Adds to editor history (for Up arrow to recall)
1030
+ * - Updates pendingMessagesDisplay when queuing
1031
+ * - Moves pendingBashComponents to chat
1032
+ * - Calls session.prompt() or command handlers
1033
+ *
1034
+ * NOTES:
1035
+ * - Empty input is ignored
1036
+ * - All errors are caught and displayed via showError()
1037
+ * - Some commands suppress editor.addToHistory() (reload, etc.)
1038
+ * - Bash commands check if bash is already running and warn
1039
+ * - Must check isBashMode before allowing bash command execution
1040
+ */
216
1041
  private setupEditorSubmitHandler;
1042
+ /**
1043
+ * Subscribe to agent session events for UI updates.
1044
+ *
1045
+ * PURPOSE:
1046
+ * Sets up the event subscription to agent session. All agent activity (messages,
1047
+ * tool execution, compaction, retry, etc.) flows through here to update the display.
1048
+ * This is the bridge between the agent execution layer and the TUI rendering layer.
1049
+ *
1050
+ * PROCESS:
1051
+ * 1. Call session.subscribe() with an async event handler
1052
+ * 2. Save unsubscribe function for cleanup on shutdown
1053
+ * 3. Handler receives AgentSessionEvent objects and calls handleEvent()
1054
+ * 4. handleEvent() dispatches based on event type to update UI components
1055
+ *
1056
+ * EVENT TYPES HANDLED:
1057
+ * - `agent_start`: Show loading animation with working message
1058
+ * - `message_start`: Create new message component (user/assistant/custom)
1059
+ * - `message_update`: Stream content to message component, add tool calls
1060
+ * - `message_end`: Mark message complete, update tool results
1061
+ * - `tool_execution_start`: Create tool execution component in chat
1062
+ * - `tool_execution_update`: Stream partial tool results
1063
+ * - `tool_execution_end`: Mark tool complete with final result
1064
+ * - `agent_end`: Hide loading animation, check for shutdown request
1065
+ * - `auto_compaction_start`: Show compaction loader, allow escape to abort
1066
+ * - `auto_compaction_end`: Hide loader, rebuild chat, flush queued messages
1067
+ * - `auto_retry_start`: Show retry countdown loader
1068
+ * - `auto_retry_end`: Hide loader, show error only on failure
1069
+ *
1070
+ * PARAMETERS:
1071
+ * None - subscribes to this.session
1072
+ *
1073
+ * RETURNS:
1074
+ * void - side effects only (sets this.unsubscribe)
1075
+ *
1076
+ * NOTES:
1077
+ * - Called from init() after TUI is started
1078
+ * - Handles streaming content incrementally
1079
+ * - Must save unsubscribe function for cleanup in stop()
1080
+ * - Events are processed sequentially (not concurrent)
1081
+ */
217
1082
  private subscribeToAgent;
1083
+ /**
1084
+ * Handle a single agent session event and update the UI.
1085
+ *
1086
+ * PURPOSE:
1087
+ * Processes agent events and translates them into UI updates. This is the main
1088
+ * event dispatcher that receives all agent activity and renders it to the terminal.
1089
+ *
1090
+ * PROCESS FOR EACH EVENT TYPE:
1091
+ *
1092
+ * **agent_start**:
1093
+ * - Stop any existing loading animation
1094
+ * - Create new Loader component in statusContainer
1095
+ * - Apply pending working message if queued
1096
+ * - Request render
1097
+ *
1098
+ * **message_start**:
1099
+ * - User messages: render to chat immediately
1100
+ * - Assistant messages: create streaming component, add to chat
1101
+ * - Custom messages: render with extension renderer
1102
+ *
1103
+ * **message_update**:
1104
+ * - Stream new content to streamingComponent
1105
+ * - For each tool call: create or update ToolExecutionComponent
1106
+ * - Track tool components by ID for later result updates
1107
+ *
1108
+ * **message_end**:
1109
+ * - Mark streaming complete
1110
+ * - If aborted/error: set error message, mark all pending tools as error
1111
+ * - Otherwise: trigger diff computation for edit tools
1112
+ * - Clear streaming component reference
1113
+ *
1114
+ * **tool_execution_start/update/end**:
1115
+ * - Create or update ToolExecutionComponent in chat
1116
+ * - Stream partial results incrementally
1117
+ * - On completion: mark expanded state and remove from pending
1118
+ *
1119
+ * **agent_end**:
1120
+ * - Stop loading animation
1121
+ * - Clear streaming component from chat
1122
+ * - Clear pending tools
1123
+ * - Check for shutdown request (if extension called shutdown())
1124
+ *
1125
+ * **auto_compaction_start**:
1126
+ * - Show compaction loader with reason (overflow, etc.)
1127
+ * - Replace main escape handler to allow abort
1128
+ * - Editor stays active for queueing messages
1129
+ *
1130
+ * **auto_compaction_end**:
1131
+ * - Hide loader
1132
+ * - Rebuild chat to show compacted state
1133
+ * - Add compaction summary component
1134
+ * - Flush queued messages
1135
+ * - Handle completion, cancellation, or errors
1136
+ *
1137
+ * **auto_retry_start**:
1138
+ * - Show retry countdown (attempt N/M in delay seconds)
1139
+ * - Replace main escape handler to allow abort
1140
+ *
1141
+ * **auto_retry_end**:
1142
+ * - Hide loader
1143
+ * - Show error only on final failure (success shows normal response)
1144
+ *
1145
+ * PARAMETERS:
1146
+ * @param event - AgentSessionEvent (message, tool, compaction, retry, etc.)
1147
+ *
1148
+ * RETURNS:
1149
+ * Promise<void> - completes when UI update is done
1150
+ *
1151
+ * STATE CHANGES:
1152
+ * - Updates streamingComponent and streamingMessage
1153
+ * - Updates pendingTools map
1154
+ * - Updates loading animations (loadingAnimation, autoCompactionLoader, retryLoader)
1155
+ * - Updates UI via this.ui.requestRender()
1156
+ * - May call checkShutdownRequested() on agent_end
1157
+ *
1158
+ * NOTES:
1159
+ * - Initializes if not yet initialized (lazy init)
1160
+ * - Handles streaming content incremental rendering
1161
+ * - Events are sequential, not concurrent
1162
+ * - Tool components maintain expanded state across events
1163
+ */
218
1164
  private handleEvent;
219
1165
  /** Extract text content from a user message */
220
1166
  private getUserMessageText;
@@ -225,27 +1171,299 @@ export declare class InteractiveMode {
225
1171
  * we update the previous status line instead of appending new ones to avoid log spam.
226
1172
  */
227
1173
  private showStatus;
1174
+ /**
1175
+ * Render a single message to the chat display.
1176
+ *
1177
+ * PURPOSE:
1178
+ * Converts an AgentMessage into one or more UI components and adds to chatContainer.
1179
+ * Handles all message types with appropriate rendering, tool display, and formatting.
1180
+ *
1181
+ * MESSAGE TYPES HANDLED:
1182
+ *
1183
+ * **user**:
1184
+ * - Extract text content (ignore images/other content)
1185
+ * - Check for skill blocks (```skill block with instructions)
1186
+ * - If skill block found:
1187
+ * a. Render SkillInvocationMessageComponent (collapsible)
1188
+ * b. Render user message separately if non-skill text exists
1189
+ * - Otherwise render UserMessageComponent with full text
1190
+ * - Optionally add to editor history for Up arrow recall
1191
+ *
1192
+ * **assistant**:
1193
+ * - Create AssistantMessageComponent with streaming content
1194
+ * - Respect hideThinkingBlock setting for visibility
1195
+ * - Tool calls are handled separately in message_update event
1196
+ *
1197
+ * **custom**:
1198
+ * - Check message.display flag (if false, skip rendering)
1199
+ * - Use extension message renderer if available
1200
+ * - Render as CustomMessageComponent with markdown theme
1201
+ *
1202
+ * **toolResult**:
1203
+ * - Rendered inline with tool calls (not standalone)
1204
+ * - Handled during renderSessionContext() matching with tool calls
1205
+ *
1206
+ * **bashExecution**:
1207
+ * - Create BashExecutionComponent
1208
+ * - Show command and real-time output
1209
+ * - Mark complete with exit code and optional truncation info
1210
+ *
1211
+ * **compactionSummary**:
1212
+ * - Show how many tokens were saved during compaction
1213
+ * - Display summary of what was compacted
1214
+ * - Component respects toolOutputExpanded setting
1215
+ *
1216
+ * **branchSummary**:
1217
+ * - Show branch point with label
1218
+ * - Display custom instructions for navigation
1219
+ * - Component respects toolOutputExpanded setting
1220
+ *
1221
+ * PARAMETERS:
1222
+ * @param message - AgentMessage to render (any role type)
1223
+ * @param options.populateHistory - Add user text to editor history (default: false)
1224
+ *
1225
+ * RETURNS:
1226
+ * void - side effects only (adds components to chatContainer)
1227
+ *
1228
+ * STATE CHANGES:
1229
+ * - Adds components to chatContainer
1230
+ * - May update editor history
1231
+ * - Updates pendingTools map (indirectly in renderSessionContext)
1232
+ *
1233
+ * NOTES:
1234
+ * - Uses getMarkdownThemeWithSettings() for consistent rendering
1235
+ * - Respects current display settings (hideThinkingBlock, showImages, etc.)
1236
+ * - Tool calls are created separately during message_update event
1237
+ * - Skill blocks use parseSkillBlock() to extract instructions
1238
+ * - Images in messages are handled by markdown renderer
1239
+ * - Does NOT call ui.requestRender() (caller does)
1240
+ *
1241
+ * SEE ALSO:
1242
+ * - renderSessionContext() which calls this for all messages
1243
+ * - handleEvent() which creates components during streaming
1244
+ */
228
1245
  private addMessageToChat;
229
1246
  /**
230
- * Render session context to chat. Used for initial load and rebuild after compaction.
231
- * @param sessionContext Session context to render
232
- * @param options.updateFooter Update footer state
233
- * @param options.populateHistory Add user messages to editor history
1247
+ * Render a complete session context (all messages) to the chat display.
1248
+ *
1249
+ * PURPOSE:
1250
+ * Renders all aligned messages from a SessionContext to the chat display.
1251
+ * Handles message-to-tool-result matching and streaming state management.
1252
+ * Used during initial load, after compaction, and during rebuilds.
1253
+ *
1254
+ * PROCESS:
1255
+ * 1. Clear pendingTools map (reset tracking)
1256
+ * 2. Iterate through all messages in context:
1257
+ * - Assistant messages: render message + create tool components for each tool call
1258
+ * - Tool result messages: match to tool component, update result, remove from pending
1259
+ * - Other messages: render via addMessageToChat()
1260
+ * 3. Final clear of pendingTools (shouldn't have any left)
1261
+ * 4. Call ui.requestRender() to display changes
1262
+ *
1263
+ * TOOL CALL/RESULT MATCHING:
1264
+ * Tool calls and results are matched by ID:
1265
+ * 1. When rendering assistant message, create ToolExecutionComponent for each tool call
1266
+ * 2. Store component in pendingTools[toolCallId]
1267
+ * 3. When rendering tool result: look up component, update it, remove from pending
1268
+ * 4. If tool errored/aborted: mark component as error, don't add to pending
1269
+ *
1270
+ * PARAMETERS:
1271
+ * @param sessionContext - SessionContext from sessionManager.buildSessionContext()
1272
+ * @param options.updateFooter - Call footer.invalidate() and updateEditorBorderColor() (default: false)
1273
+ * @param options.populateHistory - Add user message text to editor history (default: false)
1274
+ *
1275
+ * RETURNS:
1276
+ * void - side effects only
1277
+ *
1278
+ * STATE CHANGES:
1279
+ * - Clears and repopulates chatContainer
1280
+ * - Updates pendingTools map (should be empty after completion)
1281
+ * - May call footer.invalidate() if updateFooter is true
1282
+ * - Calls ui.requestRender()
1283
+ *
1284
+ * NOTES:
1285
+ * - Used internally by renderInitialMessages() and rebuildChatFromMessages()
1286
+ * - All messages must be aligned (via sessionManager.buildSessionContext())
1287
+ * - Tool calls/results must already be matched and in correct order
1288
+ * - Error state is preserved from messages (stopReason, errorMessage)
1289
+ * - Tool components track expanded state (respects this.toolOutputExpanded)
1290
+ *
1291
+ * SEE ALSO:
1292
+ * - addMessageToChat() for individual message rendering
1293
+ * - handleEvent() for streaming message handling
234
1294
  */
235
1295
  private renderSessionContext;
1296
+ /**
1297
+ * Render all session messages to the chat display.
1298
+ *
1299
+ * PURPOSE:
1300
+ * Displays all messages from the current session context in the chat area.
1301
+ * Used when initializing the UI, resuming a session, or after compaction.
1302
+ * Handles special message types: assistant, user, tool calls/results, compaction, branches.
1303
+ *
1304
+ * PROCESS:
1305
+ * 1. Get aligned session messages from sessionManager.buildSessionContext()
1306
+ * 2. Call renderSessionContext() to render all messages
1307
+ * 3. Show compaction count if session was compacted (0+ times)
1308
+ * 4. Update footer state (model, tokens, etc.)
1309
+ * 5. Populate editor history with user messages for Up arrow
1310
+ *
1311
+ * MESSAGE TYPES RENDERED:
1312
+ * - User messages: with text content and optional skill blocks
1313
+ * - Assistant messages: with streaming content, thinking blocks, tool calls
1314
+ * - Tool calls: inline with ToolExecutionComponent showing args and results
1315
+ * - Tool results: rendered within tool components (not standalone)
1316
+ * - Bash execution: with command and output
1317
+ * - Compaction summary: shows how many tokens were saved
1318
+ * - Branch summary: shows custom branch label/instructions
1319
+ * - Custom messages: rendered via extension message renderer
1320
+ *
1321
+ * PARAMETERS:
1322
+ * None - uses this.session and this.sessionManager
1323
+ *
1324
+ * RETURNS:
1325
+ * void - side effects only (adds components to chatContainer)
1326
+ *
1327
+ * STATE CHANGES:
1328
+ * - Populates chatContainer with all message components
1329
+ * - Populates editor history
1330
+ * - Updates footer.invalidate()
1331
+ * - Updates pendingTools map for tracking tool components
1332
+ * - Clears previous chat display
1333
+ *
1334
+ * NOTES:
1335
+ * - Called from init() after UI setup
1336
+ * - Called from run() before entering interactive loop
1337
+ * - Called from resume/fork/tree navigation
1338
+ * - Rebuilds entire chat, clearing previous messages
1339
+ * - Compaction entries show as status messages
1340
+ * - Only shows compaction info if compaction was performed
1341
+ *
1342
+ * SEE ALSO:
1343
+ * - renderSessionContext() for detailed rendering logic
1344
+ * - addMessageToChat() for rendering individual messages
1345
+ */
236
1346
  renderInitialMessages(): void;
237
1347
  getUserInput(): Promise<string>;
1348
+ /**
1349
+ * Rebuild chat display from scratch, clearing and re-rendering all messages.
1350
+ *
1351
+ * PURPOSE:
1352
+ * Clears the entire chat display and re-renders all messages from session context.
1353
+ * Used after toggling thinking block visibility, compaction completion, or theme changes.
1354
+ * Ensures the display matches the current session state and settings.
1355
+ *
1356
+ * PROCESS:
1357
+ * 1. Clear chatContainer (remove all rendered components)
1358
+ * 2. Get fresh session context from sessionManager
1359
+ * 3. Call renderSessionContext() to re-render all messages
1360
+ * 4. All messages respect current settings (hideThinkingBlock, showImages, etc.)
1361
+ *
1362
+ * PARAMETERS:
1363
+ * None - uses this.session and this.settingsManager
1364
+ *
1365
+ * RETURNS:
1366
+ * void - side effects only
1367
+ *
1368
+ * STATE CHANGES:
1369
+ * - Clears and repopulates chatContainer
1370
+ * - Resets pendingTools map
1371
+ * - Updates streaming/non-streaming component visibility
1372
+ * - Respects current display settings
1373
+ *
1374
+ * NOTES:
1375
+ * - Much faster than renderInitialMessages() (no footer update or history)
1376
+ * - Used internally by toggleThinkingBlockVisibility()
1377
+ * - Used after compaction to show new state
1378
+ * - Does NOT scroll to top (chat scrolls naturally)
1379
+ * - Triggers UI render request in renderSessionContext()
1380
+ *
1381
+ * SEE ALSO:
1382
+ * - renderInitialMessages() for full initialization with footer/history
1383
+ * - toggleThinkingBlockVisibility() which calls this
1384
+ */
238
1385
  private rebuildChatFromMessages;
239
1386
  private handleCtrlC;
240
1387
  private handleCtrlD;
241
1388
  /**
242
- * Gracefully shutdown the agent.
243
- * Emits shutdown event to extensions, then exits.
1389
+ * Gracefully shutdown the interactive mode and exit.
1390
+ *
1391
+ * PURPOSE:
1392
+ * Clean shutdown sequence. Gives extensions opportunity to clean up,
1393
+ * waits for pending renders, then exits the process.
1394
+ *
1395
+ * PROCESS:
1396
+ * 1. Check if already shutting down (prevent double shutdown)
1397
+ * 2. Emit session_shutdown event to extensions
1398
+ * - Extensions can clean up resources, save state, etc.
1399
+ * - Waits for handlers to complete
1400
+ * 3. Wait one tick for pending renders to complete
1401
+ * 4. Call stop() to clean up UI resources:
1402
+ * a. Stop loading animation
1403
+ * b. Dispose footer
1404
+ * c. Unsubscribe from agent events
1405
+ * d. Stop TUI (restore terminal)
1406
+ * 5. Exit process with code 0
1407
+ *
1408
+ * TRIGGERS:
1409
+ * - User presses Ctrl+D (when editor empty)
1410
+ * - User presses Ctrl+C twice within 500ms
1411
+ * - User enters /quit or /exit
1412
+ * - Extension calls shutdown() via context
1413
+ *
1414
+ * PARAMETERS:
1415
+ * None
1416
+ *
1417
+ * RETURNS:
1418
+ * Promise<void> - never resolves (process.exit is called)
1419
+ *
1420
+ * NOTES:
1421
+ * - Sets this.isShuttingDown flag to prevent double-shutdown
1422
+ * - Emits session_shutdown event (not awaited if no handlers)
1423
+ * - Extensions can catch this event with .on("session_shutdown")
1424
+ * - Clean exits prevent terminal corruption
1425
+ * - TUI stop() restores cursor and clear screen
1426
+ *
1427
+ * SEE ALSO:
1428
+ * - stop() which does actual cleanup
1429
+ * - checkShutdownRequested() which triggers shutdown on agent_end
244
1430
  */
245
1431
  private isShuttingDown;
246
1432
  private shutdown;
247
1433
  /**
248
- * Check if shutdown was requested and perform shutdown if so.
1434
+ * Check if shutdown was requested and perform it if so.
1435
+ *
1436
+ * PURPOSE:
1437
+ * Called after agent completes (agent_end event) to check if an extension
1438
+ * has requested shutdown. Allows shutdown to be queued and executed cleanly
1439
+ * after current operation completes.
1440
+ *
1441
+ * PROCESS:
1442
+ * 1. Check this.shutdownRequested flag
1443
+ * 2. If false: return (no shutdown requested)
1444
+ * 3. If true: call shutdown()
1445
+ *
1446
+ * USAGE:
1447
+ * - Extensions call context.shutdown() to request shutdown
1448
+ * - Set this.shutdownRequested = true
1449
+ * - After agent finishes, agent_end event triggers this check
1450
+ * - Shutdown happens cleanly after current message completes
1451
+ *
1452
+ * PARAMETERS:
1453
+ * None
1454
+ *
1455
+ * RETURNS:
1456
+ * Promise<void> - never resolves (process.exit is called)
1457
+ *
1458
+ * NOTES:
1459
+ * - Called from handleEvent() on agent_end
1460
+ * - Defers shutdown until agent is idle
1461
+ * - Allows current streaming/compaction to complete
1462
+ * - Much cleaner than immediate exit
1463
+ *
1464
+ * SEE ALSO:
1465
+ * - shutdown() which does the actual cleanup
1466
+ * - handleEvent() which calls this on agent_end
249
1467
  */
250
1468
  private checkShutdownRequested;
251
1469
  private handleCtrlZ;
@@ -257,8 +1475,66 @@ export declare class InteractiveMode {
257
1475
  private toggleToolOutputExpansion;
258
1476
  private toggleThinkingBlockVisibility;
259
1477
  private openExternalEditor;
1478
+ /**
1479
+ * Clear the editor and request re-render.
1480
+ *
1481
+ * PURPOSE:
1482
+ * Empties the editor text area. Used when user presses Escape with text.
1483
+ */
260
1484
  clearEditor(): void;
1485
+ /**
1486
+ * Show an error message in the chat.
1487
+ *
1488
+ * PURPOSE:
1489
+ * Display an error message to the user. Used for command failures,
1490
+ * parsing errors, and unexpected exceptions.
1491
+ *
1492
+ * PARAMETERS:
1493
+ * @param errorMessage - The error message text (without "Error:" prefix)
1494
+ *
1495
+ * RETURNS:
1496
+ * void - side effects only
1497
+ *
1498
+ * FORMATTING:
1499
+ * - Adds 1-line spacer before message
1500
+ * - Prefixes with "Error: "
1501
+ * - Uses error color from theme
1502
+ * - Adds to bottom of chat
1503
+ *
1504
+ * NOTES:
1505
+ * - Auto-calls ui.requestRender()
1506
+ * - Should be used for all errors displayed to user
1507
+ * - Does not throw (safe to use in error handlers)
1508
+ */
261
1509
  showError(errorMessage: string): void;
1510
+ /**
1511
+ * Show a warning message in the chat.
1512
+ *
1513
+ * PURPOSE:
1514
+ * Display a warning message to the user. Used for non-fatal issues,
1515
+ * deprecated features, and important notifications.
1516
+ *
1517
+ * PARAMETERS:
1518
+ * @param warningMessage - The warning message text (without "Warning:" prefix)
1519
+ *
1520
+ * RETURNS:
1521
+ * void - side effects only
1522
+ *
1523
+ * FORMATTING:
1524
+ * - Adds 1-line spacer before message
1525
+ * - Prefixes with "Warning: "
1526
+ * - Uses warning color from theme
1527
+ * - Adds to bottom of chat
1528
+ *
1529
+ * NOTES:
1530
+ * - Auto-calls ui.requestRender()
1531
+ * - Similar to showError() but with different severity
1532
+ * - Used for resource loading issues, model fallbacks, etc.
1533
+ *
1534
+ * SEE ALSO:
1535
+ * - showError() for fatal errors
1536
+ * - showStatus() for informational messages
1537
+ */
262
1538
  showWarning(warningMessage: string): void;
263
1539
  showNewVersionNotification(newVersion: string): void;
264
1540
  /**
@@ -279,11 +1555,100 @@ export declare class InteractiveMode {
279
1555
  /** Move pending bash components from pending area to chat */
280
1556
  private flushPendingBashComponents;
281
1557
  /**
282
- * Shows a selector component in place of the editor.
283
- * @param create Factory that receives a `done` callback and returns the component and focus target
1558
+ * Show a selector component, replacing the editor temporarily.
1559
+ *
1560
+ * PURPOSE:
1561
+ * Generic helper to display selector dialogs (/settings, /model, /tree, etc.).
1562
+ * Manages switching between the editor and selector, and restoring the editor.
1563
+ *
1564
+ * PROCESS:
1565
+ * 1. Create done callback that:
1566
+ * a. Clears editorContainer
1567
+ * b. Restores this.editor as the focused component
1568
+ * c. Requests UI render
1569
+ * 2. Call factory(done) to create the selector component
1570
+ * 3. Factory returns { component, focus } where focus is initial focus target
1571
+ * 4. Clear editorContainer and add selector component
1572
+ * 5. Set focus to the focus component (usually the selector itself)
1573
+ * 6. Request UI render
1574
+ * 7. Selector calls done() when user makes selection or presses escape
1575
+ *
1576
+ * SELECTOR TYPES:
1577
+ * - SettingsSelectorComponent: /settings - change settings
1578
+ * - ModelSelectorComponent: /model - select a model
1579
+ * - UserMessageSelectorComponent: /fork - pick message to branch from
1580
+ * - TreeSelectorComponent: /tree - navigate session DAG
1581
+ * - SessionSelectorComponent: /resume - switch to different session
1582
+ * - OAuthSelectorComponent: /login or /logout - manage credentials
1583
+ * - ExtensionSelectorComponent: custom dialogs from extensions
1584
+ *
1585
+ * PARAMETERS:
1586
+ * @param create - Factory function that:
1587
+ * - Receives done() callback (selector calls when finished)
1588
+ * - Returns { component, focus } where component is the selector UI
1589
+ * - focus is the component to set focus to (keyboard input target)
1590
+ *
1591
+ * RETURNS:
1592
+ * void - done callback handles restoration
1593
+ *
1594
+ * STATE CHANGES:
1595
+ * - Temporarily replaces editor with selector in editorContainer
1596
+ * - Sets keyboard focus to selector
1597
+ * - On done: restores editor and focus
1598
+ *
1599
+ * NOTES:
1600
+ * - Editor content is preserved (not cleared) during selector
1601
+ * - Selector can be closed by pressing Escape
1602
+ * - Factory receives done callback for flexible completion handling
1603
+ * - Used by all major selectors (model, settings, fork, tree, etc.)
1604
+ *
1605
+ * SEE ALSO:
1606
+ * - showModelSelector() for model selection
1607
+ * - showSettingsSelector() for settings
1608
+ * - showUserMessageSelector() for forking
1609
+ * - showTreeSelector() for tree navigation
284
1610
  */
285
1611
  private showSelector;
286
1612
  private showSettingsSelector;
1613
+ /**
1614
+ * Handle the /model command - select or switch models.
1615
+ *
1616
+ * PURPOSE:
1617
+ * Process /model commands. If search term provided, find exact match.
1618
+ * Otherwise show interactive selector. Supports both quick switch and browse.
1619
+ *
1620
+ * PROCESS:
1621
+ * If searchTerm provided:
1622
+ * 1. Call findExactModelMatch(searchTerm)
1623
+ * 2. If found: switch to model, update footer/border, show status
1624
+ * 3. If not found: show selector with search term as initial filter
1625
+ *
1626
+ * If no searchTerm:
1627
+ * 1. Show model selector dialog
1628
+ * 2. User picks a model
1629
+ * 3. Model is switched
1630
+ *
1631
+ * SEARCH FORMAT:
1632
+ * - "model-id": Match by model ID only
1633
+ * - "provider/model-id": Match provider and model ID
1634
+ * - Case-insensitive matching
1635
+ *
1636
+ * PARAMETERS:
1637
+ * @param searchTerm - Optional model ID or "provider/model-id" to search for
1638
+ *
1639
+ * RETURNS:
1640
+ * Promise<void> - completes when model is selected
1641
+ *
1642
+ * STATE CHANGES:
1643
+ * - May call session.setModel() to switch
1644
+ * - Updates footer.invalidate()
1645
+ * - Updates editor border color (thinking level)
1646
+ * - Shows status message
1647
+ *
1648
+ * SEE ALSO:
1649
+ * - findExactModelMatch() for model lookup
1650
+ * - showModelSelector() for interactive selection
1651
+ */
287
1652
  private handleModelCommand;
288
1653
  private findExactModelMatch;
289
1654
  private getModelCandidates;
@@ -339,10 +1704,199 @@ export declare class InteractiveMode {
339
1704
  private getEditorKeyDisplay;
340
1705
  private handleHotkeysCommand;
341
1706
  private handleClearCommand;
1707
+ /**
1708
+ * Handle the /debug command - write diagnostic information to file.
1709
+ *
1710
+ * PURPOSE:
1711
+ * Generates a comprehensive debug log of the current terminal rendering state
1712
+ * and agent message history. Used for troubleshooting rendering issues or
1713
+ * unusual terminal behavior.
1714
+ *
1715
+ * PROCESS:
1716
+ * 1. Get current terminal dimensions (columns x rows)
1717
+ * 2. Call ui.render() to get all rendered lines at that width
1718
+ * 3. Calculate visible width of each line (accounting for ANSI codes)
1719
+ * 4. Collect all agent messages in JSONL format (one per line)
1720
+ * 5. Write everything to debug log file (~/.indusagi/debug.log or similar)
1721
+ * 6. Display success message with file path
1722
+ *
1723
+ * DEBUG LOG CONTENTS:
1724
+ * - Timestamp of debug generation
1725
+ * - Terminal dimensions (WxH)
1726
+ * - Total rendered lines
1727
+ * - All rendered lines with visible widths and ANSI-escaped content
1728
+ * - All agent messages in JSONL format (one message object per line)
1729
+ *
1730
+ * PARAMETERS:
1731
+ * None
1732
+ *
1733
+ * RETURNS:
1734
+ * void - side effects only (writes file, shows status)
1735
+ *
1736
+ * STATE CHANGES:
1737
+ * - Writes to disk (debug log file)
1738
+ * - Adds status message to chat display
1739
+ *
1740
+ * NOTES:
1741
+ * - File path: getDebugLogPath()
1742
+ * - Creates parent directories if needed
1743
+ * - Useful for reporting rendering bugs
1744
+ * - Shows actual ANSI codes (escaped as JSON strings)
1745
+ * - One message per line in JSONL section for easy parsing
1746
+ */
342
1747
  private handleDebugCommand;
343
1748
  private handleArminSaysHi;
1749
+ /**
1750
+ * Handle bash command execution (! or !! prefix).
1751
+ *
1752
+ * PURPOSE:
1753
+ * Executes a shell command and displays the output in a BashExecutionComponent.
1754
+ * Supports including/excluding from context. Can be intercepted by extensions.
1755
+ *
1756
+ * PROCESS:
1757
+ * 1. Emit user_bash event to extensions (if loaded)
1758
+ * 2. If extension returns a result, use it (extension may intercept)
1759
+ * - Extensions can run custom operations or modify commands
1760
+ * 3. Otherwise execute bash command normally:
1761
+ * a. Create BashExecutionComponent (shows command)
1762
+ * b. If streaming: add to pendingMessagesContainer, queue for chat
1763
+ * c. If idle: add directly to chatContainer
1764
+ * 4. Stream output chunks to component in real-time
1765
+ * 5. Mark complete with exit code and truncation status
1766
+ * 6. Record result in session context
1767
+ *
1768
+ * CONTEXT HANDLING:
1769
+ * - excludeFromContext=false (!): Output included in context for agent
1770
+ * - excludeFromContext=true (!!): Output excluded from context
1771
+ * - Extensions can define custom "operations" to transform output
1772
+ *
1773
+ * PARAMETERS:
1774
+ * @param command - The bash command string (without ! or !! prefix)
1775
+ * @param excludeFromContext - If true, mark output as excluded (!! prefix)
1776
+ *
1777
+ * RETURNS:
1778
+ * Promise<void> - completes when command finishes
1779
+ *
1780
+ * STATE CHANGES:
1781
+ * - Creates BashExecutionComponent
1782
+ * - Adds to chatContainer or pendingMessagesContainer
1783
+ * - Adds to pendingBashComponents if queued
1784
+ * - Records bash result in session
1785
+ * - Updates ui on each output chunk
1786
+ *
1787
+ * ERROR HANDLING:
1788
+ * - Command failures caught and displayed as error message
1789
+ * - Bash execution may be aborted by user (Esc)
1790
+ * - Output may be truncated if too large
1791
+ * - Truncation info shown with link to full output file
1792
+ *
1793
+ * NOTES:
1794
+ * - User can check if bash is already running before executing
1795
+ * - Extension can provide custom operations (e.g., parsing specific formats)
1796
+ * - Output is streamed, so large outputs appear incrementally
1797
+ * - Bash components moved from pending to chat on next regular message
1798
+ * - Session.executeBash() handles actual execution and truncation
1799
+ *
1800
+ * SEE ALSO:
1801
+ * - session.executeBash() for actual command execution
1802
+ * - BashExecutionComponent for rendering
1803
+ */
344
1804
  private handleBashCommand;
1805
+ /**
1806
+ * Handle the /compact command - manually trigger context compaction.
1807
+ *
1808
+ * PURPOSE:
1809
+ * Allows user to manually compact the session context to reduce token usage.
1810
+ * Can include custom instructions to guide the compaction process.
1811
+ *
1812
+ * PROCESS:
1813
+ * 1. Count messages in session
1814
+ * 2. If less than 2 messages: show warning and return (nothing to compact)
1815
+ * 3. Otherwise call executeCompaction() with custom instructions
1816
+ *
1817
+ * PARAMETERS:
1818
+ * @param customInstructions - Optional custom instructions for compaction process
1819
+ *
1820
+ * RETURNS:
1821
+ * Promise<void> - completes when compaction is done
1822
+ *
1823
+ * NOTES:
1824
+ * - User can press Esc during compaction to abort
1825
+ * - Compaction may queue incoming messages
1826
+ * - Custom instructions merged with default compaction prompt
1827
+ *
1828
+ * SEE ALSO:
1829
+ * - executeCompaction() which does the actual work
1830
+ * - auto-compaction (happens automatically based on context size)
1831
+ */
345
1832
  private handleCompactCommand;
1833
+ /**
1834
+ * Execute context compaction (manual or automatic).
1835
+ *
1836
+ * PURPOSE:
1837
+ * Compacts the session context to reduce token usage by summarizing old messages.
1838
+ * Used both for manual /compact commands and automatic overflow-triggered compaction.
1839
+ *
1840
+ * PROCESS:
1841
+ * 1. Stop and clear any existing loading animation
1842
+ * 2. Replace escape handler to allow abort (Esc cancels compaction)
1843
+ * 3. Show "Compacting context..." loader with estimated time
1844
+ * 4. Call session.compact() with optional custom instructions
1845
+ * 5. On success:
1846
+ * a. Rebuild chat to show compacted state
1847
+ * b. Add CompactionSummaryMessageComponent showing tokens saved
1848
+ * c. Invalidate footer (update token counts)
1849
+ * 6. On abort/error:
1850
+ * a. Show error message
1851
+ * b. Chat state unchanged (compaction failed)
1852
+ * 7. Flush queued messages that arrived during compaction
1853
+ * 8. Restore original escape handler
1854
+ * 9. Clear loader
1855
+ *
1856
+ * CUSTOM INSTRUCTIONS:
1857
+ * - Optional guidance for compaction algorithm
1858
+ * - Examples: "focus on recent messages", "preserve code context", etc.
1859
+ * - Merged with default compaction system prompt
1860
+ *
1861
+ * AUTO vs MANUAL:
1862
+ * - isAuto=false (/compact command): shows "Compacting context..." label
1863
+ * - isAuto=true (automatic): shows "Auto-compacting..." label
1864
+ * - auto-compaction triggered by context overflow (token limit)
1865
+ *
1866
+ * QUEUED MESSAGES:
1867
+ * - Messages sent during compaction are queued in compactionQueuedMessages
1868
+ * - After compaction completes, queued messages are flushed
1869
+ * - First message becomes next prompt, rest queued as steer/followUp
1870
+ *
1871
+ * PARAMETERS:
1872
+ * @param customInstructions - Optional custom instructions for compaction
1873
+ * @param isAuto - If true, shows "Auto-compacting..." (default: false)
1874
+ *
1875
+ * RETURNS:
1876
+ * Promise<CompactionResult | undefined> - returns result or undefined on error/abort
1877
+ *
1878
+ * STATE CHANGES:
1879
+ * - Rebuilds chatContainer
1880
+ * - Updates footer
1881
+ * - Clears status container
1882
+ * - Restores escape handler
1883
+ * - Flushes compaction queue
1884
+ *
1885
+ * ERROR HANDLING:
1886
+ * - Compaction cancelled: shows "Compaction cancelled" error
1887
+ * - Compaction failed: shows detailed error message
1888
+ * - Messages queued during compaction are preserved and flushed
1889
+ *
1890
+ * NOTES:
1891
+ * - User can press Esc to abort
1892
+ * - Loader shows "Ctrl+C to cancel" hint
1893
+ * - Compaction happens asynchronously, UI stays responsive
1894
+ * - Very large contexts may take several seconds
1895
+ *
1896
+ * SEE ALSO:
1897
+ * - handleCompactCommand() for /compact processing
1898
+ * - auto-compaction in handleEvent() for automatic triggering
1899
+ */
346
1900
  private executeCompaction;
347
1901
  stop(): void;
348
1902
  }