文件系统应用程序接口参考
AG-Kit 文件系统工具的完整应用程序接口文档,包含方法签名、输入/输出模式及实际使用示例。应用程序接口概览
文件系统应用程序接口提供跨多种执行后端工作的工具,具有一致的接口和类型安全特性。可用工具
独立工具
- ReadTool - 支持编码方式读取文件内容
- WriteTool - 支持目录创建的文件写入功能
- EditTool - 对现有文件进行针对性编辑
- GlobTool - 使用通配符模式查找文件
- GrepTool - 使用正则表达式搜索文件内容
- LsTool - 列出目录内容及详细信息
综合工具
- StrReplaceEditor - 面向AI编码工作流的高级多操作文件编辑器
快速对比
| 特性 | 本地模式 | 内存模式 | 沙盒模式 |
|---|---|---|---|
| 性能 | ✅ 最高 | ✅ 高 | ⚠️ 网络开销 |
| 安全性 | ⚠️ 完全访问 | ✅ 隔离 | ✅ 沙盒化 |
| 持久性 | ✅ 永久 | ❌ 临时 | ✅ 会话级 |
| 测试支持 | ⚠️ 副作用 | ✅ 理想 | ⚠️ 复杂配置 |
配置
本地文件操作器
复制
import { LocalFileOperator } from '@ag-kit/tools/fs';
const context = {
workingDirectory: process.cwd(),
fsOperator: new LocalFileOperator()
};
内存文件操作器
复制
import { InMemoryFileOperator } from '@ag-kit/tools/fs';
import { fs } from 'memfs';
const context = {
workingDirectory: '/virtual',
fsOperator: new InMemoryFileOperator(fs)
};
沙盒文件操作器
复制
import { SandboxFileOperator } from '@ag-kit/tools/fs';
const context = {
workingDirectory: '/home/user',
fsOperator: new SandboxFileOperator({ sandbox })
};
事务支持
事务支持允许您将多个文件操作分组,并在需要时回滚。TransactionFileOperator 可包装任何基础操作器(本地、内存或沙盒)以提供原子操作。
基础用法
复制
import { TransactionFileOperator, TransactionExecutor } from '@ag-kit/tools/fs/transaction';
import { LocalFileOperator } from '@ag-kit/tools/fs';
// 用事务支持包装任何基础操作器
const baseOperator = new LocalFileOperator(); // 或 InMemoryFileOperator, SandboxFileOperator
const transactionOperator = new TransactionFileOperator(baseOperator);
const context = {
workingDirectory: process.cwd(),
fsOperator: transactionOperator
};
手动事务控制
复制
await transactionOperator.beginTransaction();
try {
await writeTool.invoke({
file_path: 'config.json',
content: '{"version": "2.0"}'
});
await editTool.invoke({
file_path: 'package.json',
old_string: '"version": "1.0.0"',
new_string: '"version": "2.0.0"'
});
await transactionOperator.commitTransaction();
} catch (error) {
await transactionOperator.rollbackTransaction(); // 所有变更将被回滚
}
执行器模式(推荐)
复制
import { TransactionExecutor, createTransactionExecutor, withTransaction } from '@ag-kit/tools/fs/transaction';
// 方法1:使用 TransactionExecutor 类
const executor = new TransactionExecutor(baseOperator);
const result = await executor.executeInTransaction(async (transactionOperator) => {
// 所有操作自动具备事务性
await writeTool.invoke({
file_path: 'data.json',
content: JSON.stringify(data)
});
await editTool.invoke({
file_path: 'config.ts',
old_string: 'DEBUG = false',
new_string: 'DEBUG = true'
});
// 若此处抛出异常,所有操作将自动回滚
if (!validateData(data)) {
throw new Error('Validation failed');
}
return { filesModified: 2 };
});
// 方法2:使用便捷函数
const result2 = await withTransaction(baseOperator, async (transactionOperator) => {
// 同上操作
return { success: true };
});
// 方法3:使用构建器模式
const executor2 = createTransactionExecutor(baseOperator);
const builderResult = await executor2
.writeFile('config.json', JSON.stringify(config))
.mkdir('logs', { recursive: true })
.custom(async (op) => {
// 自定义操作
await op.writeFile('logs/app.log', 'Application started');
})
.execute();
if (builderResult.success) {
console.log('All operations completed successfully');
} else {
console.error('Transaction failed:', builderResult.error);
}
实际示例
安全配置更新
复制
async function updateConfig(newConfig: Config) {
const executor = new TransactionExecutor(transactionOperator);
return await executor.execute(async () => {
// 更新主配置
await writeTool.invoke({
file_path: 'config.json',
content: JSON.stringify(newConfig, null, 2)
});
// 更新 package.json 版本
await editTool.invoke({
file_path: 'package.json',
old_string: `"version": "${oldConfig.version}"`,
new_string: `"version": "${newConfig.version}"`
});
// 验证 - 若失败则回滚
if (!isValidConfig(newConfig)) {
throw new Error('Invalid configuration');
}
return { updated: true };
});
}
批量文件处理
复制
async function processFiles(files: string[]) {
const executor = new TransactionExecutor(transactionOperator);
return await executor.execute(async () => {
for (const file of files) {
const content = await readTool.invoke({ file_path: file });
const processed = processContent(content);
await writeTool.invoke({
file_path: file,
content: processed
});
}
return { processed: files.length };
});
}
独立工具用法
ReadTool
复制
import { createReadTool } from '@ag-kit/tools/fs';
const readTool = createReadTool(context);
// 读取完整文件
const result = await readTool.invoke({
file_path: 'src/config.json'
});
// 按行范围读取
const partialResult = await readTool.invoke({
file_path: 'large-file.txt',
start_line: 100,
end_line: 200
});
WriteTool
复制
import { createWriteTool } from '@ag-kit/tools/fs';
const writeTool = createWriteTool(context);
const result = await writeTool.invoke({
file_path: 'output/data.json',
content: JSON.stringify({ message: 'Hello World' }, null, 2),
create_directories: true
});
EditTool
复制
import { createEditTool } from '@ag-kit/tools/fs';
const editTool = createEditTool(context);
const result = await editTool.invoke({
file_path: 'src/config.ts',
old_string: 'const API_URL = "http://localhost"',
new_string: 'const API_URL = "https://api.production.com"',
expected_replacements: 1 // 可选:验证精确替换次数
});
GlobTool
复制
import { createGlobTool } from '@ag-kit/tools/fs';
const globTool = createGlobTool(context);
const result = await globTool.invoke({
pattern: '**/*.ts',
exclude_patterns: ['node_modules/**', 'dist/**']
});
GrepTool
复制
import { createGrepTool } from '@ag-kit/tools
});
// 创建新文件
await editor.invoke({
command: 'create',
path: 'new-file.ts',
file_text: 'export const config = {};'
});
应用程序接口参考
通用接口
复制
interface ExecutionContext {
workingDirectory: string;
fsOperator: BaseFileOperator;
messageHandler?: any;
}
interface ToolResponse {
success: boolean;
error?: string;
error_type?: 'validation' | 'security' | 'file_not_found' | 'permission' | 'execution';
[key: string]: any;
}
文件系统工具包配置
复制
/**
* FilesystemToolkit的配置选项
*/
interface FilesystemToolkitConfig {
/**
* 文件编辑操作模式
* - 'integrated': 使用str-replace-editor工具(单一工具处理读写编辑操作)
* - 'atomic': 使用独立的读、写和编辑工具
* - 'enhanced': 使用原子工具加批量操作的多编辑工具
*/
mode: "integrated" | "atomic" | "enhanced";
}
interface FilesystemToolkitOptions extends IToolkitOptions {
context: ExecutionContext;
config?: FilesystemToolkitConfig;
}
class FilesystemToolkit extends BaseToolkit {
constructor(options: FilesystemToolkitOptions);
// 按类别获取工具
getFileOperationTools(): BaseTool[];
getUtilityTools(): BaseTool[];
// 配置管理
getConfig(): FilesystemToolkitConfig;
switchMode(mode: "integrated" | "atomic"): void;
// 统计信息
getStats(): { mode: string };
}
// 使用示例
const toolkit = new FilesystemToolkit({
context: {
workingDirectory: process.cwd(),
fsOperator: new LocalFileOperator()
},
config: {
mode: "enhanced" // 使用原子工具+多编辑模式
}
});
// 动态切换模式
toolkit.switchMode("integrated"); // 切换到str-replace-editor
toolkit.switchMode("enhanced"); // 切换回增强模式
工具参数
复制
// ReadTool
interface ReadToolParams {
file_path: string;
start_line?: number;
end_line?: number;
encoding?: BufferEncoding;
}
// WriteTool
interface WriteToolParams {
file_path: string;
content: string;
create_directories?: boolean;
encoding?: BufferEncoding;
}
// EditTool
interface EditToolParams {
file_path: string;
old_string: string;
new_string: string;
expected_replacements?: number;
}
// GlobTool
interface GlobToolParams {
pattern: string;
exclude_patterns?: string[];
include_directories?: boolean;
max_results?: number;
}
// GrepTool
interface GrepToolParams {
pattern: string;
file_pattern?: string;
case_sensitive?: boolean;
max_results?: number;
context_lines?: number;
}
// LsTool
interface LsToolParams {
directory_path: string;
recursive?: boolean;
show_hidden?: boolean;
include_stats?: boolean;
}
事务接口
复制
// 基础操作器的事务包装器
class TransactionFileOperator extends BaseFileOperator {
constructor(baseOperator: BaseFileOperator, operatorType?: EOperatorType);
// 事务管理
beginTransaction(): Promise<void>;
commitTransaction(): Promise<void>;
rollbackTransaction(): Promise<void>;
resetTransactionState(): void;
// 状态与配置
isTransactionActive(): boolean;
getTransactionOperations(): readonly TransactionOperation[];
setConfig(config: Partial<ITransactionFileOperatorConfig>): void;
getConfig(): ITransactionFileOperatorConfig;
// 所有BaseFileOperator方法均可用
// (readFile, writeFile, mkdir, unlink等)
}
// 事务执行器,便于操作管理
class TransactionExecutor {
constructor(baseOperator: BaseFileOperator);
// 获取底层事务操作器
getOperator(): TransactionFileOperator;
// 构建器模式方法
writeFile(path: string, data: string | Buffer, options?: any): TransactionExecutor;
mkdir(path: string, options?: any): TransactionExecutor;
custom(operation: (op: TransactionFileOperator) => Promise<void>): TransactionExecutor;
// 执行方法
execute(): Promise<{ success: boolean; error?: Error }>;
executeInTransaction<T>(operation: (operator: TransactionFileOperator) => Promise<T>): Promise<T>;
createTransaction(): Promise<TransactionController>;
}
// 手动事务控制
class TransactionController {
constructor(transactionOperator: TransactionFileOperator);
getOperator(): TransactionFileOperator;
commit(): Promise<void>;
rollback(): Promise<void>;
isTransactionCompleted(): boolean;
getOperationHistory(): readonly TransactionOperation[];
}
// 配置接口
interface ITransactionFileOperatorConfig {
batchSize: number;
maxConcurrency: number;
enableLazyLoading: boolean;
}
enum EOperatorType {
LOCAL = "local",
MEMORY = "memory",
SANDBOX = "sandbox"
}
interface TransactionOperation {
type: "write" | "mkdir" | "unlink" | "rmdir" | "rename";
path: string;
oldPath?: string;
timestamp: number;
}
interface FileState {
exists: boolean;
isDirectory: boolean;
contentLoader?: () => Promise<Buffer>;
}
// 工具函数
function createTransactionExecutor(baseOperator: BaseFileOperator): TransactionExecutor;
function withTransaction<T>(
baseOperator: BaseFileOperator,
operation: (operator: TransactionFileOperator) => Promise<T>
): Promise<T>;
高级用法
使用MultiEditTool进行多文件重构
复制
import { createMultieditTool, createGrepTool } from '@ag-kit/tools/fs';
const multieditTool = createMultieditTool(context);
const grepTool = createGrepTool(context);
// 查找所有需要重构的文件
const searchResult = await grepTool.invoke({
pattern: 'oldApiFunction|OLD_CONSTANT',
file_pattern: '**/*.{ts,js}',
case_sensitive: false
});
// 对每个文件应用一致的重构
for (const match of searchResult.data.matches) {
const refactorResult = await multieditTool.invoke({
file_path: match.file,
edits: [
{
old_string: 'oldApiFunction',
new_string: 'newApiFunction',
expected_replacements: 1
},
{
old_string: 'OLD_CONSTANT',
new_string: 'NEW_CONSTANT',
expected_replacements: 1
},
{
old_string: '// TODO: Update this',
new_string: '// DONE: Updated to new API',
expected_replacements: 1
}
]
});
if (refactorResult.success) {
console.log(`✓ 已重构 ${match.file}: ${refactorResult.data.total_replacements} 处变更`);
} else {
console.log(`✗ 重构 ${match.file} 失败`);
}
}
事务性文件操作
复制
import { withTransaction, TransactionExecutor } from '@ag-kit/tools/fs/transaction';
import { LocalFileOperator } from '@ag-kit/tools/fs';
const baseOperator = new LocalFileOperator();
// 方法1:简单事务包装器
const result = await withTransaction(baseOperator, async (transactionOp) => {
// 原子化创建多个关联文件
await transactionOp.mkdir('project/src', { recursive: true });
await transactionOp.mkdir('project/tests', { recursive: true });
await transactionOp.writeFile('project/package.json', JSON.stringify({
name: 'my-project',
version: '1.0.0'
}, null, 2));
await transactionOp.writeFile('project/src/index.ts', 'export const main = () => console.log("Hello");');
await transactionOp.writeFile('project/tests/index.test.ts', 'import { main } from "../src/index";');
// 若任何操作失败,所有变更将被回滚
return { projectCreated: true };
});
// 方法2:手动事务控制
const executor = new TransactionExecutor(baseOperator);
const transaction = await executor.createTransaction();
try {
const operator = transaction.getOperator();
// 执行操作
await operator.writeFile('config.json', JSON.stringify(config));
await operator.writeFile('backup.json', JSON.stringify(backup));
// 提交前验证
if (await validateConfiguration(config)) {
await transaction.commit();
console.log('配置更新成功');
} else
```typescript
break;
default:
console.log('未知错误:', result.error);
}
}
} catch (error) {
console.error('工具执行失败:', error);
}
安全特性
路径验证
所有工具自动验证路径以防止目录遍历攻击:复制
// ✅ 安全 - 工作区内的相对路径
{ file_path: 'src/config.ts' }
// ❌ 阻止 - 目录遍历
{ file_path: '../../../etc/passwd' }
生产环境建议
- 使用沙盒文件操作器处理不可信代码
- 使用内存文件操作器进行测试
- 仅限可信环境使用本地文件操作器
示例
开发工作流
复制
// 读取配置
const config = await readTool.invoke({ file_path: 'config.json' });
// 更新配置
await editTool.invoke({
file_path: 'config.json',
old_string: '"debug": false',
new_string: '"debug": true'
});
// 查找所有TypeScript文件
const tsFiles = await globTool.invoke({
pattern: '**/*.ts',
exclude_patterns: ['node_modules/**']
});
// 搜索TODOs
const todos = await grepTool.invoke({
pattern: 'TODO|FIXME',
file_pattern: '**/*.{ts,js}'
});
安全配置迁移
复制
import { withTransaction } from '@ag-kit/tools/fs/transaction';
import { createMultieditTool, createReadTool, createWriteTool, createGrepTool } from '@ag-kit/tools/fs';
async function migrateConfiguration(oldConfigPath: string, newConfigPath: string) {
const readTool = createReadTool(context);
const writeTool = createWriteTool(context);
const multieditTool = createMultieditTool(context);
const grepTool = createGrepTool(context);
return await withTransaction(context.fsOperator, async (transactionOp) => {
// 读取旧配置
const oldConfig = await readTool.invoke({ file_path: oldConfigPath });
const configData = JSON.parse(oldConfig.data.content);
// 转换配置结构
const newConfigData = {
version: '2.0',
settings: {
api: {
baseUrl: configData.apiUrl,
timeout: configData.timeout || 5000
},
features: {
debug: configData.debug || false,
logging: configData.enableLogging || true
}
}
};
// 写入新配置
await writeTool.invoke({
file_path: newConfigPath,
content: JSON.stringify(newConfigData, null, 2),
create_directories: true
});
// 更新所有引用旧配置的文件
const configReferences = await grepTool.invoke({
pattern: oldConfigPath.replace(/\./g, '\\.'),
file_pattern: '**/*.{ts,js,json}'
});
for (const ref of configReferences.data.matches) {
await multieditTool.invoke({
file_path: ref.file,
edits: [
{
old_string: oldConfigPath,
new_string: newConfigPath,
expected_replacements: 1
}
]
});
}
// 归档旧配置
await transactionOp.rename(oldConfigPath, `${oldConfigPath}.backup`);
return {
migrated: true,
newConfigPath,
referencesUpdated: configReferences.data.matches.length
};
});
}
// 使用示例
const migrationResult = await migrateConfiguration('old-config.json', 'config/app.json');
if (migrationResult.migrated) {
console.log(`配置已成功迁移至 ${migrationResult.newConfigPath}`);
console.log(`更新了 ${migrationResult.referencesUpdated} 处文件引用`);
}
带错误恢复的批量文件处理
复制
import { TransactionExecutor } from '@ag-kit/tools/fs/transaction';
async function processFilesWithRecovery(filePatterns: string[]) {
const executor = new TransactionExecutor(context.fsOperator);
const results = [];
for (const pattern of filePatterns) {
const transaction = await executor.createTransaction();
try {
const operator = transaction.getOperator();
// 查找匹配模式的文件
const files = await globTool.invoke({ pattern });
// 处理每个文件
for (const file of files.data.matches) {
const content = await readTool.invoke({ file_path: file.path });
// 应用转换
const processedContent = await processFileContent(content.data.content);
// 写回处理后的内容
await operator.writeFile(file.path, processedContent);
}
// 所有文件处理成功后提交
await transaction.commit();
results.push({ pattern, success: true, filesProcessed: files.data.matches.length });
} catch (error) {
// 出错时回滚
await transaction.rollback();
results.push({ pattern, success: false, error: error.message });
}
}
return results;
}
async function processFileContent(content: string): Promise<string> {
// 示例:移除console.log语句并添加适当日志
return content
.replace(/console\.log\([^)]+\);?\n?/g, '')
.replace(/\/\/ TODO:/g, '// DONE:')
.replace(/var /g, 'const ');
}
核心特性摘要
本版新增
MultiEditTool
- 用途:对单个文件执行多次顺序编辑
- 优势:原子批量操作、一致的错误处理、详细结果
- 使用场景:配置更新、代码重构、批量替换
事务支持
- 用途:分组多个文件操作并支持回滚
- 优势:数据一致性、错误恢复、原子操作
- 策略:本地(文件备份)、内存(快照)、沙盒(内容追踪)
增强型工具包模式
- 用途:结合原子工具与多编辑能力
- 优势:适应不同使用场景的灵活性、最优工具选择
- 配置:在FilesystemToolkit中设置
mode: "enhanced"
最佳实践
- 使用MultiEditTool处理同一文件的多次变更
- 使用事务确保操作要么全部成功要么全部回滚
- 使用增强模式当需要同时进行原子和批量操作时
- 验证expected_replacements捕获意外变更
- 优雅处理错误配合适当的回滚机制
迁移指南
从EditTool迁移到MultiEditTool
复制
// 之前:多次EditTool调用
await editTool.invoke({ file_path: 'config.ts', old_string: 'A', new_string: 'B' });
await editTool.invoke({ file_path: 'config.ts', old_string: 'C', new_string: 'D' });
// 之后:单次MultiEditTool调用
await multieditTool.invoke({
file_path: 'config.ts',
edits: [
{ old_string: 'A', new_string: 'B' },
{ old_string: 'C', new_string: 'D' }
]
});
添加事务支持
复制
// 之前:直接操作
await writeTool.invoke({ file_path: 'file1.txt', content: 'data1' });
await writeTool.invoke({ file_path: 'file2.txt', content: 'data2' });
// 之后:事务操作
await withTransaction(baseOperator, async (transactionOp) => {
await transactionOp.writeFile('file1.txt', 'data1');
await transactionOp.writeFile('file2.txt', 'data2');
// 要么全部成功,要么全部回滚
});