@codebolt/agent 2.2.2 → 2.2.5

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 (141) hide show
  1. package/dist/builderpattern/agent.js +2 -2
  2. package/dist/builderpattern/followupquestionbuilder.js +1 -1
  3. package/dist/builderpattern/llmoutputhandler.js +7 -7
  4. package/dist/builderpattern/usermessage.d.ts +6 -1
  5. package/dist/composablepattern/document.js +2 -35
  6. package/dist/local-tools/fileTools.d.ts +26 -0
  7. package/dist/local-tools/fileTools.js +162 -0
  8. package/dist/processor/types/interfaces.d.ts +44 -21
  9. package/dist/processor-pieces/additionalModifiers/argumentProcessorModifier.d.ts +13 -0
  10. package/dist/processor-pieces/additionalModifiers/argumentProcessorModifier.js +68 -0
  11. package/dist/processor-pieces/additionalModifiers/atFileProcessorModifier.d.ts +15 -0
  12. package/dist/processor-pieces/additionalModifiers/atFileProcessorModifier.js +212 -0
  13. package/dist/processor-pieces/additionalModifiers/chatCompressionModifier.d.ts +19 -0
  14. package/dist/processor-pieces/additionalModifiers/chatCompressionModifier.js +110 -0
  15. package/dist/processor-pieces/additionalModifiers/chatRecordingModifier.d.ts +23 -0
  16. package/dist/processor-pieces/additionalModifiers/chatRecordingModifier.js +173 -0
  17. package/dist/processor-pieces/additionalModifiers/coreSystemPromptModifier.d.ts +14 -0
  18. package/dist/processor-pieces/additionalModifiers/coreSystemPromptModifier.js +93 -0
  19. package/dist/processor-pieces/additionalModifiers/directoryContextModifier.d.ts +30 -0
  20. package/dist/processor-pieces/additionalModifiers/directoryContextModifier.js +330 -0
  21. package/dist/processor-pieces/additionalModifiers/environmentContextModifier.d.ts +26 -0
  22. package/dist/processor-pieces/additionalModifiers/environmentContextModifier.js +269 -0
  23. package/dist/processor-pieces/additionalModifiers/fallbackHandlerModifier.d.ts +38 -0
  24. package/dist/processor-pieces/additionalModifiers/fallbackHandlerModifier.js +217 -0
  25. package/dist/processor-pieces/additionalModifiers/ideContextModifier.d.ts +34 -0
  26. package/dist/processor-pieces/additionalModifiers/ideContextModifier.js +147 -0
  27. package/dist/processor-pieces/additionalModifiers/index.d.ts +12 -0
  28. package/dist/processor-pieces/additionalModifiers/index.js +28 -0
  29. package/dist/processor-pieces/additionalModifiers/loopDetectionModifier.d.ts +29 -0
  30. package/dist/processor-pieces/additionalModifiers/loopDetectionModifier.js +155 -0
  31. package/dist/processor-pieces/additionalModifiers/memoryImportModifier.d.ts +15 -0
  32. package/dist/processor-pieces/additionalModifiers/memoryImportModifier.js +129 -0
  33. package/dist/processor-pieces/additionalModifiers/shellProcessorModifier.d.ts +25 -0
  34. package/dist/processor-pieces/additionalModifiers/shellProcessorModifier.js +169 -0
  35. package/dist/processor-pieces/additionalModifiers/toolInjectionModifier.d.ts +20 -0
  36. package/dist/processor-pieces/additionalModifiers/toolInjectionModifier.js +152 -0
  37. package/dist/processor-pieces/messageModifiers/addCurrentDirectoryRootFilesModifier.d.ts +7 -0
  38. package/dist/processor-pieces/messageModifiers/addCurrentDirectoryRootFilesModifier.js +93 -0
  39. package/dist/processor-pieces/messageModifiers/addToolsListMessageModifier.d.ts +14 -5
  40. package/dist/processor-pieces/messageModifiers/addToolsListMessageModifier.js +41 -40
  41. package/dist/processor-pieces/messageModifiers/advancedSystemInstructionMessageModifier.d.ts +9 -0
  42. package/dist/processor-pieces/messageModifiers/advancedSystemInstructionMessageModifier.js +77 -0
  43. package/dist/processor-pieces/messageModifiers/atFileProcessorModifier.js +5 -5
  44. package/dist/processor-pieces/messageModifiers/baseContextMessageModifier.d.ts +5 -13
  45. package/dist/processor-pieces/messageModifiers/baseContextMessageModifier.js +50 -58
  46. package/dist/processor-pieces/messageModifiers/baseSystemInstructionMessageModifier.d.ts +6 -8
  47. package/dist/processor-pieces/messageModifiers/baseSystemInstructionMessageModifier.js +66 -22
  48. package/dist/processor-pieces/messageModifiers/chatCompressionModifier.d.ts +19 -0
  49. package/dist/processor-pieces/messageModifiers/chatCompressionModifier.js +110 -0
  50. package/dist/processor-pieces/messageModifiers/chatHistoryMessageModifier.example.d.ts +20 -0
  51. package/dist/processor-pieces/messageModifiers/chatHistoryMessageModifier.example.js +124 -0
  52. package/dist/processor-pieces/messageModifiers/environmentContext.d.ts +41 -0
  53. package/dist/processor-pieces/messageModifiers/environmentContext.js +355 -0
  54. package/dist/processor-pieces/messageModifiers/handleUrlMessageModifier.d.ts +3 -2
  55. package/dist/processor-pieces/messageModifiers/handleUrlMessageModifier.js +1 -2
  56. package/dist/processor-pieces/messageModifiers/imageAttachmentMessageModifier.d.ts +3 -2
  57. package/dist/processor-pieces/messageModifiers/imageAttachmentMessageModifier.js +1 -2
  58. package/dist/processor-pieces/messageModifiers/mentionedFilesModifier.d.ts +23 -0
  59. package/dist/processor-pieces/messageModifiers/mentionedFilesModifier.js +207 -0
  60. package/dist/processor-pieces/messageModifiers/simpleMessageModifier.d.ts +7 -0
  61. package/dist/processor-pieces/messageModifiers/simpleMessageModifier.js +26 -0
  62. package/dist/processor-pieces/messageModifiers/workingDirectoryMessageModifier.d.ts +18 -2
  63. package/dist/processor-pieces/messageModifiers/workingDirectoryMessageModifier.js +291 -93
  64. package/dist/processor-pieces/postInference/llmOutputValidityProcessor.d.ts +1 -0
  65. package/dist/processor-pieces/postInference/llmOutputValidityProcessor.js +2 -0
  66. package/dist/processor-pieces/postInferenceProcessors/checkForNoToolCall.d.ts +7 -0
  67. package/dist/processor-pieces/postInferenceProcessors/checkForNoToolCall.js +24 -0
  68. package/dist/processor-pieces/postToolCall/advancedLoopDetectionProcessor.d.ts +41 -0
  69. package/dist/processor-pieces/postToolCall/advancedLoopDetectionProcessor.js +197 -0
  70. package/dist/processor-pieces/postToolCall/chatCompressionProcessor.d.ts +26 -0
  71. package/dist/processor-pieces/postToolCall/chatCompressionProcessor.js +90 -0
  72. package/dist/processor-pieces/postToolCall/chatRecordingProcessor.d.ts +81 -0
  73. package/dist/processor-pieces/postToolCall/chatRecordingProcessor.js +329 -0
  74. package/dist/processor-pieces/postToolCall/contextManagementProcessor.d.ts +40 -0
  75. package/dist/processor-pieces/postToolCall/contextManagementProcessor.js +272 -0
  76. package/dist/processor-pieces/postToolCall/conversationCompactorProcessor.d.ts +49 -0
  77. package/dist/processor-pieces/postToolCall/conversationCompactorProcessor.js +291 -0
  78. package/dist/processor-pieces/postToolCall/conversationContinuityProcessor.d.ts +49 -0
  79. package/dist/processor-pieces/postToolCall/conversationContinuityProcessor.js +293 -0
  80. package/dist/processor-pieces/postToolCall/followUpConversationProcessor.d.ts +47 -0
  81. package/dist/processor-pieces/postToolCall/followUpConversationProcessor.js +249 -0
  82. package/dist/processor-pieces/postToolCall/loopDetectionProcessor.d.ts +30 -0
  83. package/dist/processor-pieces/postToolCall/loopDetectionProcessor.js +137 -0
  84. package/dist/processor-pieces/postToolCall/responseValidationProcessor.d.ts +30 -0
  85. package/dist/processor-pieces/postToolCall/responseValidationProcessor.js +228 -0
  86. package/dist/processor-pieces/postToolCall/telemetryProcessor.d.ts +99 -0
  87. package/dist/processor-pieces/postToolCall/telemetryProcessor.js +278 -0
  88. package/dist/processor-pieces/postToolCall/tokenManagementProcessor.d.ts +37 -0
  89. package/dist/processor-pieces/postToolCall/tokenManagementProcessor.js +178 -0
  90. package/dist/processor-pieces/postToolCall/toolExecutionProcessor.d.ts +43 -0
  91. package/dist/processor-pieces/postToolCall/toolExecutionProcessor.js +207 -0
  92. package/dist/processor-pieces/preInference/conversationCompactorProcessor.d.ts +52 -0
  93. package/dist/processor-pieces/preInference/conversationCompactorProcessor.js +264 -0
  94. package/dist/processor-pieces/preInference/conversationContinuityProcessor.d.ts +49 -0
  95. package/dist/processor-pieces/preInference/conversationContinuityProcessor.js +293 -0
  96. package/dist/processor-pieces/preInferenceProcessors/conversationCompaction.d.ts +7 -0
  97. package/dist/processor-pieces/preInferenceProcessors/conversationCompaction.js +31 -0
  98. package/dist/processor-pieces/preToolCall/index.d.ts +9 -0
  99. package/dist/processor-pieces/preToolCall/index.js +18 -0
  100. package/dist/processor-pieces/preToolCall/localToolInterceptorProcessor.d.ts +58 -0
  101. package/dist/processor-pieces/preToolCall/localToolInterceptorProcessor.js +444 -0
  102. package/dist/processor-pieces/preToolCall/toolParameterModifierProcessor.d.ts +44 -0
  103. package/dist/processor-pieces/preToolCall/toolParameterModifierProcessor.js +367 -0
  104. package/dist/processor-pieces/preToolCall/toolValidationProcessor.d.ts +58 -0
  105. package/dist/processor-pieces/preToolCall/toolValidationProcessor.js +391 -0
  106. package/dist/unified/agent/agent.js +2 -2
  107. package/dist/unified/agent/tool.d.ts +99 -0
  108. package/dist/unified/agent/tool.js +440 -0
  109. package/dist/unified/base/initialPromptGenerator.js +5 -5
  110. package/dist/unified/base/responseExecutor.js +6 -6
  111. package/dist/unified/examples/agentExample.d.ts +46 -0
  112. package/dist/unified/examples/agentExample.js +464 -0
  113. package/dist/unified/examples/documentationPatternExample.d.ts +10 -0
  114. package/dist/unified/examples/documentationPatternExample.js +385 -0
  115. package/dist/unified/examples/followUpProcessorsExample.d.ts +45 -0
  116. package/dist/unified/examples/followUpProcessorsExample.js +311 -0
  117. package/dist/unified/examples/orchestratorExample.d.ts +16 -0
  118. package/dist/unified/examples/orchestratorExample.js +415 -0
  119. package/dist/unified/examples/preToolCallProcessorsExample.d.ts +36 -0
  120. package/dist/unified/examples/preToolCallProcessorsExample.js +458 -0
  121. package/dist/unified/examples/workflowExample.d.ts +12 -0
  122. package/dist/unified/examples/workflowExample.js +497 -0
  123. package/dist/unified/orchestrator/orchestrator.d.ts +260 -0
  124. package/dist/unified/orchestrator/orchestrator.js +519 -0
  125. package/package.json +5 -5
  126. package/dist/agent.d.ts +0 -86
  127. package/dist/agent.js +0 -324
  128. package/dist/followupquestionbuilder.d.ts +0 -75
  129. package/dist/followupquestionbuilder.js +0 -197
  130. package/dist/index.d.ts +0 -14
  131. package/dist/index.js +0 -23
  132. package/dist/llmoutputhandler.d.ts +0 -102
  133. package/dist/llmoutputhandler.js +0 -452
  134. package/dist/promptbuilder.d.ts +0 -382
  135. package/dist/promptbuilder.js +0 -805
  136. package/dist/systemprompt.d.ts +0 -20
  137. package/dist/systemprompt.js +0 -48
  138. package/dist/taskInstruction.d.ts +0 -37
  139. package/dist/taskInstruction.js +0 -57
  140. package/dist/usermessage.d.ts +0 -70
  141. package/dist/usermessage.js +0 -123
