diff --git a/core/kernel/src/main/kotlin/com/correx/core/kernel/orchestration/SessionOrchestrator.kt b/core/kernel/src/main/kotlin/com/correx/core/kernel/orchestration/SessionOrchestrator.kt index b5d516a2..e78ead73 100644 --- a/core/kernel/src/main/kotlin/com/correx/core/kernel/orchestration/SessionOrchestrator.kt +++ b/core/kernel/src/main/kotlin/com/correx/core/kernel/orchestration/SessionOrchestrator.kt @@ -1275,7 +1275,9 @@ abstract class SessionOrchestrator( mode = approvalMode, ) val requestId = ApprovalRequestId(UUID.randomUUID().toString()) - val toolPreview = computeToolPreview(toolCall.function.name, parameters) + val toolPreview = computeToolPreview( + toolCall.function.name, parameters, effectives.policy?.workspaceRoot, + ) val domainRequest = DomainApprovalRequest( id = requestId, tier = tier, @@ -3382,10 +3384,14 @@ abstract class SessionOrchestrator( * This function performs blocking I/O (file reads) and must be called from a suspend context * that will dispatch it on [Dispatchers.IO]. */ -private suspend fun computeToolPreview(toolName: String, parameters: Map): String? { +private suspend fun computeToolPreview( + toolName: String, + parameters: Map, + workspaceRoot: java.nio.file.Path?, +): String? { if (toolName == "shell") return shellCommandPreview(parameters) if (toolName == "task_decompose") return renderDecomposePreview(parameters) - if (toolName == "file_edit") return computeFileEditPreview(parameters) + if (toolName == "file_edit") return computeFileEditPreview(parameters, workspaceRoot) if (toolName != "file_write") return null val path = parameters["path"] as? String ?: return null // file_write no longer carries an `operation` param (delete was split into file_delete), so the @@ -3393,18 +3399,23 @@ private suspend fun computeToolPreview(toolName: String, parameters: Map): String? { +private suspend fun computeFileEditPreview( + parameters: Map, + workspaceRoot: java.nio.file.Path?, +): String? { val path = parameters["path"] as? String ?: return null val operation = parameters["operation"] as? String ?: return null - val existingContent = readFileIfExists(path) ?: return null + val existingContent = readFileIfExists(path, workspaceRoot) ?: return null val proposedContent = when (operation) { "append" -> existingContent + (parameters["content"] as? String ?: return null)