From a8c18dba8205d7707a46ec0859db672370be8963 Mon Sep 17 00:00:00 2001 From: adamelmore <2363879+adamdottv@users.noreply.github.com> Date: Mon, 26 Jan 2026 19:57:34 -0600 Subject: [PATCH] fix(core): expose Instance.directory to custom tools --- packages/opencode/src/tool/read.ts | 2 +- packages/opencode/src/tool/registry.ts | 5 +++-- packages/plugin/src/tool.ts | 5 +++++ packages/web/src/content/docs/custom-tools.mdx | 10 ++++++---- 4 files changed, 15 insertions(+), 7 deletions(-) diff --git a/packages/opencode/src/tool/read.ts b/packages/opencode/src/tool/read.ts index 93c1b751f..746e0b173 100644 --- a/packages/opencode/src/tool/read.ts +++ b/packages/opencode/src/tool/read.ts @@ -24,7 +24,7 @@ export const ReadTool = Tool.define("read", { async execute(params, ctx) { let filepath = params.filePath if (!path.isAbsolute(filepath)) { - filepath = path.join(Instance.directory, filepath) + filepath = path.resolve(Instance.directory, filepath) } const title = path.relative(Instance.worktree, filepath) diff --git a/packages/opencode/src/tool/registry.ts b/packages/opencode/src/tool/registry.ts index faa5f72bc..2c862dfd8 100644 --- a/packages/opencode/src/tool/registry.ts +++ b/packages/opencode/src/tool/registry.ts @@ -16,7 +16,7 @@ import { Tool } from "./tool" import { Instance } from "../project/instance" import { Config } from "../config/config" import path from "path" -import { type ToolDefinition } from "@opencode-ai/plugin" +import { type ToolContext as PluginToolContext, type ToolDefinition } from "@opencode-ai/plugin" import z from "zod" import { Plugin } from "../plugin" import { WebSearchTool } from "./websearch" @@ -67,7 +67,8 @@ export namespace ToolRegistry { parameters: z.object(def.args), description: def.description, execute: async (args, ctx) => { - const result = await def.execute(args as any, ctx) + const pluginCtx = { ...ctx, directory: Instance.directory } as unknown as PluginToolContext + const result = await def.execute(args as any, pluginCtx) const out = await Truncate.output(result, {}, initCtx?.agent) return { title: "", diff --git a/packages/plugin/src/tool.ts b/packages/plugin/src/tool.ts index f759c07d2..6b4f7f1d1 100644 --- a/packages/plugin/src/tool.ts +++ b/packages/plugin/src/tool.ts @@ -4,6 +4,11 @@ export type ToolContext = { sessionID: string messageID: string agent: string + /** + * Current project directory for this session. + * Prefer this over process.cwd() when resolving relative paths. + */ + directory: string abort: AbortSignal metadata(input: { title?: string; metadata?: { [key: string]: any } }): void ask(input: AskInput): Promise diff --git a/packages/web/src/content/docs/custom-tools.mdx b/packages/web/src/content/docs/custom-tools.mdx index e089a035b..ef93a64e2 100644 --- a/packages/web/src/content/docs/custom-tools.mdx +++ b/packages/web/src/content/docs/custom-tools.mdx @@ -120,8 +120,8 @@ export default tool({ args: {}, async execute(args, context) { // Access context information - const { agent, sessionID, messageID } = context - return `Agent: ${agent}, Session: ${sessionID}, Message: ${messageID}` + const { agent, sessionID, messageID, directory } = context + return `Agent: ${agent}, Session: ${sessionID}, Message: ${messageID}, Directory: ${directory}` }, }) ``` @@ -148,6 +148,7 @@ Then create the tool definition that invokes it: ```ts title=".opencode/tools/python-add.ts" {10} import { tool } from "@opencode-ai/plugin" +import path from "path" export default tool({ description: "Add two numbers using Python", @@ -155,8 +156,9 @@ export default tool({ a: tool.schema.number().describe("First number"), b: tool.schema.number().describe("Second number"), }, - async execute(args) { - const result = await Bun.$`python3 .opencode/tools/add.py ${args.a} ${args.b}`.text() + async execute(args, context) { + const script = path.join(context.directory, ".opencode/tools/add.py") + const result = await Bun.$`python3 ${script} ${args.a} ${args.b}`.text() return result.trim() }, })