@@ -37,37 +37,49 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
37
37
  };
38
38
  Object.defineProperty(exports, "__esModule", { value: true });
39
39
  exports.WorkingDirectoryMessageModifier = void 0;
40
- const processor_1 = require("../../processor");
40
+ const base_1 = require("../base");
41
41
  const codeboltjs_1 = __importDefault(require("@codebolt/codeboltjs"));
42
42
  const path = __importStar(require("path"));
43
- class WorkingDirectoryMessageModifier extends processor_1.BaseMessageModifier {
43
+ const fs = __importStar(require("fs/promises"));
44
+ class WorkingDirectoryMessageModifier extends base_1.BaseMessageModifier {
44
45
  constructor(options = {}) {
45
46
  super({ context: options });
47
+ this.defaultIgnoredFolders = new Set(['node_modules', '.git', 'dist', '.codebolt', '.codeboltAgents']);
48
+ this.truncationIndicator = '...';
46
49
  this.showFolderStructureSummary = options.showFolderStructureSummary || false;
47
50
  this.listFiles = options.listFiles || false;
48
51
  this.listFilesDepth = options.listFilesDepth || 2;
49
- this.listFilesLimit = options.listFilesLimit || 200;
52
+ this.listFilesLimit = options.listFilesLimit || 100;
50
53
  this.listFilesIgnoreFromGitignore = options.listFilesIgnoreFromGitignore || true;
51
- this.listFilesIgnore = options.listFilesIgnore || ['node_modules', '.git', 'dist', 'build'];
54
+ this.listFilesIgnore = options.listFilesIgnore || ['node_modules', '.git', 'dist', '.codebolt', '.codeboltAgents'];
55
+ this.maxItems = options.maxItems || 200;
56
+ this.showFullDirectoryContext = options.showFullDirectoryContext || true;
52
57
  }
53
- async modify(input) {
58
+ async modify(originalRequest, createdMessage) {
54
59
  try {
55
- const { originalRequest, createdMessage, context } = input;
56
60
  const contextParts = [];
57
61
  // Get project information
58
62
  try {
59
- const projectPathResponse = await codeboltjs_1.default.project.getProjectPath();
60
- const projectPath = typeof projectPathResponse === 'string'
61
- ? projectPathResponse
62
- : (projectPathResponse === null || projectPathResponse === void 0 ? void 0 : projectPathResponse.path) || String(projectPathResponse) || '';
63
- contextParts.push(`Project Directory: ${projectPath}`);
64
- if (this.showFolderStructureSummary) {
65
- const summary = await this.generateFolderStructureSummary(projectPath);
66
- contextParts.push(`Folder Structure Summary:\n${summary}`);
63
+ const { projectPath } = await codeboltjs_1.default.project.getProjectPath();
64
+ if (!projectPath) {
65
+ throw new Error('Project path not available');
67
66
  }
68
- if (this.listFiles) {
69
- const filesList = await this.generateFilesList(projectPath);
70
- contextParts.push(`Files List:\n${filesList}`);
67
+ // Generate comprehensive directory context similar to gemini-cli
68
+ if (this.showFullDirectoryContext) {
69
+ const directoryContext = await this.getDirectoryContextString(projectPath);
70
+ contextParts.push(directoryContext);
71
+ }
72
+ else {
73
+ // Fallback to original behavior
74
+ contextParts.push(`Project Directory: ${projectPath}`);
75
+ if (this.showFolderStructureSummary) {
76
+ const summary = await this.generateFolderStructureSummary(projectPath);
77
+ contextParts.push(`Folder Structure Summary:\n${summary}`);
78
+ }
79
+ if (this.listFiles) {
80
+ const filesList = await this.generateFilesList(projectPath);
81
+ contextParts.push(`Files List:\n${filesList}`);
82
+ }
71
83
  }
72
84
  }
73
85
  catch (error) {
@@ -76,13 +88,30 @@ class WorkingDirectoryMessageModifier extends processor_1.BaseMessageModifier {
76
88
  }
77
89
  // Create context message if we have any context parts
78
90
  if (contextParts.length > 0) {
79
- const contextMessage = {
80
- role: 'system',
81
- content: contextParts.join('\n\n'),
82
- name: 'working-directory-context'
83
- };
91
+ const contextContent = contextParts.join('\n\n');
92
+ const messages = [...createdMessage.message.messages];
93
+ // Find existing system message
94
+ const systemMessageIndex = messages.findIndex(msg => msg.role === 'system');
95
+ if (systemMessageIndex !== -1) {
96
+ // Update existing system message
97
+ messages[systemMessageIndex] = {
98
+ ...messages[systemMessageIndex],
99
+ content: `${messages[systemMessageIndex].content}\n\n${contextContent}`
100
+ };
101
+ }
102
+ else {
103
+ // Add new system message at the top
104
+ messages.unshift({
105
+ role: 'system',
106
+ content: contextContent
107
+ });
108
+ }
84
109
  return {
85
- messages: [contextMessage, ...createdMessage.messages],
110
+ ...createdMessage,
111
+ message: {
112
+ ...createdMessage.message,
113
+ messages
114
+ },
86
115
  metadata: {
87
116
  ...createdMessage.metadata,
88
117
  workingDirectoryContextAdded: true,
@@ -99,44 +128,14 @@ class WorkingDirectoryMessageModifier extends processor_1.BaseMessageModifier {
99
128
  }
100
129
  async generateFolderStructureSummary(projectPath) {
101
130
  try {
102
- // Use CodeBolt's directory listing with recursive option
103
- const response = await codeboltjs_1.default.fs.listDirectory({
104
- path: projectPath,
105
- show_hidden: false,
106
- detailed: false,
107
- limit: 200,
108
- notifyUser: false
109
- });
110
131
  const directories = new Set();
111
- // Extract directories from the response
112
- if (response && response.success) {
113
- let entries;
114
- if (typeof response.result === 'string') {
115
- // If result is a string, we'll need to parse it or work with what we have
116
- return response.result.split('\n').slice(0, 20).join('\n');
117
- }
118
- else if (response.result && response.result.entries) {
119
- entries = response.result.entries;
120
- }
121
- else if (response.entries) {
122
- entries = response.entries;
123
- }
124
- if (entries) {
125
- entries.forEach((entry) => {
126
- if (entry.type === 'directory' && !this.shouldIgnore(entry.path || entry.name)) {
127
- directories.add(entry.path || entry.name);
128
- }
129
- // Also get parent directories of files
130
- const dir = path.dirname(entry.path || entry.name);
131
- if (dir !== '.' && !this.shouldIgnore(dir)) {
132
- directories.add(dir);
133
- }
134
- });
135
- }
136
- }
137
- const sortedDirs = Array.from(directories).sort();
132
+ await this.collectDirectories(projectPath, directories, 0, 3); // Max depth of 3
133
+ const sortedDirs = Array.from(directories)
134
+ .filter(dir => dir !== projectPath && !this.shouldIgnore(dir))
135
+ .sort()
136
+ .slice(0, 20);
138
137
  return sortedDirs.length > 0
139
- ? sortedDirs.slice(0, 20).join('\n')
138
+ ? sortedDirs.join('\n')
140
139
  : 'No accessible directories found';
141
140
  }
142
141
  catch (error) {
@@ -145,40 +144,12 @@ class WorkingDirectoryMessageModifier extends processor_1.BaseMessageModifier {
145
144
  }
146
145
  async generateFilesList(projectPath) {
147
146
  try {
148
- // Use CodeBolt's directory listing to get files
149
- const response = await codeboltjs_1.default.fs.listDirectory({
150
- path: projectPath,
151
- show_hidden: false,
152
- detailed: false,
153
- limit: this.listFilesLimit,
154
- notifyUser: false
155
- });
156
147
  const files = [];
157
- // Extract files from the response
158
- if (response && response.success) {
159
- let entries;
160
- if (typeof response.result === 'string') {
161
- // If result is a string, split and filter for files
162
- return response.result.split('\n')
163
- .filter((line) => !this.shouldIgnore(line))
164
- .slice(0, this.listFilesLimit)
165
- .join('\n');
166
- }
167
- else if (response.result && response.result.entries) {
168
- entries = response.result.entries;
169
- }
170
- else if (response.entries) {
171
- entries = response.entries;
172
- }
173
- if (entries) {
174
- entries.forEach((entry) => {
175
- if (entry.type === 'file' && !this.shouldIgnore(entry.path || entry.name)) {
176
- files.push(entry.path || entry.name);
177
- }
178
- });
179
- }
180
- }
181
- const filteredFiles = files.slice(0, this.listFilesLimit);
148
+ await this.collectFiles(projectPath, files, 0, 2); // Max depth of 2
149
+ const filteredFiles = files
150
+ .filter(filePath => !this.shouldIgnore(filePath))
151
+ .slice(0, this.listFilesLimit)
152
+ .map(filePath => path.basename(filePath));
182
153
  return filteredFiles.length > 0
183
154
  ? filteredFiles.join('\n')
184
155
  : 'No accessible files found';
@@ -187,8 +158,235 @@ class WorkingDirectoryMessageModifier extends processor_1.BaseMessageModifier {
187
158
  return 'Unable to generate files list';
188
159
  }
189
160
  }
161
+ async collectDirectories(dirPath, directories, currentDepth, maxDepth) {
162
+ if (currentDepth >= maxDepth)
163
+ return;
164
+ try {
165
+ const entries = await fs.readdir(dirPath, { withFileTypes: true });
166
+ for (const entry of entries) {
167
+ if (entry.isDirectory()) {
168
+ const fullPath = path.join(dirPath, entry.name);
169
+ if (!this.shouldIgnore(fullPath)) {
170
+ directories.add(fullPath);
171
+ await this.collectDirectories(fullPath, directories, currentDepth + 1, maxDepth);
172
+ }
173
+ }
174
+ }
175
+ }
176
+ catch (error) {
177
+ // Skip directories we can't read
178
+ }
179
+ }
180
+ async collectFiles(dirPath, files, currentDepth, maxDepth) {
181
+ if (currentDepth >= maxDepth || files.length >= this.listFilesLimit)
182
+ return;
183
+ try {
184
+ const entries = await fs.readdir(dirPath, { withFileTypes: true });
185
+ for (const entry of entries) {
186
+ if (entry.isFile()) {
187
+ const fullPath = path.join(dirPath, entry.name);
188
+ if (!this.shouldIgnore(fullPath)) {
189
+ files.push(fullPath);
190
+ if (files.length >= this.listFilesLimit)
191
+ break;
192
+ }
193
+ }
194
+ else if (entry.isDirectory() && currentDepth < maxDepth - 1) {
195
+ const fullPath = path.join(dirPath, entry.name);
196
+ if (!this.shouldIgnore(fullPath)) {
197
+ await this.collectFiles(fullPath, files, currentDepth + 1, maxDepth);
198
+ }
199
+ }
200
+ }
201
+ }
202
+ catch (error) {
203
+ // Skip directories we can't read
204
+ }
205
+ }
190
206
  shouldIgnore(filePath) {
191
- return this.listFilesIgnore.some(ignore => filePath.includes(ignore) || path.basename(filePath) === ignore);
207
+ const basename = path.basename(filePath);
208
+ // Ignore any folder/file that starts with a dot
209
+ if (basename.startsWith('.')) {
210
+ return true;
211
+ }
212
+ return this.listFilesIgnore.some(ignore => filePath.includes(ignore) || basename === ignore);
213
+ }
214
+ // Comprehensive directory context methods exactly like gemini-cli
215
+ async getDirectoryContextString(projectPath) {
216
+ const folderStructure = await this.getFolderStructure(projectPath);
217
+ const workingDirPreamble = `I'm currently working in the directory: ${projectPath}`;
218
+ return `${workingDirPreamble}
219
+ Here is the folder structure of the current working directories:
220
+
221
+ ${folderStructure}`;
222
+ }
223
+ async getFolderStructure(directory) {
224
+ const resolvedPath = path.resolve(directory);
225
+ try {
226
+ const structureRoot = await this.readFullStructure(resolvedPath);
227
+ if (!structureRoot) {
228
+ return `Error: Could not read directory "${resolvedPath}". Check path and permissions.`;
229
+ }
230
+ const structureLines = [];
231
+ this.formatStructure(structureRoot, '', true, true, structureLines);
232
+ const isTruncated = this.isTruncated(structureRoot);
233
+ let summary = `Showing up to ${this.maxItems} items (files + folders).`;
234
+ if (isTruncated) {
235
+ summary += ` Folders or files indicated with ${this.truncationIndicator} contain more items not shown, were ignored, or the display limit (${this.maxItems} items) was reached.`;
236
+ }
237
+ return `${summary}\n\n${resolvedPath}${path.sep}\n${structureLines.join('\n')}`;
238
+ }
239
+ catch (error) {
240
+ console.error(`Error getting folder structure for ${resolvedPath}:`, error);
241
+ return `Error processing directory "${resolvedPath}": ${error instanceof Error ? error.message : String(error)}`;
242
+ }
243
+ }
244
+ async readFullStructure(rootPath) {
245
+ const rootName = path.basename(rootPath);
246
+ const rootNode = {
247
+ name: rootName,
248
+ path: rootPath,
249
+ files: [],
250
+ subFolders: [],
251
+ totalChildren: 0,
252
+ totalFiles: 0,
253
+ };
254
+ const queue = [
255
+ { folderInfo: rootNode, currentPath: rootPath },
256
+ ];
257
+ let currentItemCount = 0;
258
+ const processedPaths = new Set();
259
+ while (queue.length > 0) {
260
+ const { folderInfo, currentPath } = queue.shift();
261
+ if (processedPaths.has(currentPath)) {
262
+ continue;
263
+ }
264
+ processedPaths.add(currentPath);
265
+ if (currentItemCount >= this.maxItems) {
266
+ continue;
267
+ }
268
+ let entries;
269
+ try {
270
+ const rawEntries = await fs.readdir(currentPath, { withFileTypes: true });
271
+ entries = rawEntries.sort((a, b) => a.name.localeCompare(b.name));
272
+ }
273
+ catch (error) {
274
+ if (error.code === 'EACCES' || error.code === 'ENOENT') {
275
+ console.warn(`Warning: Could not read directory ${currentPath}: ${error.message}`);
276
+ if (currentPath === rootPath && error.code === 'ENOENT') {
277
+ return null;
278
+ }
279
+ continue;
280
+ }
281
+ throw error;
282
+ }
283
+ const filesInCurrentDir = [];
284
+ const subFoldersInCurrentDir = [];
285
+ // Process files first
286
+ for (const entry of entries) {
287
+ if (entry.isFile()) {
288
+ if (currentItemCount >= this.maxItems) {
289
+ folderInfo.hasMoreFiles = true;
290
+ break;
291
+ }
292
+ const fileName = entry.name;
293
+ const filePath = path.join(currentPath, fileName);
294
+ if (!this.shouldIgnore(filePath)) {
295
+ filesInCurrentDir.push(fileName);
296
+ currentItemCount++;
297
+ folderInfo.totalFiles++;
298
+ folderInfo.totalChildren++;
299
+ }
300
+ }
301
+ }
302
+ folderInfo.files = filesInCurrentDir;
303
+ // Process directories
304
+ for (const entry of entries) {
305
+ if (entry.isDirectory()) {
306
+ if (currentItemCount >= this.maxItems) {
307
+ folderInfo.hasMoreSubfolders = true;
308
+ break;
309
+ }
310
+ const subFolderName = entry.name;
311
+ const subFolderPath = path.join(currentPath, subFolderName);
312
+ const isIgnored = this.defaultIgnoredFolders.has(subFolderName) ||
313
+ subFolderName.startsWith('.') ||
314
+ this.shouldIgnore(subFolderPath);
315
+ if (isIgnored) {
316
+ const ignoredSubFolder = {
317
+ name: subFolderName,
318
+ path: subFolderPath,
319
+ files: [],
320
+ subFolders: [],
321
+ totalChildren: 0,
322
+ totalFiles: 0,
323
+ isIgnored: true,
324
+ };
325
+ subFoldersInCurrentDir.push(ignoredSubFolder);
326
+ currentItemCount++;
327
+ folderInfo.totalChildren++;
328
+ continue;
329
+ }
330
+ const subFolderNode = {
331
+ name: subFolderName,
332
+ path: subFolderPath,
333
+ files: [],
334
+ subFolders: [],
335
+ totalChildren: 0,
336
+ totalFiles: 0,
337
+ };
338
+ subFoldersInCurrentDir.push(subFolderNode);
339
+ currentItemCount++;
340
+ folderInfo.totalChildren++;
341
+ queue.push({ folderInfo: subFolderNode, currentPath: subFolderPath });
342
+ }
343
+ }
344
+ folderInfo.subFolders = subFoldersInCurrentDir;
345
+ }
346
+ return rootNode;
347
+ }
348
+ formatStructure(node, currentIndent, isLastChildOfParent, isProcessingRootNode, builder) {
349
+ const connector = isLastChildOfParent ? '└───' : '├───';
350
+ if (!isProcessingRootNode || node.isIgnored) {
351
+ builder.push(`${currentIndent}${connector}${node.name}${path.sep}${node.isIgnored ? this.truncationIndicator : ''}`);
352
+ }
353
+ const indentForChildren = isProcessingRootNode
354
+ ? ''
355
+ : currentIndent + (isLastChildOfParent ? ' ' : '│ ');
356
+ // Render files
357
+ const fileCount = node.files.length;
358
+ for (let i = 0; i < fileCount; i++) {
359
+ const isLastFileAmongSiblings = i === fileCount - 1 &&
360
+ node.subFolders.length === 0 &&
361
+ !node.hasMoreSubfolders;
362
+ const fileConnector = isLastFileAmongSiblings ? '└───' : '├───';
363
+ builder.push(`${indentForChildren}${fileConnector}${node.files[i]}`);
364
+ }
365
+ if (node.hasMoreFiles) {
366
+ const isLastIndicatorAmongSiblings = node.subFolders.length === 0 && !node.hasMoreSubfolders;
367
+ const fileConnector = isLastIndicatorAmongSiblings ? '└───' : '├───';
368
+ builder.push(`${indentForChildren}${fileConnector}${this.truncationIndicator}`);
369
+ }
370
+ // Render subfolders
371
+ const subFolderCount = node.subFolders.length;
372
+ for (let i = 0; i < subFolderCount; i++) {
373
+ const isLastSubfolderAmongSiblings = i === subFolderCount - 1 && !node.hasMoreSubfolders;
374
+ this.formatStructure(node.subFolders[i], indentForChildren, isLastSubfolderAmongSiblings, false, builder);
375
+ }
376
+ if (node.hasMoreSubfolders) {
377
+ builder.push(`${indentForChildren}└───${this.truncationIndicator}`);
378
+ }
379
+ }
380
+ isTruncated(node) {
381
+ if (node.hasMoreFiles || node.hasMoreSubfolders || node.isIgnored) {
382
+ return true;
383
+ }
384
+ for (const sub of node.subFolders) {
385
+ if (this.isTruncated(sub)) {
386
+ return true;
387
+ }
388
+ }
389
+ return false;
192
390
  }
193
391
  }
194
392
  exports.WorkingDirectoryMessageModifier = WorkingDirectoryMessageModifier;
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,7 @@
1
+ import { ProcessedMessage } from "@codebolt/types/agent";
2
+ import { BasePostInferenceProcessor } from "../base";
3
+ import { LLMResponse } from "@codebolt/types/sdk";
4
+ export declare class CheckForNoToolCall extends BasePostInferenceProcessor {
5
+ constructor();
6
+ modify(llmMessageSent: ProcessedMessage, llmResponseMessage: LLMResponse, nextPrompt: ProcessedMessage): Promise<ProcessedMessage>;
7
+ }
@@ -0,0 +1,24 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.CheckForNoToolCall = void 0;
4
+ const base_1 = require("../base");
5
+ class CheckForNoToolCall extends base_1.BasePostInferenceProcessor {
6
+ constructor() {
7
+ super();
8
+ }
9
+ modify(llmMessageSent, llmResponseMessage, nextPrompt) {
10
+ // Check if tool_calls exist in the LLM response
11
+ const hasToolCalls = llmResponseMessage.tool_calls && llmResponseMessage.tool_calls.length > 0;
12
+ if (!hasToolCalls) {
13
+ // Create a new message indicating no tool call was found
14
+ const noToolCallMessage = {
15
+ role: 'user',
16
+ content: 'no tool call found in request'
17
+ };
18
+ nextPrompt.message.messages.push(noToolCallMessage);
19
+ }
20
+ // If tool calls exist, return the nextPrompt unchanged
21
+ return Promise.resolve(nextPrompt);
22
+ }
23
+ }
24
+ exports.CheckForNoToolCall = CheckForNoToolCall;
@@ -0,0 +1,41 @@
1
+ import { BaseProcessor, ProcessorInput, ProcessorOutput } from '../../processor';
2
+ export interface AdvancedLoopDetectionProcessorOptions {
3
+ toolCallThreshold?: number;
4
+ contentLoopThreshold?: number;
5
+ contentChunkSize?: number;
6
+ maxHistoryLength?: number;
7
+ enableLLMDetection?: boolean;
8
+ llmCheckAfterTurns?: number;
9
+ defaultLLMCheckInterval?: number;
10
+ }
11
+ export declare class AdvancedLoopDetectionProcessor extends BaseProcessor {
12
+ private readonly toolCallThreshold;
13
+ private readonly contentLoopThreshold;
14
+ private readonly contentChunkSize;
15
+ private readonly maxHistoryLength;
16
+ private readonly enableLLMDetection;
17
+ private readonly llmCheckAfterTurns;
18
+ private readonly defaultLLMCheckInterval;
19
+ private lastToolCallKey;
20
+ private toolCallRepetitionCount;
21
+ private streamContentHistory;
22
+ private contentStats;
23
+ private lastContentIndex;
24
+ private loopDetected;
25
+ private inCodeBlock;
26
+ private turnsInCurrentPrompt;
27
+ private llmCheckInterval;
28
+ private lastCheckTurn;
29
+ constructor(options?: AdvancedLoopDetectionProcessorOptions);
30
+ processInput(input: ProcessorInput): Promise<ProcessorOutput[]>;
31
+ private getToolCallKey;
32
+ private checkToolCallLoop;
33
+ private checkContentLoop;
34
+ private truncateAndUpdate;
35
+ private analyzeContentChunksForLoop;
36
+ private hasMoreChunksToProcess;
37
+ private isLoopDetectedForChunk;
38
+ private isActualContentMatch;
39
+ private resetContentTracking;
40
+ reset(): void;
41
+ }