Build tool
Skill pantheon-org/tekhne/skills/agentic-harness/opencode-toolkit/build-tool
Agents Skills
npx -y skills add pantheon-org/tekhne --skill build-toolAssembled from the repository path, not quoted from the project. Check it against their README if it does not work.
One thing to look at
- 9 stars9 stars. Stars are a popularity signal and not a quality one, but at this level it is likely that nobody has read this closely except its author, and you would be relying on your own review.
What its author says it does
Copied from the file, not written here
Build custom tools and plugins using the OpenCode SDK packages. Use when creating custom tools, implementing tool schemas, building plugins, managing OpenCode sessions, using opencode-ai/sdk or opencode-ai/plugin, creating a tool.ts file, writing an execute handler, using tool.schema, ToolContext, createOpencode, plugin hooks, custom auth, automating OpenCode from a script, building a CI tool, or integrating external APIs. Keywords: Zod schema, execute handler, event streaming, session management, abort signal, tool discovery, multiple tools per file, tool factory.
SKILL.md
3.8 KB, as published. Nobody here has run it
OpenCode SDK Development
Quick Start: Custom Tool in 3 Steps
- Create
.opencode/tool/my-tool.ts:
import { tool } from "@opencode-ai/plugin"
export default tool({
description: "Brief description of what the tool does",
args: {
query: tool.schema.string().describe("Search query")
},
async execute({ query }, { abort }) {
return `Result for: ${query}`
}
})
- Restart OpenCode — tools are auto-discovered.
- Filename = tool name:
my-tool.ts→my-tool.
Mindset
@opencode-ai/plugin— Tools + Hooks: Add LLM-callable tools, intercept execution, react to events@opencode-ai/sdk— Client API: Control OpenCode from external scripts, session management
When to use: Adding new capabilities the agent doesn't have, automating OpenCode from CI/scripts, or integrating external APIs as first-class tools.
When NOT to use: Built-in tool exists (client.tool.list()). Need shell (use $ from Bun). Logic belongs in system prompt (AGENTS.md). Need MCP.
Full decision guide in advanced-patterns.md.
Tool File Locations
.opencode/tool/*.ts # project-specific
~/.config/opencode/tool/*.ts # global
Multiple named exports per file → multiple tools: filename_exportname
Anti-Patterns
NEVER return non-string from execute. WHY: The tool runtime expects a string response; returning an object throws at runtime.
// BAD - throws at runtime
async execute({ query }) { return { results: [] } }
// GOOD - serialize first
async execute({ query }) { return JSON.stringify({ results: [] }) }
NEVER import { tool } from "@opencode-ai/sdk". WHY: The SDK package has no tool() export. The tool factory is only in @opencode-ai/plugin.
// BAD - import error at runtime
import { tool } from "@opencode-ai/sdk"
// GOOD
import { tool } from "@opencode-ai/plugin"
NEVER ignore the abort signal in long-running operations. WHY: Ignoring abort leaves processes dangling after the user cancels, consuming resources.
// BAD - dangling fetch after cancel
async execute({ url }) { return await fetch(url).then(r => r.text()) }
// GOOD - propagate abort
async execute({ url }, { abort }) { return await fetch(url, { signal: abort }).then(r => r.text()) }
Reference Files
- advanced-patterns.md — patterns, anti-patterns, SDK examples; sdk-api.md — SDK client API; plugin-api.md — plugin hooks
- basic-tool.ts — simple tool; full-plugin.ts — complete plugin
Run bun run opencode run "list tools" to verify your tool is discovered and named correctly.
---
description: custom tools opencode SDK plugin execute handler abort signal Zod schema session management event streaming
---