From 3a0c73f598b388c319e43a7e45e6e729b39fece6 Mon Sep 17 00:00:00 2001 From: Bryan Dady Date: Fri, 22 May 2026 12:29:16 -0600 Subject: [PATCH 1/2] fix(acp): include shell command in permission request metadata and title --- packages/opencode/src/acp/agent.ts | 5 ++++- packages/opencode/src/tool/shell.ts | 8 ++++---- 2 files changed, 8 insertions(+), 5 deletions(-) diff --git a/packages/opencode/src/acp/agent.ts b/packages/opencode/src/acp/agent.ts index 8b74b9c9bad3..c02cd105a439 100644 --- a/packages/opencode/src/acp/agent.ts +++ b/packages/opencode/src/acp/agent.ts @@ -205,7 +205,10 @@ export class Agent implements ACPAgent { toolCall: { toolCallId: permission.tool?.callID ?? permission.id, status: "pending", - title: permission.permission, + title: + typeof permission.metadata?.command === "string" + ? permission.metadata.command + : permission.permission, rawInput: permission.metadata, kind: toToolKind(permission.permission), locations: toLocations(permission.permission, permission.metadata), diff --git a/packages/opencode/src/tool/shell.ts b/packages/opencode/src/tool/shell.ts index 506d98466e76..ffcaee09185e 100644 --- a/packages/opencode/src/tool/shell.ts +++ b/packages/opencode/src/tool/shell.ts @@ -263,7 +263,7 @@ const parse = Effect.fn("ShellTool.parse")(function* (command: string, ps: boole return tree }) -const ask = Effect.fn("ShellTool.ask")(function* (ctx: Tool.Context, scan: Scan) { +const ask = Effect.fn("ShellTool.ask")(function* (ctx: Tool.Context, scan: Scan, command: string) { if (scan.dirs.size > 0) { const globs = Array.from(scan.dirs).map((dir) => { if (process.platform === "win32") return AppFileSystem.normalizePathPattern(path.join(dir, "*")) @@ -273,7 +273,7 @@ const ask = Effect.fn("ShellTool.ask")(function* (ctx: Tool.Context, scan: Scan) permission: "external_directory", patterns: globs, always: globs, - metadata: {}, + metadata: { command }, }) } @@ -282,7 +282,7 @@ const ask = Effect.fn("ShellTool.ask")(function* (ctx: Tool.Context, scan: Scan) permission: ShellID.ToolID, patterns: Array.from(scan.patterns), always: Array.from(scan.always), - metadata: {}, + metadata: { command }, }) }) @@ -625,7 +625,7 @@ export const ShellTool = Tool.define( ) const scan = yield* collect(tree.rootNode, cwd, ps, shell, instanceCtx) if (!containsPath(cwd, instanceCtx)) scan.dirs.add(cwd) - yield* ask(ctx, scan) + yield* ask(ctx, scan, params.command) }), ) From 7c1a3dffe51b73ef3b956e021ed8d643753ca40c Mon Sep 17 00:00:00 2001 From: Bryan Dady Date: Fri, 22 May 2026 13:38:34 -0600 Subject: [PATCH 2/2] fix(acp): prefer description over command in shell permission prompt title --- packages/opencode/src/acp/agent.ts | 8 +++++--- packages/opencode/src/tool/shell.ts | 13 +++++++++---- 2 files changed, 14 insertions(+), 7 deletions(-) diff --git a/packages/opencode/src/acp/agent.ts b/packages/opencode/src/acp/agent.ts index c02cd105a439..0c7076b9926e 100644 --- a/packages/opencode/src/acp/agent.ts +++ b/packages/opencode/src/acp/agent.ts @@ -206,9 +206,11 @@ export class Agent implements ACPAgent { toolCallId: permission.tool?.callID ?? permission.id, status: "pending", title: - typeof permission.metadata?.command === "string" - ? permission.metadata.command - : permission.permission, + typeof permission.metadata?.description === "string" + ? permission.metadata.description + : typeof permission.metadata?.command === "string" + ? permission.metadata.command + : permission.permission, rawInput: permission.metadata, kind: toToolKind(permission.permission), locations: toLocations(permission.permission, permission.metadata), diff --git a/packages/opencode/src/tool/shell.ts b/packages/opencode/src/tool/shell.ts index ffcaee09185e..2a98e2e963e8 100644 --- a/packages/opencode/src/tool/shell.ts +++ b/packages/opencode/src/tool/shell.ts @@ -263,7 +263,12 @@ const parse = Effect.fn("ShellTool.parse")(function* (command: string, ps: boole return tree }) -const ask = Effect.fn("ShellTool.ask")(function* (ctx: Tool.Context, scan: Scan, command: string) { +const ask = Effect.fn("ShellTool.ask")(function* ( + ctx: Tool.Context, + scan: Scan, + command: string, + description: string | undefined, +) { if (scan.dirs.size > 0) { const globs = Array.from(scan.dirs).map((dir) => { if (process.platform === "win32") return AppFileSystem.normalizePathPattern(path.join(dir, "*")) @@ -273,7 +278,7 @@ const ask = Effect.fn("ShellTool.ask")(function* (ctx: Tool.Context, scan: Scan, permission: "external_directory", patterns: globs, always: globs, - metadata: { command }, + metadata: { command, description }, }) } @@ -282,7 +287,7 @@ const ask = Effect.fn("ShellTool.ask")(function* (ctx: Tool.Context, scan: Scan, permission: ShellID.ToolID, patterns: Array.from(scan.patterns), always: Array.from(scan.always), - metadata: { command }, + metadata: { command, description }, }) }) @@ -625,7 +630,7 @@ export const ShellTool = Tool.define( ) const scan = yield* collect(tree.rootNode, cwd, ps, shell, instanceCtx) if (!containsPath(cwd, instanceCtx)) scan.dirs.add(cwd) - yield* ask(ctx, scan, params.command) + yield* ask(ctx, scan, params.command, params.description) }), )