@xalia/agent 0.6.10 → 0.6.11

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 (161) hide show
  1. package/package.json +5 -2
  2. package/.env.development +0 -6
  3. package/.env.test +0 -7
  4. package/.prettierrc.json +0 -11
  5. package/context_system.md +0 -498
  6. package/eslint.config.mjs +0 -38
  7. package/scripts/chat_server +0 -8
  8. package/scripts/git_message +0 -31
  9. package/scripts/git_wip +0 -21
  10. package/scripts/pr_message +0 -18
  11. package/scripts/pr_review +0 -16
  12. package/scripts/setup_chat +0 -90
  13. package/scripts/shutdown_chat_server +0 -42
  14. package/scripts/start_chat_server +0 -24
  15. package/scripts/sudomcp_import +0 -23
  16. package/scripts/test_chat +0 -327
  17. package/src/agent/agent.ts +0 -699
  18. package/src/agent/agentUtils.ts +0 -286
  19. package/src/agent/compressingContextManager.ts +0 -129
  20. package/src/agent/context.ts +0 -265
  21. package/src/agent/contextWithWorkspace.ts +0 -162
  22. package/src/agent/documentSummarizer.ts +0 -157
  23. package/src/agent/dummyLLM.ts +0 -130
  24. package/src/agent/iAgentEventHandler.ts +0 -64
  25. package/src/agent/imageGenLLM.ts +0 -101
  26. package/src/agent/imageGenerator.ts +0 -45
  27. package/src/agent/iplatform.ts +0 -18
  28. package/src/agent/llm.ts +0 -74
  29. package/src/agent/mcpServerManager.ts +0 -541
  30. package/src/agent/nullAgentEventHandler.ts +0 -26
  31. package/src/agent/nullPlatform.ts +0 -13
  32. package/src/agent/openAI.ts +0 -123
  33. package/src/agent/openAILLM.ts +0 -99
  34. package/src/agent/openAILLMStreaming.ts +0 -648
  35. package/src/agent/promptProvider.ts +0 -87
  36. package/src/agent/repeatLLM.ts +0 -62
  37. package/src/agent/sudoMcpServerManager.ts +0 -361
  38. package/src/agent/test_data/harrypotter.txt +0 -6065
  39. package/src/agent/tokenAuth.ts +0 -50
  40. package/src/agent/tokenCounter.test.ts +0 -243
  41. package/src/agent/tokenCounter.ts +0 -483
  42. package/src/agent/toolSettings.ts +0 -24
  43. package/src/agent/tools/calculatorTool.ts +0 -50
  44. package/src/agent/tools/contentExtractors/htmlToText.ts +0 -61
  45. package/src/agent/tools/contentExtractors/pdfToText.ts +0 -60
  46. package/src/agent/tools/datetimeTool.ts +0 -41
  47. package/src/agent/tools/fileManager/fileManagerTool.ts +0 -199
  48. package/src/agent/tools/fileManager/index.ts +0 -50
  49. package/src/agent/tools/fileManager/memoryFileManager.ts +0 -120
  50. package/src/agent/tools/fileManager/mimeTypes.ts +0 -60
  51. package/src/agent/tools/fileManager/prompt.ts +0 -38
  52. package/src/agent/tools/fileManager/types.ts +0 -189
  53. package/src/agent/tools/index.ts +0 -49
  54. package/src/agent/tools/openUrlTool.ts +0 -62
  55. package/src/agent/tools/renderTool.ts +0 -92
  56. package/src/agent/tools/utils.ts +0 -74
  57. package/src/agent/tools/webSearch.ts +0 -138
  58. package/src/agent/tools/webSearchTool.ts +0 -44
  59. package/src/chat/client/chatClient.ts +0 -967
  60. package/src/chat/client/connection.test.ts +0 -241
  61. package/src/chat/client/connection.ts +0 -286
  62. package/src/chat/client/constants.ts +0 -1
  63. package/src/chat/client/index.ts +0 -21
  64. package/src/chat/client/interfaces.ts +0 -34
  65. package/src/chat/client/sessionClient.ts +0 -574
  66. package/src/chat/client/sessionFiles.ts +0 -142
  67. package/src/chat/client/teamManager.ts +0 -29
  68. package/src/chat/constants.ts +0 -6
  69. package/src/chat/data/apiKeyManager.ts +0 -76
  70. package/src/chat/data/dataModels.ts +0 -107
  71. package/src/chat/data/database.ts +0 -997
  72. package/src/chat/data/dbMcpServerConfigs.ts +0 -59
  73. package/src/chat/data/dbSessionFiles.ts +0 -107
  74. package/src/chat/data/dbSessionMessages.ts +0 -102
  75. package/src/chat/protocol/connectionMessages.ts +0 -49
  76. package/src/chat/protocol/constants.ts +0 -55
  77. package/src/chat/protocol/errors.ts +0 -16
  78. package/src/chat/protocol/messages.ts +0 -899
  79. package/src/chat/server/README.md +0 -127
  80. package/src/chat/server/chatContextManager.ts +0 -660
  81. package/src/chat/server/connectionManager.test.ts +0 -246
  82. package/src/chat/server/connectionManager.ts +0 -506
  83. package/src/chat/server/conversation.ts +0 -319
  84. package/src/chat/server/errorUtils.ts +0 -28
  85. package/src/chat/server/imageGeneratorTools.ts +0 -179
  86. package/src/chat/server/openAIRouterLLM.ts +0 -168
  87. package/src/chat/server/openSession.ts +0 -1945
  88. package/src/chat/server/openSessionMessageSender.ts +0 -4
  89. package/src/chat/server/promptRefiner.ts +0 -106
  90. package/src/chat/server/server.ts +0 -178
  91. package/src/chat/server/sessionFileManager.ts +0 -151
  92. package/src/chat/server/sessionRegistry.test.ts +0 -137
  93. package/src/chat/server/sessionRegistry.ts +0 -1553
  94. package/src/chat/server/test-utils/mockFactories.ts +0 -422
  95. package/src/chat/server/titleGenerator.test.ts +0 -103
  96. package/src/chat/server/titleGenerator.ts +0 -143
  97. package/src/chat/server/tools.ts +0 -170
  98. package/src/chat/utils/agentSessionMap.ts +0 -76
  99. package/src/chat/utils/approvalManager.ts +0 -189
  100. package/src/chat/utils/asyncLock.ts +0 -43
  101. package/src/chat/utils/asyncQueue.ts +0 -62
  102. package/src/chat/utils/multiAsyncQueue.ts +0 -66
  103. package/src/chat/utils/responseAwaiter.ts +0 -181
  104. package/src/chat/utils/userResolver.ts +0 -48
  105. package/src/chat/utils/websocket.ts +0 -16
  106. package/src/index.ts +0 -0
  107. package/src/test/agent.test.ts +0 -584
  108. package/src/test/approvalManager.test.ts +0 -141
  109. package/src/test/chatContextManager.test.ts +0 -552
  110. package/src/test/clientServerConnection.test.ts +0 -205
  111. package/src/test/compressingContextManager.test.ts +0 -77
  112. package/src/test/context.test.ts +0 -150
  113. package/src/test/contextTestTools.ts +0 -95
  114. package/src/test/conversation.test.ts +0 -109
  115. package/src/test/db.test.ts +0 -363
  116. package/src/test/dbMcpServerConfigs.test.ts +0 -112
  117. package/src/test/dbSessionFiles.test.ts +0 -258
  118. package/src/test/dbSessionMessages.test.ts +0 -85
  119. package/src/test/dbTestTools.ts +0 -157
  120. package/src/test/imageLoad.test.ts +0 -15
  121. package/src/test/mcpServerManager.test.ts +0 -114
  122. package/src/test/multiAsyncQueue.test.ts +0 -183
  123. package/src/test/openaiStreaming.test.ts +0 -177
  124. package/src/test/prompt.test.ts +0 -27
  125. package/src/test/promptProvider.test.ts +0 -33
  126. package/src/test/responseAwaiter.test.ts +0 -103
  127. package/src/test/sudoMcpServerManager.test.ts +0 -63
  128. package/src/test/testTools.ts +0 -176
  129. package/src/test/tools.test.ts +0 -64
  130. package/src/tool/agentChat.ts +0 -203
  131. package/src/tool/agentMain.ts +0 -180
  132. package/src/tool/chatMain.ts +0 -621
  133. package/src/tool/commandPrompt.ts +0 -264
  134. package/src/tool/files.ts +0 -82
  135. package/src/tool/main.ts +0 -25
  136. package/src/tool/nodePlatform.ts +0 -73
  137. package/src/tool/options.ts +0 -144
  138. package/src/tool/prompt.ts +0 -101
  139. package/test_data/background_test_profile.json +0 -6
  140. package/test_data/background_test_script.json +0 -11
  141. package/test_data/dummyllm_script_crash.json +0 -32
  142. package/test_data/dummyllm_script_image_gen.json +0 -19
  143. package/test_data/dummyllm_script_image_gen_fe.json +0 -29
  144. package/test_data/dummyllm_script_invoke_image_gen_tool.json +0 -37
  145. package/test_data/dummyllm_script_render_tool.json +0 -29
  146. package/test_data/dummyllm_script_simplecalc.json +0 -28
  147. package/test_data/dummyllm_script_test_auto_approve.json +0 -81
  148. package/test_data/dummyllm_script_test_simplecalc_addition.json +0 -29
  149. package/test_data/frog.png +0 -0
  150. package/test_data/frog.png.b64 +0 -1
  151. package/test_data/git_message_profile.json +0 -4
  152. package/test_data/git_wip_system.txt +0 -5
  153. package/test_data/image_gen_test_profile.json +0 -5
  154. package/test_data/pr_message_profile.json +0 -4
  155. package/test_data/pr_review_profile.json +0 -4
  156. package/test_data/prompt_simplecalc.txt +0 -1
  157. package/test_data/simplecalc_profile.json +0 -4
  158. package/test_data/sudomcp_import_profile.json +0 -4
  159. package/test_data/test_script_profile.json +0 -8
  160. package/tsconfig.json +0 -13
  161. package/vitest.config.ts +0 -39
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@xalia/agent",
3
- "version": "0.6.10",
3
+ "version": "0.6.11",
4
4
  "keywords": [],
