@amodalai/runtime 0.3.32 → 0.3.34
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.
- package/dist/src/session/session-builder.js +21 -0
- package/dist/src/session/session-builder.js.map +1 -1
- package/dist/src/tools/file-tools.d.ts +20 -0
- package/dist/src/tools/file-tools.js +603 -0
- package/dist/src/tools/file-tools.js.map +1 -0
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +4 -4
|
@@ -0,0 +1,603 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license
|
|
3
|
+
* Copyright 2026 Amodal Labs, Inc.
|
|
4
|
+
* SPDX-License-Identifier: MIT
|
|
5
|
+
*/
|
|
6
|
+
/**
|
|
7
|
+
* File tools — sandboxed filesystem access for agent repo directories.
|
|
8
|
+
*
|
|
9
|
+
* Provides 8 tools: read_repo_file, write_repo_file, edit_repo_file,
|
|
10
|
+
* delete_repo_file, list_repo_files, glob_repo_files, grep_repo_files,
|
|
11
|
+
* and read_many_repo_files. All paths are validated against an allowlist
|
|
12
|
+
* of directories and a blocklist of sensitive filenames.
|
|
13
|
+
*
|
|
14
|
+
* When `studioUrl` is set, writes go to Studio's draft API instead of
|
|
15
|
+
* disk, and reads check drafts first (draft overlay).
|
|
16
|
+
*/
|
|
17
|
+
import { readFile, readdir, writeFile, mkdir, unlink } from 'node:fs/promises';
|
|
18
|
+
import * as path from 'node:path';
|
|
19
|
+
import { z } from 'zod';
|
|
20
|
+
// ---------------------------------------------------------------------------
|
|
21
|
+
// Sandbox path resolution (inlined from @amodalai/workspace-tools to avoid
|
|
22
|
+
// making the private workspace-tools package a published dependency)
|
|
23
|
+
// ---------------------------------------------------------------------------
|
|
24
|
+
function resolveSandboxPath(sandboxRoot, requestedPath) {
|
|
25
|
+
if (path.isAbsolute(requestedPath)) {
|
|
26
|
+
throw new FileToolError(`Absolute paths are not allowed: ${requestedPath}`);
|
|
27
|
+
}
|
|
28
|
+
if (requestedPath.includes('\0')) {
|
|
29
|
+
throw new FileToolError('Path contains null bytes');
|
|
30
|
+
}
|
|
31
|
+
const segments = requestedPath.split(/[/\\]/);
|
|
32
|
+
if (segments.includes('..')) {
|
|
33
|
+
throw new FileToolError(`Path traversal is not allowed: ${requestedPath}`);
|
|
34
|
+
}
|
|
35
|
+
const resolved = path.resolve(sandboxRoot, requestedPath);
|
|
36
|
+
if (resolved !== sandboxRoot && !resolved.startsWith(sandboxRoot + path.sep)) {
|
|
37
|
+
throw new FileToolError(`Path escapes sandbox: ${requestedPath}`);
|
|
38
|
+
}
|
|
39
|
+
return resolved;
|
|
40
|
+
}
|
|
41
|
+
// ---------------------------------------------------------------------------
|
|
42
|
+
// Constants
|
|
43
|
+
// ---------------------------------------------------------------------------
|
|
44
|
+
export const DEFAULT_ALLOWED_DIRS = [
|
|
45
|
+
'skills',
|
|
46
|
+
'knowledge',
|
|
47
|
+
'connections',
|
|
48
|
+
'stores',
|
|
49
|
+
'pages',
|
|
50
|
+
'automations',
|
|
51
|
+
'evals',
|
|
52
|
+
'agents',
|
|
53
|
+
'tools',
|
|
54
|
+
];
|
|
55
|
+
export const DEFAULT_BLOCKED_FILES = [
|
|
56
|
+
'.env',
|
|
57
|
+
'amodal.json',
|
|
58
|
+
'package.json',
|
|
59
|
+
'pnpm-lock.yaml',
|
|
60
|
+
'tsconfig.json',
|
|
61
|
+
];
|
|
62
|
+
/** Maximum number of grep results returned. */
|
|
63
|
+
const GREP_MAX_RESULTS = 100;
|
|
64
|
+
/** Maximum number of files for read_many_repo_files. */
|
|
65
|
+
const READ_MANY_MAX_FILES = 20;
|
|
66
|
+
// ---------------------------------------------------------------------------
|
|
67
|
+
// Error class
|
|
68
|
+
// ---------------------------------------------------------------------------
|
|
69
|
+
export class FileToolError extends Error {
|
|
70
|
+
constructor(message) {
|
|
71
|
+
super(message);
|
|
72
|
+
this.name = 'FileToolError';
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
// ---------------------------------------------------------------------------
|
|
76
|
+
// Path validation
|
|
77
|
+
// ---------------------------------------------------------------------------
|
|
78
|
+
function validatePath(repoRoot, filePath, allowedDirs, blockedFiles) {
|
|
79
|
+
const abs = resolveSandboxPath(repoRoot, filePath);
|
|
80
|
+
const rel = path.relative(repoRoot, abs);
|
|
81
|
+
const topDir = rel.split(path.sep)[0];
|
|
82
|
+
if (!allowedDirs.includes(topDir)) {
|
|
83
|
+
throw new FileToolError(`Path "${filePath}" is not in an allowed directory. Allowed: ${allowedDirs.join(', ')}`);
|
|
84
|
+
}
|
|
85
|
+
const basename = path.basename(abs);
|
|
86
|
+
if (blockedFiles.includes(basename)) {
|
|
87
|
+
throw new FileToolError(`File "${basename}" cannot be accessed`);
|
|
88
|
+
}
|
|
89
|
+
return abs;
|
|
90
|
+
}
|
|
91
|
+
/**
|
|
92
|
+
* Validate that a directory path is within allowed dirs.
|
|
93
|
+
* If dir is omitted, returns null (meaning "all allowed dirs").
|
|
94
|
+
*/
|
|
95
|
+
function validateDirPath(repoRoot, dir, allowedDirs) {
|
|
96
|
+
if (!dir)
|
|
97
|
+
return null;
|
|
98
|
+
// The dir itself must be an allowed top-level dir or a subdirectory of one
|
|
99
|
+
const abs = resolveSandboxPath(repoRoot, dir);
|
|
100
|
+
const rel = path.relative(repoRoot, abs);
|
|
101
|
+
const topDir = rel.split(path.sep)[0];
|
|
102
|
+
if (!allowedDirs.includes(topDir)) {
|
|
103
|
+
throw new FileToolError(`Directory "${dir}" is not in an allowed directory. Allowed: ${allowedDirs.join(', ')}`);
|
|
104
|
+
}
|
|
105
|
+
return abs;
|
|
106
|
+
}
|
|
107
|
+
// ---------------------------------------------------------------------------
|
|
108
|
+
// Draft API helpers
|
|
109
|
+
// ---------------------------------------------------------------------------
|
|
110
|
+
async function readFromDraft(studioUrl, filePath, logger) {
|
|
111
|
+
try {
|
|
112
|
+
const res = await fetch(`${studioUrl}/api/drafts/${encodeURIComponent(filePath)}`, {
|
|
113
|
+
signal: AbortSignal.timeout(5000),
|
|
114
|
+
});
|
|
115
|
+
if (res.ok) {
|
|
116
|
+
const raw = await res.json();
|
|
117
|
+
if (raw && typeof raw === 'object' && 'content' in raw) {
|
|
118
|
+
const val = raw['content'];
|
|
119
|
+
if (typeof val === 'string')
|
|
120
|
+
return val;
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
catch (err) {
|
|
125
|
+
logger.debug('draft_read_fallback', { path: filePath, error: err instanceof Error ? err.message : String(err) });
|
|
126
|
+
}
|
|
127
|
+
return null;
|
|
128
|
+
}
|
|
129
|
+
async function writeToDraft(studioUrl, filePath, content) {
|
|
130
|
+
const res = await fetch(`${studioUrl}/api/drafts/${encodeURIComponent(filePath)}`, {
|
|
131
|
+
method: 'PUT',
|
|
132
|
+
headers: { 'Content-Type': 'application/json' },
|
|
133
|
+
body: JSON.stringify({ content }),
|
|
134
|
+
signal: AbortSignal.timeout(10000),
|
|
135
|
+
});
|
|
136
|
+
if (!res.ok) {
|
|
137
|
+
throw new FileToolError(`Failed to save draft: ${res.status} ${res.statusText}`);
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
async function deleteFromDraft(studioUrl, filePath) {
|
|
141
|
+
const res = await fetch(`${studioUrl}/api/drafts/${encodeURIComponent(filePath)}`, {
|
|
142
|
+
method: 'DELETE',
|
|
143
|
+
signal: AbortSignal.timeout(5000),
|
|
144
|
+
});
|
|
145
|
+
if (!res.ok) {
|
|
146
|
+
throw new FileToolError(`Failed to delete draft: ${res.status} ${res.statusText}`);
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
// ---------------------------------------------------------------------------
|
|
150
|
+
// Read helper (with draft overlay)
|
|
151
|
+
// ---------------------------------------------------------------------------
|
|
152
|
+
async function readFileContent(abs, relPath, studioUrl, logger) {
|
|
153
|
+
// Try draft overlay first
|
|
154
|
+
if (studioUrl) {
|
|
155
|
+
const draftContent = await readFromDraft(studioUrl, relPath, logger);
|
|
156
|
+
if (draftContent !== null)
|
|
157
|
+
return draftContent;
|
|
158
|
+
}
|
|
159
|
+
// Fall back to disk
|
|
160
|
+
return readFile(abs, 'utf-8');
|
|
161
|
+
}
|
|
162
|
+
// ---------------------------------------------------------------------------
|
|
163
|
+
// Write helper (draft or disk)
|
|
164
|
+
// ---------------------------------------------------------------------------
|
|
165
|
+
async function writeFileContent(abs, relPath, content, studioUrl) {
|
|
166
|
+
if (studioUrl) {
|
|
167
|
+
await writeToDraft(studioUrl, relPath, content);
|
|
168
|
+
}
|
|
169
|
+
else {
|
|
170
|
+
await mkdir(path.dirname(abs), { recursive: true });
|
|
171
|
+
await writeFile(abs, content, 'utf-8');
|
|
172
|
+
}
|
|
173
|
+
}
|
|
174
|
+
// ---------------------------------------------------------------------------
|
|
175
|
+
// Glob pattern helper
|
|
176
|
+
// ---------------------------------------------------------------------------
|
|
177
|
+
/**
|
|
178
|
+
* Convert a simple glob pattern to a RegExp.
|
|
179
|
+
* Supports *, **, and ? wildcards.
|
|
180
|
+
*/
|
|
181
|
+
function globToRegex(pattern) {
|
|
182
|
+
let regexStr = '';
|
|
183
|
+
let i = 0;
|
|
184
|
+
while (i < pattern.length) {
|
|
185
|
+
const char = pattern[i];
|
|
186
|
+
if (char === '*') {
|
|
187
|
+
if (pattern[i + 1] === '*') {
|
|
188
|
+
// ** matches any path segments
|
|
189
|
+
regexStr += '.*';
|
|
190
|
+
i += 2;
|
|
191
|
+
// Skip trailing separator after **
|
|
192
|
+
if (pattern[i] === '/' || pattern[i] === path.sep) {
|
|
193
|
+
i += 1;
|
|
194
|
+
}
|
|
195
|
+
}
|
|
196
|
+
else {
|
|
197
|
+
// * matches anything except path separator
|
|
198
|
+
regexStr += '[^/]*';
|
|
199
|
+
i += 1;
|
|
200
|
+
}
|
|
201
|
+
}
|
|
202
|
+
else if (char === '?') {
|
|
203
|
+
regexStr += '[^/]';
|
|
204
|
+
i += 1;
|
|
205
|
+
}
|
|
206
|
+
else if (char === '.') {
|
|
207
|
+
regexStr += '\\.';
|
|
208
|
+
i += 1;
|
|
209
|
+
}
|
|
210
|
+
else {
|
|
211
|
+
regexStr += char;
|
|
212
|
+
i += 1;
|
|
213
|
+
}
|
|
214
|
+
}
|
|
215
|
+
return new RegExp(`^${regexStr}$`);
|
|
216
|
+
}
|
|
217
|
+
// ---------------------------------------------------------------------------
|
|
218
|
+
// Recursive directory listing
|
|
219
|
+
// ---------------------------------------------------------------------------
|
|
220
|
+
async function listFilesRecursive(dirPath, basePath, logger) {
|
|
221
|
+
const results = [];
|
|
222
|
+
try {
|
|
223
|
+
const entries = await readdir(dirPath, { withFileTypes: true });
|
|
224
|
+
for (const entry of entries) {
|
|
225
|
+
const fullPath = path.join(dirPath, entry.name);
|
|
226
|
+
const relPath = path.relative(basePath, fullPath);
|
|
227
|
+
if (entry.isDirectory()) {
|
|
228
|
+
const subFiles = await listFilesRecursive(fullPath, basePath, logger);
|
|
229
|
+
results.push(...subFiles);
|
|
230
|
+
}
|
|
231
|
+
else {
|
|
232
|
+
results.push(relPath);
|
|
233
|
+
}
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
catch (err) {
|
|
237
|
+
logger.debug('file_tool_readdir_skipped', { dir: dirPath, error: err instanceof Error ? err.message : String(err) });
|
|
238
|
+
}
|
|
239
|
+
return results;
|
|
240
|
+
}
|
|
241
|
+
// ---------------------------------------------------------------------------
|
|
242
|
+
// Tool registration
|
|
243
|
+
// ---------------------------------------------------------------------------
|
|
244
|
+
export function registerFileTools(registry, opts) {
|
|
245
|
+
const { repoRoot, allowedDirs, blockedFiles, studioUrl, logger } = opts;
|
|
246
|
+
// -------------------------------------------------------------------------
|
|
247
|
+
// read_repo_file
|
|
248
|
+
// -------------------------------------------------------------------------
|
|
249
|
+
registry.register('read_repo_file', {
|
|
250
|
+
description: 'Read a file from the agent repository. Supports optional line-based offset and limit for large files.',
|
|
251
|
+
parameters: z.object({
|
|
252
|
+
path: z.string().describe('Relative path to the file within the repo'),
|
|
253
|
+
offset: z.number().optional().describe('Line number to start reading from (0-based)'),
|
|
254
|
+
limit: z.number().optional().describe('Maximum number of lines to return'),
|
|
255
|
+
}),
|
|
256
|
+
readOnly: true,
|
|
257
|
+
metadata: { category: 'system' },
|
|
258
|
+
async execute(params, _ctx) {
|
|
259
|
+
const startMs = Date.now();
|
|
260
|
+
try {
|
|
261
|
+
const abs = validatePath(repoRoot, params.path, allowedDirs, blockedFiles);
|
|
262
|
+
const relPath = path.relative(repoRoot, abs);
|
|
263
|
+
logger.debug('file_tool_call', { tool: 'read_repo_file', path: params.path });
|
|
264
|
+
let content = await readFileContent(abs, relPath, studioUrl, logger);
|
|
265
|
+
// Apply line-based offset/limit
|
|
266
|
+
if (params.offset !== undefined || params.limit !== undefined) {
|
|
267
|
+
const lines = content.split('\n');
|
|
268
|
+
const start = params.offset ?? 0;
|
|
269
|
+
const end = params.limit !== undefined ? start + params.limit : lines.length;
|
|
270
|
+
content = lines.slice(start, end).join('\n');
|
|
271
|
+
}
|
|
272
|
+
const durationMs = Date.now() - startMs;
|
|
273
|
+
logger.debug('file_tool_complete', { tool: 'read_repo_file', path: params.path, durationMs });
|
|
274
|
+
return content;
|
|
275
|
+
}
|
|
276
|
+
catch (err) {
|
|
277
|
+
const durationMs = Date.now() - startMs;
|
|
278
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
279
|
+
logger.debug('file_tool_error', { tool: 'read_repo_file', path: params.path, error: message, durationMs });
|
|
280
|
+
return { error: message };
|
|
281
|
+
}
|
|
282
|
+
},
|
|
283
|
+
});
|
|
284
|
+
// -------------------------------------------------------------------------
|
|
285
|
+
// write_repo_file
|
|
286
|
+
// -------------------------------------------------------------------------
|
|
287
|
+
registry.register('write_repo_file', {
|
|
288
|
+
description: 'Write content to a file in the agent repository. Creates parent directories as needed.',
|
|
289
|
+
parameters: z.object({
|
|
290
|
+
path: z.string().describe('Relative path to the file within the repo'),
|
|
291
|
+
content: z.string().describe('The content to write to the file'),
|
|
292
|
+
}),
|
|
293
|
+
readOnly: false,
|
|
294
|
+
metadata: { category: 'system' },
|
|
295
|
+
async execute(params, _ctx) {
|
|
296
|
+
const startMs = Date.now();
|
|
297
|
+
try {
|
|
298
|
+
const abs = validatePath(repoRoot, params.path, allowedDirs, blockedFiles);
|
|
299
|
+
const relPath = path.relative(repoRoot, abs);
|
|
300
|
+
logger.debug('file_tool_call', { tool: 'write_repo_file', path: params.path });
|
|
301
|
+
await writeFileContent(abs, relPath, params.content, studioUrl);
|
|
302
|
+
const durationMs = Date.now() - startMs;
|
|
303
|
+
logger.debug('file_tool_complete', { tool: 'write_repo_file', path: params.path, durationMs });
|
|
304
|
+
return { success: true, path: params.path };
|
|
305
|
+
}
|
|
306
|
+
catch (err) {
|
|
307
|
+
const durationMs = Date.now() - startMs;
|
|
308
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
309
|
+
logger.debug('file_tool_error', { tool: 'write_repo_file', path: params.path, error: message, durationMs });
|
|
310
|
+
return { error: message };
|
|
311
|
+
}
|
|
312
|
+
},
|
|
313
|
+
});
|
|
314
|
+
// -------------------------------------------------------------------------
|
|
315
|
+
// edit_repo_file
|
|
316
|
+
// -------------------------------------------------------------------------
|
|
317
|
+
registry.register('edit_repo_file', {
|
|
318
|
+
description: 'Edit a file by replacing a string. Reads the current content, finds old_string, and replaces it with new_string. ' +
|
|
319
|
+
'If multiple matches are found and allow_multiple is not set, returns an error.',
|
|
320
|
+
parameters: z.object({
|
|
321
|
+
path: z.string().describe('Relative path to the file within the repo'),
|
|
322
|
+
old_string: z.string().describe('The exact string to find and replace'),
|
|
323
|
+
new_string: z.string().describe('The replacement string'),
|
|
324
|
+
allow_multiple: z.boolean().optional().describe('Allow replacing all occurrences if multiple matches found'),
|
|
325
|
+
}),
|
|
326
|
+
readOnly: false,
|
|
327
|
+
metadata: { category: 'system' },
|
|
328
|
+
async execute(params, _ctx) {
|
|
329
|
+
const startMs = Date.now();
|
|
330
|
+
try {
|
|
331
|
+
const abs = validatePath(repoRoot, params.path, allowedDirs, blockedFiles);
|
|
332
|
+
const relPath = path.relative(repoRoot, abs);
|
|
333
|
+
logger.debug('file_tool_call', { tool: 'edit_repo_file', path: params.path });
|
|
334
|
+
const content = await readFileContent(abs, relPath, studioUrl, logger);
|
|
335
|
+
// Count occurrences
|
|
336
|
+
let count = 0;
|
|
337
|
+
let idx = 0;
|
|
338
|
+
while (true) {
|
|
339
|
+
idx = content.indexOf(params.old_string, idx);
|
|
340
|
+
if (idx === -1)
|
|
341
|
+
break;
|
|
342
|
+
count += 1;
|
|
343
|
+
idx += params.old_string.length;
|
|
344
|
+
}
|
|
345
|
+
if (count === 0) {
|
|
346
|
+
return { error: `String not found in ${params.path}` };
|
|
347
|
+
}
|
|
348
|
+
if (count > 1 && !params.allow_multiple) {
|
|
349
|
+
return { error: `Multiple matches found (${String(count)}), set allow_multiple: true to replace all` };
|
|
350
|
+
}
|
|
351
|
+
// Replace
|
|
352
|
+
let newContent;
|
|
353
|
+
if (params.allow_multiple) {
|
|
354
|
+
newContent = content.split(params.old_string).join(params.new_string);
|
|
355
|
+
}
|
|
356
|
+
else {
|
|
357
|
+
newContent = content.replace(params.old_string, params.new_string);
|
|
358
|
+
}
|
|
359
|
+
await writeFileContent(abs, relPath, newContent, studioUrl);
|
|
360
|
+
const durationMs = Date.now() - startMs;
|
|
361
|
+
logger.debug('file_tool_complete', { tool: 'edit_repo_file', path: params.path, replacements: count, durationMs });
|
|
362
|
+
return { success: true, path: params.path, replacements: count };
|
|
363
|
+
}
|
|
364
|
+
catch (err) {
|
|
365
|
+
const durationMs = Date.now() - startMs;
|
|
366
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
367
|
+
logger.debug('file_tool_error', { tool: 'edit_repo_file', path: params.path, error: message, durationMs });
|
|
368
|
+
return { error: message };
|
|
369
|
+
}
|
|
370
|
+
},
|
|
371
|
+
});
|
|
372
|
+
// -------------------------------------------------------------------------
|
|
373
|
+
// delete_repo_file
|
|
374
|
+
// -------------------------------------------------------------------------
|
|
375
|
+
registry.register('delete_repo_file', {
|
|
376
|
+
description: 'Delete a file from the agent repository.',
|
|
377
|
+
parameters: z.object({
|
|
378
|
+
path: z.string().describe('Relative path to the file within the repo'),
|
|
379
|
+
}),
|
|
380
|
+
readOnly: false,
|
|
381
|
+
metadata: { category: 'system' },
|
|
382
|
+
async execute(params, _ctx) {
|
|
383
|
+
const startMs = Date.now();
|
|
384
|
+
try {
|
|
385
|
+
const abs = validatePath(repoRoot, params.path, allowedDirs, blockedFiles);
|
|
386
|
+
const relPath = path.relative(repoRoot, abs);
|
|
387
|
+
logger.debug('file_tool_call', { tool: 'delete_repo_file', path: params.path });
|
|
388
|
+
if (studioUrl) {
|
|
389
|
+
await deleteFromDraft(studioUrl, relPath);
|
|
390
|
+
}
|
|
391
|
+
else {
|
|
392
|
+
await unlink(abs);
|
|
393
|
+
}
|
|
394
|
+
const durationMs = Date.now() - startMs;
|
|
395
|
+
logger.debug('file_tool_complete', { tool: 'delete_repo_file', path: params.path, durationMs });
|
|
396
|
+
return { success: true, path: params.path };
|
|
397
|
+
}
|
|
398
|
+
catch (err) {
|
|
399
|
+
const durationMs = Date.now() - startMs;
|
|
400
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
401
|
+
logger.debug('file_tool_error', { tool: 'delete_repo_file', path: params.path, error: message, durationMs });
|
|
402
|
+
return { error: message };
|
|
403
|
+
}
|
|
404
|
+
},
|
|
405
|
+
});
|
|
406
|
+
// -------------------------------------------------------------------------
|
|
407
|
+
// list_repo_files
|
|
408
|
+
// -------------------------------------------------------------------------
|
|
409
|
+
registry.register('list_repo_files', {
|
|
410
|
+
description: 'List files in the agent repository. If dir is provided, lists that directory. ' +
|
|
411
|
+
'If omitted, lists all allowed directories.',
|
|
412
|
+
parameters: z.object({
|
|
413
|
+
dir: z.string().optional().describe('Directory to list (relative path). If omitted, lists all allowed directories.'),
|
|
414
|
+
}),
|
|
415
|
+
readOnly: true,
|
|
416
|
+
metadata: { category: 'system' },
|
|
417
|
+
async execute(params, _ctx) {
|
|
418
|
+
const startMs = Date.now();
|
|
419
|
+
try {
|
|
420
|
+
logger.debug('file_tool_call', { tool: 'list_repo_files', dir: params.dir });
|
|
421
|
+
let files;
|
|
422
|
+
if (params.dir) {
|
|
423
|
+
const absDir = validateDirPath(repoRoot, params.dir, allowedDirs);
|
|
424
|
+
if (!absDir) {
|
|
425
|
+
return { error: 'Invalid directory' };
|
|
426
|
+
}
|
|
427
|
+
files = await listFilesRecursive(absDir, repoRoot, logger);
|
|
428
|
+
}
|
|
429
|
+
else {
|
|
430
|
+
// List all allowed directories
|
|
431
|
+
files = [];
|
|
432
|
+
for (const dir of allowedDirs) {
|
|
433
|
+
const absDir = path.join(repoRoot, dir);
|
|
434
|
+
const dirFiles = await listFilesRecursive(absDir, repoRoot, logger);
|
|
435
|
+
files.push(...dirFiles);
|
|
436
|
+
}
|
|
437
|
+
}
|
|
438
|
+
const durationMs = Date.now() - startMs;
|
|
439
|
+
logger.debug('file_tool_complete', { tool: 'list_repo_files', fileCount: files.length, durationMs });
|
|
440
|
+
return { files };
|
|
441
|
+
}
|
|
442
|
+
catch (err) {
|
|
443
|
+
const durationMs = Date.now() - startMs;
|
|
444
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
445
|
+
logger.debug('file_tool_error', { tool: 'list_repo_files', error: message, durationMs });
|
|
446
|
+
return { error: message };
|
|
447
|
+
}
|
|
448
|
+
},
|
|
449
|
+
});
|
|
450
|
+
// -------------------------------------------------------------------------
|
|
451
|
+
// glob_repo_files
|
|
452
|
+
// -------------------------------------------------------------------------
|
|
453
|
+
registry.register('glob_repo_files', {
|
|
454
|
+
description: 'Find files matching a glob pattern in the agent repository. ' +
|
|
455
|
+
'Supports *, **, and ? wildcards. Only searches allowed directories.',
|
|
456
|
+
parameters: z.object({
|
|
457
|
+
pattern: z.string().describe('Glob pattern to match files against (e.g., "**/*.yaml", "skills/*.md")'),
|
|
458
|
+
}),
|
|
459
|
+
readOnly: true,
|
|
460
|
+
metadata: { category: 'system' },
|
|
461
|
+
async execute(params, _ctx) {
|
|
462
|
+
const startMs = Date.now();
|
|
463
|
+
try {
|
|
464
|
+
logger.debug('file_tool_call', { tool: 'glob_repo_files', pattern: params.pattern });
|
|
465
|
+
const regex = globToRegex(params.pattern);
|
|
466
|
+
const matches = [];
|
|
467
|
+
for (const dir of allowedDirs) {
|
|
468
|
+
const absDir = path.join(repoRoot, dir);
|
|
469
|
+
const files = await listFilesRecursive(absDir, repoRoot, logger);
|
|
470
|
+
for (const file of files) {
|
|
471
|
+
if (regex.test(file)) {
|
|
472
|
+
matches.push(file);
|
|
473
|
+
}
|
|
474
|
+
}
|
|
475
|
+
}
|
|
476
|
+
const durationMs = Date.now() - startMs;
|
|
477
|
+
logger.debug('file_tool_complete', { tool: 'glob_repo_files', matchCount: matches.length, durationMs });
|
|
478
|
+
return { files: matches };
|
|
479
|
+
}
|
|
480
|
+
catch (err) {
|
|
481
|
+
const durationMs = Date.now() - startMs;
|
|
482
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
483
|
+
logger.debug('file_tool_error', { tool: 'glob_repo_files', error: message, durationMs });
|
|
484
|
+
return { error: message };
|
|
485
|
+
}
|
|
486
|
+
},
|
|
487
|
+
});
|
|
488
|
+
// -------------------------------------------------------------------------
|
|
489
|
+
// grep_repo_files
|
|
490
|
+
// -------------------------------------------------------------------------
|
|
491
|
+
registry.register('grep_repo_files', {
|
|
492
|
+
description: 'Search file contents with a regex pattern. Returns matching lines with file path and line number. ' +
|
|
493
|
+
'Capped at 100 results. Only searches allowed directories.',
|
|
494
|
+
parameters: z.object({
|
|
495
|
+
pattern: z.string().describe('Regex pattern to search for in file contents'),
|
|
496
|
+
dir: z.string().optional().describe('Directory to search in (relative path). If omitted, searches all allowed directories.'),
|
|
497
|
+
}),
|
|
498
|
+
readOnly: true,
|
|
499
|
+
metadata: { category: 'system' },
|
|
500
|
+
async execute(params, _ctx) {
|
|
501
|
+
const startMs = Date.now();
|
|
502
|
+
try {
|
|
503
|
+
logger.debug('file_tool_call', { tool: 'grep_repo_files', pattern: params.pattern, dir: params.dir });
|
|
504
|
+
let regex;
|
|
505
|
+
try {
|
|
506
|
+
regex = new RegExp(params.pattern);
|
|
507
|
+
}
|
|
508
|
+
catch {
|
|
509
|
+
return { error: `Invalid regex pattern: ${params.pattern}` };
|
|
510
|
+
}
|
|
511
|
+
const results = [];
|
|
512
|
+
// Determine which directories to search
|
|
513
|
+
const dirsToSearch = [];
|
|
514
|
+
if (params.dir) {
|
|
515
|
+
const absDir = validateDirPath(repoRoot, params.dir, allowedDirs);
|
|
516
|
+
if (!absDir) {
|
|
517
|
+
return { error: 'Invalid directory' };
|
|
518
|
+
}
|
|
519
|
+
dirsToSearch.push(params.dir);
|
|
520
|
+
}
|
|
521
|
+
else {
|
|
522
|
+
dirsToSearch.push(...allowedDirs);
|
|
523
|
+
}
|
|
524
|
+
for (const dir of dirsToSearch) {
|
|
525
|
+
if (results.length >= GREP_MAX_RESULTS)
|
|
526
|
+
break;
|
|
527
|
+
const absDir = path.join(repoRoot, dir);
|
|
528
|
+
const files = await listFilesRecursive(absDir, repoRoot, logger);
|
|
529
|
+
for (const file of files) {
|
|
530
|
+
if (results.length >= GREP_MAX_RESULTS)
|
|
531
|
+
break;
|
|
532
|
+
const absFile = path.join(repoRoot, file);
|
|
533
|
+
try {
|
|
534
|
+
const content = await readFile(absFile, 'utf-8');
|
|
535
|
+
const lines = content.split('\n');
|
|
536
|
+
for (let i = 0; i < lines.length; i++) {
|
|
537
|
+
if (results.length >= GREP_MAX_RESULTS)
|
|
538
|
+
break;
|
|
539
|
+
if (regex.test(lines[i])) {
|
|
540
|
+
results.push({ file, line: i + 1, content: lines[i] });
|
|
541
|
+
}
|
|
542
|
+
}
|
|
543
|
+
}
|
|
544
|
+
catch (err) {
|
|
545
|
+
logger.debug('file_tool_grep_skip', { file, error: err instanceof Error ? err.message : String(err) });
|
|
546
|
+
}
|
|
547
|
+
}
|
|
548
|
+
}
|
|
549
|
+
const durationMs = Date.now() - startMs;
|
|
550
|
+
logger.debug('file_tool_complete', { tool: 'grep_repo_files', resultCount: results.length, durationMs });
|
|
551
|
+
return { results, truncated: results.length >= GREP_MAX_RESULTS };
|
|
552
|
+
}
|
|
553
|
+
catch (err) {
|
|
554
|
+
const durationMs = Date.now() - startMs;
|
|
555
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
556
|
+
logger.debug('file_tool_error', { tool: 'grep_repo_files', error: message, durationMs });
|
|
557
|
+
return { error: message };
|
|
558
|
+
}
|
|
559
|
+
},
|
|
560
|
+
});
|
|
561
|
+
// -------------------------------------------------------------------------
|
|
562
|
+
// read_many_repo_files
|
|
563
|
+
// -------------------------------------------------------------------------
|
|
564
|
+
registry.register('read_many_repo_files', {
|
|
565
|
+
description: 'Read multiple files at once. Returns an object mapping each path to its content. ' +
|
|
566
|
+
`Maximum ${String(READ_MANY_MAX_FILES)} files per call.`,
|
|
567
|
+
parameters: z.object({
|
|
568
|
+
paths: z.array(z.string()).max(READ_MANY_MAX_FILES).describe(`Array of relative file paths to read (max ${String(READ_MANY_MAX_FILES)})`),
|
|
569
|
+
}),
|
|
570
|
+
readOnly: true,
|
|
571
|
+
metadata: { category: 'system' },
|
|
572
|
+
async execute(params, _ctx) {
|
|
573
|
+
const startMs = Date.now();
|
|
574
|
+
try {
|
|
575
|
+
logger.debug('file_tool_call', { tool: 'read_many_repo_files', fileCount: params.paths.length });
|
|
576
|
+
if (params.paths.length > READ_MANY_MAX_FILES) {
|
|
577
|
+
return { error: `Too many files requested. Maximum is ${String(READ_MANY_MAX_FILES)}.` };
|
|
578
|
+
}
|
|
579
|
+
const results = {};
|
|
580
|
+
for (const filePath of params.paths) {
|
|
581
|
+
try {
|
|
582
|
+
const abs = validatePath(repoRoot, filePath, allowedDirs, blockedFiles);
|
|
583
|
+
const relPath = path.relative(repoRoot, abs);
|
|
584
|
+
results[filePath] = await readFileContent(abs, relPath, studioUrl, logger);
|
|
585
|
+
}
|
|
586
|
+
catch (err) {
|
|
587
|
+
results[filePath] = { error: err instanceof Error ? err.message : String(err) };
|
|
588
|
+
}
|
|
589
|
+
}
|
|
590
|
+
const durationMs = Date.now() - startMs;
|
|
591
|
+
logger.debug('file_tool_complete', { tool: 'read_many_repo_files', fileCount: params.paths.length, durationMs });
|
|
592
|
+
return results;
|
|
593
|
+
}
|
|
594
|
+
catch (err) {
|
|
595
|
+
const durationMs = Date.now() - startMs;
|
|
596
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
597
|
+
logger.debug('file_tool_error', { tool: 'read_many_repo_files', error: message, durationMs });
|
|
598
|
+
return { error: message };
|
|
599
|
+
}
|
|
600
|
+
},
|
|
601
|
+
});
|
|
602
|
+
}
|
|
603
|
+
//# sourceMappingURL=file-tools.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"file-tools.js","sourceRoot":"","sources":["../../../src/tools/file-tools.ts"],"names":[],"mappings":"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"}
|