import { Box, Text } from "ink" import * as theme from "../../theme.js" import { Icon } from "../Icon.js" import type { ToolRendererProps } from "./types.js" import { truncateText, sanitizeContent, getToolDisplayName, getToolIconName, parseDiff } from "./utils.js" const MAX_DIFF_LINES = 15 export function FileWriteTool({ toolData }: ToolRendererProps) { const iconName = getToolIconName(toolData.tool) const displayName = getToolDisplayName(toolData.tool) const path = toolData.path || "" const diffStats = toolData.diffStats const diff = toolData.diff ? sanitizeContent(toolData.diff) : "" const isProtected = toolData.isProtected const isOutsideWorkspace = toolData.isOutsideWorkspace const isNewFile = toolData.tool === "newFileCreated" || toolData.tool === "write_to_file" // Handle batch diff operations if (toolData.batchDiffs && toolData.batchDiffs.length > 0) { return ( {/* Header */} {" "} {displayName} ({toolData.batchDiffs.length} files) {/* File list with stats */} {toolData.batchDiffs.slice(0, 8).map((file, index) => ( {file.path} {file.diffStats && ( +{file.diffStats.added} / -{file.diffStats.removed} )} ))} {toolData.batchDiffs.length > 8 && ( ... and {toolData.batchDiffs.length - 8} more files )} ) } // Single file write const { text: previewDiff, truncated, hiddenLines } = truncateText(diff, MAX_DIFF_LINES) const diffHunks = diff ? parseDiff(diff) : [] return ( {/* Header row with path on same line */} {displayName} {path && ( <> ยท {path} )} {isNewFile && ( {" "} NEW )} {/* Diff stats badge */} {diffStats && ( <> +{diffStats.added} / -{diffStats.removed} )} {/* Warning badges */} {isProtected && ๐Ÿ”’ protected} {isOutsideWorkspace && ( {" "} โš  outside workspace )} {/* Diff preview */} {diffHunks.length > 0 && ( {diffHunks.slice(0, 2).map((hunk, hunkIndex) => ( {/* Hunk header */} {hunk.header} {/* Diff lines */} {hunk.lines.slice(0, 8).map((line, lineIndex) => ( {line.type === "added" ? "+" : line.type === "removed" ? "-" : " "} {line.content} ))} {hunk.lines.length > 8 && ( ... ({hunk.lines.length - 8} more lines in hunk) )} ))} {diffHunks.length > 2 && ( ... ({diffHunks.length - 2} more hunks) )} )} {/* Fallback to raw diff if no hunks parsed */} {diffHunks.length === 0 && previewDiff && ( {previewDiff} {truncated && ( ... ({hiddenLines} more lines) )} )} ) }