5
5
  "author": "",
6
6
  "license": "ISC",
@@ -43,5 +43,8 @@
43
43
  "@types/html-to-text": "^9.0.4",
44
44
  "@types/ws": "^8.18.0",
45
45
  "vitest": "^3.1.1"
46
- }
46
+ },
47
+ "files": [
48
+ "dist"
49
+ ]
47
50
  }
package/.env.development DELETED
@@ -1,6 +0,0 @@
1
- LLM_API_KEY_MAP={"openrouter":"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","together":"5928479bc38fd315acc8359ba42587f8efc804e01b06eb02eb5ee97e044afaa1","openai":"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"}
2
-
3
- # Internal API secret for sending emails
4
- SEND_EMAIL_API_SECRET=73f52358f5741e2467d0ca13733b03f34ed334589c878c28c442f8a08abf85a6
5
-
6
- XALIA_URL=http://localhost:3000
package/.env.test DELETED
@@ -1,7 +0,0 @@
1
- # Test environment configuration
2
- # Copy API keys from .env.development and add test-specific settings
3
-
4
- LLM_API_KEY_MAP={"openrouter":"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","together":"5928479bc38fd315acc8359ba42587f8efc804e01b06eb02eb5ee97e044afaa1","openai":"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"}
5
-
6
- # Disable LLM-generated titles for deterministic Playwright tests
7
- DISABLE_LLM_TITLES=true
package/.prettierrc.json DELETED
@@ -1,11 +0,0 @@
1
- {
2
- "overrides": [
3
- {
4
- "files": "*.ts",
5
- "options": {
6
- "printWidth": 80,
7
- "trailingComma": "es5"
8
- }
9
- }
10
- ]
11
- }
package/context_system.md DELETED
@@ -1,498 +0,0 @@
1
- # Agent Context System
2
-
3
- ## Overview
4
-
5
- This document describes how the agent's context system works, including context formation, compression, fragment injection, and message flow during agent execution.
6
-
7
- ## High-Level Architecture
8
-
9
- The context system uses a **layered architecture** with:
10
- 1. **Fragment-based system prompts** for modularity
11
- 2. **Transaction-based updates** for atomicity
12
- 3. **Automatic compression** for long conversations
13
- 4. **Dynamic context injection** for tools and files
14
-
15
- ### Context Window Structure
16
-
17
- ```
18
- ┌─────────────────────────────────────────────────────────────────┐
19
- │ CONTEXT WINDOW (MessageParam[]) │
20
- ├─────────────────────────────────────────────────────────────────┤
21
- │ Index 0: SYSTEM MESSAGE (Always present, dynamically generated) │
22
- ├─────────────────────────────────────────────────────────────────┤
23
- │ Index 1+: CONVERSATION MESSAGES │
24
- │ - May start with checkpoint message (if compressed) │
25
- │ - User, Assistant, and Tool messages │
26
- │ - Workspace message at end (if ContextManagerWithWorkspace) │
27
- └─────────────────────────────────────────────────────────────────┘
28
- ```
29
-
30
- ## Core Components
31
-
32
- ### 1. System Prompt Composition (Index 0)
33
-
34
- The system message is **never stored in the database**. It's dynamically composed from three sources:
35
-
36
- ```
37
- SystemPromptProvider.computePrompt():
38
- ├── Global Prompt (static, shared by all agents)
39
- ├── Agent Prompt (per-agent, from AgentProfile)
40
- └── Fragments (dynamic, tool-specific context)
41
- ├── "file_manager" → Available files list
42
- ├── "participants" → User UUID to name mapping
43
- └── [Custom fragments...]
44
-
45
- Composition: global + "\n" + agent + "\n" + fragments.join("\n")
46
- ```
47
-
48
- The full prompt is lazily created and cached on every call to `getLLMContext()`.
49
-
50
- **Key files:**
51
- - `agent/src/agent/promptProvider.ts` - System prompt composition
52
- - `agent/src/agent/context.ts` - Base context manager
53
-
54
- ### 2. Conversation Messages (Index 1+)
55
-
56
- Messages are stored in the database and loaded on session start. All messages are stored, whether or not the conversation has been compressed. Compressed conversations also have "checkpoints" (which include a message index).
57
- In this way, the (compressed) LLM context can be recreated and historical messages can still be sent to clients.
58
-
59
- The LLM structure varies depending on compression state:
60
-
61
- #### Without Compression (< 80 messages)
62
-
63
- ```
64
- Index 0: System Message
65
- Index 1: User Message
66
- Index 2: Assistant Message (with tool_calls)
67
- Index 3: Tool Message (results, with content deduplication)
68
- Index 4: Assistant Message
69
- ...
70
- Index N: Workspace Message (optional, special position)
71
- ```
72
-
73
- #### With Compression (≥ 80 messages)
74
- ```
75
- Index 0: System Message
76
- Index 1: Checkpoint Message (summarizes old messages)
77
- Index 2+: Recent messages (20-30 most recent)
78
- Index N: Workspace Message (if applicable)
79
- ```
80
-
81
- **Key files:**
82
- - `agent/src/agent/compressingContextManager.ts` - Compression logic
83
- - `agent/src/agent/contextWithWorkspace.ts` - Workspace message handling
84
- - `agent/src/chat/server/chatContextManager.ts` - Chat-specific coordination
85
-
86
- ## Context Formation During Agent Session
87
-
88
- ### Initial Setup
89
-
90
- ```typescript
91
- // chatContextManager.ts:229-269
92
- constructor(
93
- systemPrompt: string,
94
- sessionMessages: SessionMessage[],
95
- checkpoint: SessionCheckpoint | undefined
96
- ) {
97
- // Resolve messages with checkpoint (if compressed)
98
- const { messages: llmMessages } = resolveConversationWithCheckpoint(
99
- sessionMessages,
100
- checkpoint
101
- );
102
-
103
- // Create compressing context manager
104
- this.llmContext = new CompressingContextManager(
105
- systemPrompt,
106
- llmMessages,
107
- getLLM
108
- );
109
- }
110
- ```
111
-
112
- ### Transaction-Based Message Flow
113
-
114
- ```
115
- User sends messages
116
-
117
- startTx(userMessages) → Creates ChatContextTransaction
118
-
119
- Transaction context = [
120
- System (with fragments: files, participants),
121
- ...Committed messages,
122
- ...New user messages,
123
- Workspace message (if set)
124
- ]
125
-
126
- Agent executes (tool calls, reasoning, responses)
127
-
128
- commit(tx) → Appends agent messages to committed history
129
-
130
- checkCompression() → Triggers if > 80 messages
131
- ```
132
-
133
- **Key files:**
134
- - `agent/src/agent/agent.ts:472-479` - Transaction pattern
135
- - `agent/src/chat/server/chatContextManager.ts` - Transaction implementation
136
-
137
- ## Context Compression
138
-
139
- ### Trigger Mechanism
140
-
141
- Compression activates when committed messages exceed **80 messages** (configurable via `COMPRESSION_TRIGGER_NUM_MESSAGES`).
142
-
143
- ### Compression Process
144
-
145
- ```typescript
146
- // compressingContextManager.ts:99-128
147
- async compress(): Promise<string> {
148
- // Step 1: Extract messages to compress
149
- const messagesToCompress = this.leadingMessages(numToCompress);
150
-
151
- // Step 2: Create summary with specialized LLM
152
- const llm = await this.getLLM();
153
- const summary = await createSummary(llm, messagesToCompress);
154
-
155
- // Step 3: Replace with checkpoint message
156
- const checkpointMessage = {
157
- role: "user",
158
- content: "We are continuing an earlier conversation. " +
159
- "The remainder of this message is a summary: " + summary
160
- };
161
- this.replaceLeadingMessages(numToCompress, checkpointMessage);
162
-
163
- // Step 4: Save checkpoint to database
164
- await checkpointWriter.createCheckpoint({
165
- summary,
166
- num_messages_compressed: numToCompress,
167
- session_uuid: sessionUUID
168
- });
169
-
170
- return summary;
171
- }
172
- ```
173
-
174
- The compression agent uses a specialized prompt:
175
- ```
176
- "You are a context summarizer, creating MINIMAL conversation digests
177
- which can be used to CONTINUE the conversation at a later date.
178
- TOKEN EFFICIENCY is a HIGH PRIORITY. Summaries will only be seen by
179
- LLMs and should USE ANY AND ALL ABBREVIATIONS to keep them as CONCISE
180
- as possible, while PRESERVING IMPORTANT DETAILS of the CONVERSATION."
181
- ```
182
-
183
- **Result:** Token savings of ~50-70% while preserving conversational context.
184
-
185
- **Key files:**
186
- - `agent/src/agent/compressingContextManager.ts` - Compression implementation
187
- - `agent/src/chat/server/chatContextManager.ts:535-548` - Trigger logic
188
-
189
- ## Tool-Specific Context Injection
190
-
191
- The system uses **prompt fragments** to inject dynamic context. Fragments are identified by string IDs and can be updated independently.
192
-
193
- ### Fragment Injection Pattern
194
-
195
- ```typescript
196
- // Lazy-update pattern (chatContextManager.ts:272-281)
197
- getLLMContext(): MessageParam[] {
198
- if (this.fileManagerDescriptionsDirty) { // Check dirty flag
199
- // Regenerate the file list prompt
200
- const prompt = createSessionFilesManagerPrompt(this.fileManager);
201
-
202
- // Update the system prompt fragment
203
- this.llmContext.setPromptFragment("file_manager", prompt);
204
-
205
- this.fileManagerDescriptionsDirty = false; // Clear flag
206
- }
207
-
208
- return this.llmContext.getLLMContext();
209
- }
210
- ```
211
-
212
- ### Key Injection Points
213
-
214
- #### A. File Manager Context
215
-
216
- ```typescript
217
- // sessionFileManager.ts:271-287
218
- function createSessionFilesManagerPrompt(fm: ISessionFileManager): string {
219
- const files = fm.listFiles();
220
- if (files.length === 0) return "";
221
-
222
- let prompt =
223
- "Files can be read/written as required. Create new files conservatively, " +
224
- "usually when complex content is requested. Use base64 for binary (image," +
225
- "pdf), ascii for text formats (html,markdown). " +
226
- "Available files:\nname,type,summary\n";
227
-
228
- for (const f of files) {
229
- prompt += `${f.name},${f.mime_type},${f.summary || ""}\n`;
230
- }
231
- return prompt;
232
- }
233
- ```
234
-
235
- **Event-driven updates:**
236
- ```typescript
237
- // When files change, mark dirty
238
- onFileChanged(_entry: SessionFileEntry): void {
239
- this.fileManagerDescriptionsDirty = true;
240
- }
241
- ```
242
-
243
- #### B. Participants Context
244
-
245
- ```typescript
246
- // openSession.ts:1532-1547
247
- private updateParticipantsPrompt(): void {
248
- const prompt =
249
- "The following map is from user_uuids to real names. In user " +
250
- "messages, real names will be used...\n" +
251
- participants.map(([uuid, name]) => `${uuid}: ${name}`).join("\n");
252
-
253
- this.contextManager.setPromptFragment("participants", prompt);
254
- }
255
- ```
256
-
257
- #### C. MCP Tool Definitions
258
-
259
- MCP tools are passed as a separate parameter to the LLM, not as system prompt fragments:
260
-
261
- ```typescript
262
- // agent.ts:245-254
263
- async chatCompletion(context: MessageParam[]) {
264
- const mcpTools = this.mcpServerManager.getOpenAITools();
265
- const enabledTools = this.tools.concat(mcpTools);
266
-
267
- return await this.llm.getConversationResponse(
268
- context,
269
- enabledTools, // ← Tool schemas passed here
270
- eventHandler
271
- );
272
- }
273
- ```
274
-
275
- **Key files:**
276
- - `agent/src/agent/promptProvider.ts` - Fragment management
277
- - `agent/src/chat/server/sessionFileManager.ts` - File manager integration
278
- - `agent/src/chat/server/openSession.ts` - Participants management
279
-
280
- ## Session Files Handling
281
-
282
- Session files use an **event-driven architecture** with **lazy-update prompt injection**.
283
-
284
- ### File Storage
285
-
286
- Two implementations:
287
- - **MemoryFileManager**: In-memory storage for testing
288
- - **ChatSessionFileManager**: Database-backed with two-tier caching
289
- - Metadata cache: `fileMap: Map<string, SessionFileDescriptor>`
290
- - Content cache: `fileDataCache: Map<string, string>`
291
-
292
- ### Event Flow
293
-
294
- ```
295
- User/Agent modifies file
296
-
297
- SessionFileManager.putFileContent() / deleteFile()
298
-
299
- Update internal state (fileMap, DB)
300
-
301
- Trigger event handlers
302
-
303
- ChatContextManager.onFileChanged() / onFileDeleted()
304
-
305
- Set fileManagerDescriptionsDirty = true
306
-
307
- Next getLLMContext() call regenerates prompt fragment
308
- ```
309
-
310
- ### Content Deduplication
311
-
312
- File tool calls use a special optimization to prevent context bloat:
313
-
314
- ```typescript
315
- // sessionFileManager.ts:361-369
316
- const getFileContentFn: ToolHandler = async (_, args) => {
317
- const { name } = parseName(args);
318
- const response = await fileManager.getFileContent(name);
319
-
320
- // Replace full data URL with session file reference
321
- const overwriteResponse = fileManager.getSessionFileRelativeUrl(name);
322
-
323
- return { response, overwriteResponse };
324
- };
325
- ```
326
-
327
- **Result:**
328
- - **Initial response**: `data:image/png;base64,iVBORw0KGg...` (large)
329
- - **Overwritten to**: `file+session://./chart.png` (compact)
330
-
331
- **Key files:**
332
- - `agent/src/chat/server/sessionFileManager.ts` - File management
333
- - `agent/src/chat/server/chatContextManager.ts:271-315` - File event handling
334
-
335
- ## Workspace Message
336
-
337
- The workspace message is a **special trailing user message** that provides persistent context across all agent responses in a session.
338
-
339
- ### Special Handling
340
-
341
- ```typescript
342
- // contextWithWorkspace.ts:142-149
343
- setWorkspace(userMessage: UserMessageParam | undefined) {
344
- if (!userMessage) {
345
- userMessage = { role: "user", content: "" };
346
- }
347
- super.popMessage(); // Remove old workspace
348
- super.pushMessage(userMessage); // Add new workspace
349
- }
350
- ```
351
-
352
- ### Transaction Behavior
353
-
354
- During transactions, the workspace message is:
355
- 1. Moved from the end of committed messages
356
- 2. Positioned **before** agent responses
357
- 3. Restored to the end after commit
358
-
359
- ```
360
- Committed: [U1, A1, U2, A2, Workspace]
361
- Transaction: [U1, A1, U2, A2, NewUser, Workspace, NewAgent]
362
- After commit: [U1, A1, U2, A2, NewUser, NewAgent, Workspace]
363
- ```
364
-
365
- **Key files:**
366
- - `agent/src/agent/contextWithWorkspace.ts` - Workspace implementation
367
-
368
- ## Dynamic Todo/Task Tracking
369
-
370
- **Result: NOT IMPLEMENTED**
371
-
372
- The current agent does not have a dynamic todo/task tracking system during execution. There is no equivalent to Claude Code's TodoWrite tool.
373
-
374
- What exists:
375
- - Message history tracking
376
- - Tool call result tracking
377
- - File metadata tracking
378
- - Checkpoint tracking
379
-
380
- This could be a future enhancement.
381
-
382
- ## Complete Data Flow
383
-
384
- ```
385
- ┌────────────────────────────────────────────────────────────┐
386
- │ 1. User Message Received │
387
- └────────────────────────────────────────────────────────────┘
388
-
389
- ┌────────────────────────────────────────────────────────────┐
390
- │ 2. ChatContextManager.processUserMessage() │
391
- │ → Assigns message_idx │
392
- └────────────────────────────────────────────────────────────┘
393
-
394
- ┌────────────────────────────────────────────────────────────┐
395
- │ 3. ChatContextManager.startAgentResponse() │
396
- │ → Creates ChatContextTransaction │
397
- │ → Injects: user messages + workspace + file list │
398
- │ + participants │
399
- └────────────────────────────────────────────────────────────┘
400
-
401
- ┌────────────────────────────────────────────────────────────┐
402
- │ 4. Agent.userMessagesRaw() │
403
- │ → Loop: LLM call → Tool calls → LLM call → ... │
404
- └────────────────────────────────────────────────────────────┘
405
-
406
- ┌────────────────────────────────────────────────────────────┐
407
- │ 5. ChatContextManager.endAgentResponse() │
408
- │ → Commits transaction │
409
- │ → Checks compression trigger │
410
- └────────────────────────────────────────────────────────────┘
411
- ↓ (if > 80 messages)
412
- ┌────────────────────────────────────────────────────────────┐
413
- │ 6. Background: CompressingContextManager.compress() │
414
- │ → Summarizes old messages │
415
- │ → Creates checkpoint │
416
- │ → Saves to DB │
417
- └────────────────────────────────────────────────────────────┘
418
- ```
419
-
420
- ## Architecture Layers
421
-
422
- ```
423
- ┌─────────────────────────────────────────────┐
424
- │ Agent (agent.ts) │
425
- │ - Execution loop │
426
- │ - Tool orchestration │
427
- └─────────────────┬───────────────────────────┘
428
-
429
- ┌─────────────────▼───────────────────────────┐
430
- │ ChatContextManager (chatContextManager.ts) │
431
- │ - Transaction management │
432
- │ - Compression triggering │
433
- │ - Fragment coordination │
434
- └─────────────────┬───────────────────────────┘
435
-
436
- ┌─────────┴─────────┐
437
- ▼ ▼
438
- ┌───────────────────┐ ┌────────────────────────┐
439
- │ CompressingContext│ │ SessionFileManager │
440
- │ Manager │ │ (sessionFileManager.ts)│
441
- │ (compressing...ts)│ │ - File tracking │
442
- │ - Summarization │ │ - Prompt generation │
443
- └───────┬───────────┘ └────────────────────────┘
444
-
445
-
446
- ┌──────────────────────┐
447
- │ ContextWithWorkspace │
448
- │ (contextWith...ts) │
449
- │ - Workspace msg │
450
- └──────────┬───────────┘
451
-
452
-
453
- ┌──────────────────────┐
454
- │ ContextManager │
455
- │ (context.ts) │
456
- │ - Base messages │
457
- │ - SystemPromptProvider│
458
- └──────────────────────┘
459
- ```
460
-
461
- ## Key Design Principles
462
-
463
- 1. **System message is never stored** - Regenerated on every context request
464
- 2. **Fragments use lazy evaluation** - Only recomputed when dirty flags are set
465
- 3. **Workspace has special handling** - Always at end, moved during transactions
466
- 4. **Content is deduplicated** - Large data URLs replaced with compact references
467
- 5. **Compression is one-way** - Old messages summarized, originals kept in DB for audit
468
- 6. **Checkpoints are user messages** - Special prefix indicates it's a summary
469
- 7. **Transactions ensure atomicity** - All-or-nothing commits with rollback
470
-
471
- ## Performance Optimizations
472
-
473
- - **Lazy fragment updates**: Only regenerate when dirty
474
- - **Content deduplication**: File contents replaced with references
475
- - **Automatic compression**: Keeps context window manageable
476
- - **Two-tier file caching**: Metadata + content caches
477
- - **Event-driven updates**: Minimizes unnecessary recomputation
478
-
479
- ## References
480
-
481
- ### Core Context Files
482
-
483
- | Function | File |
484
- |----------|------|
485
- | Base context | [`src/agent/context.ts`](src/agent/context.ts) |
486
- | Workspace support | [`src/agent/contextWithWorkspace.ts`](src/agent/contextWithWorkspace.ts) |
487
- | Compression logic | [`src/agent/compressingContextManager.ts`](src/agent/compressingContextManager.ts) |
488
- | System prompt fragments | [`src/agent/promptProvider.ts`](src/agent/promptProvider.ts) |
489
- | Agent execution | [`src/agent/agent.ts`](src/agent/agent.ts) |
490
-
491
- ### Chat System Files
492
-
493
- | Function | File |
494
- |----------|------|
495
- | Chat coordination | [`src/chat/server/chatContextManager.ts`](src/chat/server/chatContextManager.ts) |
496
- | File context | [`src/chat/server/sessionFileManager.ts`](src/chat/server/sessionFileManager.ts) |
497
- | Participants context | [`src/chat/server/openSession.ts`](src/chat/server/openSession.ts) |
498
- | Message transformation | [`src/chat/server/conversation.ts`](src/chat/server/conversation.ts) |
package/eslint.config.mjs DELETED
@@ -1,38 +0,0 @@
1
- import eslint from "@eslint/js";
2
- import tseslint from "typescript-eslint";
3
-
4
- export default tseslint.config(
5
- eslint.configs.recommended,
6
- ...tseslint.configs.strict,
7
- ...tseslint.configs.strictTypeChecked,
8
- {
9
- languageOptions: {
10
- parserOptions: {
11
- project: "./tsconfig.json",
12
- tsconfigRootDir: import.meta.dirname,
13
- },
14
- },
15
- },
16
- {
17
- rules: {
18
- "@typescript-eslint/no-unused-vars": [
19
- "error",
20
- {
21
- args: "all",
22
- argsIgnorePattern: "^_",
23
- caughtErrors: "all",
24
- caughtErrorsIgnorePattern: "^_",
25
- destructuredArrayIgnorePattern: "^_",
26
- varsIgnorePattern: "^_",
27
- ignoreRestSiblings: true,
28
- },
29
- ],
30
- "max-len": ["error", { code: 80 }],
31
- "linebreak-style": ["error", "unix"],
32
- },
33
- },
34
- {
35
- files: ["**/*.mjs", "**/*.js"],
36
- ...tseslint.configs.disableTypeChecked,
37
- },
38
- );
@@ -1,8 +0,0 @@
1
- #!/usr/bin/env bash
2
-
3
- # Script to run the chat server so deployment logic does not have to know the
4
- # location of the entrypoint (which can change easily).
5
-
6
- this_dir=`dirname ${BASH_SOURCE[0]}`
7
- agent_dir=`realpath ${this_dir}/..`
8
- ${agent_dir}/dist/agent/src/tool/main.js chat server $@
@@ -1,31 +0,0 @@
1
- #!/usr/bin/env bash
2
-
3
- this_dir=`dirname ${BASH_SOURCE[0]}`
4
- this_dir=`realpath ${this_dir}`
5
- client=${this_dir}/../dist/main.js
6
-
7
- prompt=/tmp/git_message_prompt.txt
8
- msg=/tmp/git_message.txt
9
-
10
- while [[ "$#" -gt 0 ]]; do
11
- case "$1" in
12
- -n) dry_run=1 ;;
13
- *) echo "Unknown parameter: $1" ; exit 1 ;;
14
- esac
15
- shift
16
- done
17
-
18
- # Create prompt
19
- echo "Create the commit message for the following diff:" > ${prompt}
20
- git diff --no-ext-diff --cached -U6 >> ${prompt}
21
-
22
- ${client} -1 \
23
- --agent-profile ${this_dir}/../test_data/git_message_profile.json \
24
- --prompt ${prompt} > ${msg}
25
-
26
- # Use as commit message
27
- if [ -z ${dry_run} ] ; then
28
- git commit -e -F ${msg}
29
- else
30
- cat ${msg}
31
- fi
package/scripts/git_wip DELETED
@@ -1,21 +0,0 @@
1
- #!/usr/bin/env bash
2
-
3
- this_dir=`dirname ${BASH_SOURCE[0]}`
4
- this_dir=`realpath ${this_dir}`
5
- client=${this_dir}/../dist/main.js
6
-
7
- prompt=/tmp/git_wip_prompt.txt
8
-
9
- # Create prompt
10
- echo "Below are my WIP diffs:" > ${prompt}
11
- git diff HEAD --no-ext-diff -U6 >> ${prompt}
12
- num_lines=`cat ${prompt} | wc -l`
13
- if [ "1" == ${num_lines} ] ; then
14
- echo Using last commit
15
- git show -U6 >> ${prompt}
16
- fi
17
-
18
- ${client} -y -1 -q \
19
- --sysprompt ${this_dir}/../test_data/git_wip_system.txt \
20
- --prompt ${prompt} | pbcopy
21
- pbpaste
@@ -1,18 +0,0 @@
1
- #!/usr/bin/env bash
2
-
3
- this_dir=`dirname ${BASH_SOURCE[0]}`
4
- this_dir=`realpath ${this_dir}`
5
- client=${this_dir}/../dist/main.js
6
-
7
- prompt=/tmp/pr_message_prompt.txt
8
- msg=/tmp/pr_message.txt
9
-
10
-
11
- # Create prompt
12
- echo "Create the PR message for the following commits:" > ${prompt}
13
- git log origin/master..HEAD >> ${prompt}
14
-
15
- ${client} -1 \
16
- --agent-profile ${this_dir}/../test_data/pr_message_profile.json \
17
- --prompt ${prompt} | tee ${msg}
18
- cat ${msg} | pbcopy
package/scripts/pr_review DELETED
@@ -1,16 +0,0 @@
1
- #!/usr/bin/env bash
2
-
3
- this_dir=`dirname ${BASH_SOURCE[0]}`
4
- this_dir=`realpath ${this_dir}`
5
- client=${this_dir}/../dist/main.js
6
-
7
- prompt=/tmp/pr_review_prompt.txt
8
-
9
-
10
- # Create prompt
11
- echo "Review the following PR diff:" > ${prompt}
12
- git log -p -U10 origin/master..HEAD >> ${prompt}
13
-
14
- ${client} -1 \
15
- --agent-profile ${this_dir}/../test_data/pr_review_profile.json \
16
- --prompt ${prompt}