execute method

  1. @override
Future<ToolResult> execute(
  1. Map<String, dynamic> input
)
override

Execute the tool with the given input.

Implementation

@override
Future<ToolResult> execute(Map<String, dynamic> input) async {
  final validation = validateInput(input);
  if (!validation.isValid) return ToolResult.error(validation.error!);

  final parsed = MultiEditInput.fromJson(input);
  final file = File(parsed.filePath);

  if (!await file.exists()) {
    return ToolResult.error('File not found: ${parsed.filePath}');
  }

  try {
    var content = await file.readAsString();
    final original = content;

    // Verify all edits can be applied before making changes.
    for (var i = 0; i < parsed.edits.length; i++) {
      if (!content.contains(parsed.edits[i].oldText)) {
        return ToolResult.error(
          'Edit $i: old_text not found in file. '
          'No edits were applied (atomic).',
        );
      }
    }

    // Apply edits sequentially.
    var applied = 0;
    for (final edit in parsed.edits) {
      content = content.replaceFirst(edit.oldText, edit.newText);
      applied++;
    }

    if (content == original) {
      return ToolResult.success('No changes made (all edits were no-ops)');
    }

    await file.writeAsString(content);
    final out = MultiEditOutput(
      success: true,
      editsApplied: applied,
      newContent: content,
    );
    return ToolResult.success(out.toString());
  } catch (e) {
    return ToolResult.error('Error during multi-edit: $e');
  }
}