OpenCode 工具系统实战教程:从内置到扩展
📚 分类: OpenCode 教程 ⏱️ 预计耗时: 30 分钟 🎯 难度: 入门 🔧 环境要求: 已安装并成功运行 OpenCode
你将学到什么
完成本教程后,你将能够:
- [ ] 区分 OpenCode 中不同工具(内置、MCP、LSP、Formatter)的职责与使用场景
- [ ] 独立配置 OpenCode 的权限系统,安全地管理工具的访问级别
- [ ] 根据项目需求,判断何时需要接入 MCP 服务器或启用 LSP
- [ ] 配置 Formatter,避免其掩盖代码逻辑变更
- [ ] 理解自定义工具(Custom Tools)的价值和适用场景
最终效果
你将能够清晰地规划出一个项目的“工具策略”,知道在什么阶段该用什么工具,并能在 opencode.json 配置文件中安全、合理地启用和管理这些工具,避免“工具越多越好”的陷阱。
前置准备
在开始前,请确认你的环境满足以下条件:
| 检查项 | 要求版本 | 验证命令 |
|---|---|---|
| OpenCode | 最新稳定版 | opencode --version |
| Node.js (可选,用于自定义工具) | ≥ 18.0 | node -v |
1. 准备一个测试项目
为了实践本教程,我们创建一个简单的测试项目。
# 创建项目目录
$ mkdir opencode-tools-demo && cd opencode-tools-demo
# 初始化一个 Node.js 项目(用于演示 LSP 和格式化)
$ npm init -y✅ 验证:你的终端当前路径应该在 opencode-tools-demo 目录下,并且该目录包含一个 package.json 文件。
第 1 步:理解 OpenCode 的工具分层
🎯 目标:理解 OpenCode 的工具不是平铺直叙的列表,而是按能力和风险分层的体系。这能帮你建立正确的决策框架。
📝 操作:阅读下面的工具分层模型,并思考每个层级与项目核心的距离。
OpenCode 的工具可以按距离项目核心的远近分为以下几层:
- 内置工具 (Built-in Tools):最核心层,直接与文件系统和本地环境交互。例如:
read(读文件)、grep(搜索)、edit(编辑)、bash(运行命令)。 - LSP (Language Server Protocol):为 Agent 提供代码理解能力,如跳转定义、查找引用、诊断错误。它不直接修改文件,而是提供上下文。
- Formatter (格式化器):在文件写入后自动进行机械格式化,如调整缩进、分号等。
- 自定义工具 (Custom Tools):用于封装项目中重复的、特定操作,如运行内部诊断脚本。
- MCP Servers (Model Context Protocol):连接外部系统(如 GitHub、数据库、内部 API),为 Agent 提供项目外部的上下文。
- Plugins (插件):用于扩展 OpenCode 自身的运行时生命周期,属于高级用法。
🤔 为什么要这样分层? 分层是为了让你能按需、按风险接入工具。核心原则是:能用内置工具解决的问题,就不要引入外部依赖。 每向外扩展一层,都会增加 Agent 的上下文消耗、权限风险和配置复杂度。
✅ 验证:你能口头说出从最内层到最外层的工具层级顺序吗?(内置 → LSP/Formatter → 自定义工具 → MCP → 插件)
第 2 步:掌握内置工具并配置权限
🎯 目标:熟悉最常用的内置工具,并学会使用 permission 系统来精细控制它们的访问权限,这是安全使用 OpenCode 的基石。
📝 操作:
首先,在你的项目根目录创建或修改 opencode.json 配置文件。
{
"$schema": "https://opencode.ai/config.json",
"permission": {
// 新增:设置内置工具的默认权限
"read": "allow", // 读文件:总是允许,风险低
"grep": "allow", // 搜索代码:总是允许
"glob": "allow", // 查找路径:总是允许
"edit": "ask", // 修改文件:每次询问,安全第一
"bash": "ask", // 运行命令:每次询问
"webfetch": "ask", // 获取网页:每次询问
"write": "ask" // 写入新文件:每次询问
}
}💡 提示:$schema 字段是可选的,但它能让你在支持 JSON Schema 的编辑器中获得代码补全和校验。
✅ 验证:保存文件后,在终端运行 opencode 并尝试执行一个简单的 read 命令(例如,读取 package.json)。你应该能看到文件内容,而不会被询问。然后尝试执行一个 edit 命令(例如,修改 package.json 中的 name 字段),OpenCode 应该会询问你是否允许。
⚠️ 常见错误:不要长期依赖默认的“开放”状态。在生产或共享项目中,务必收紧权限。提示词里的“谨慎操作”不可靠,permission 配置才是真正的执行边界。
第 3 步:判断何时需要 MCP 服务器
🎯 目标:理解 MCP 的价值是在于连接外部系统,并学会区分“本地能解决的问题”和“需要外部上下文的问题”。
📝 操作:
场景分析:
- 不需要 MCP 的场景:你想让 Agent 搜索本地文件中的某个关键词、读取一个本地配置文件、运行一个本地测试脚本。这些工作,内置的
grep、read、bash工具就能完美胜任。 - 需要 MCP 的场景:你想让 Agent 查询 GitHub 仓库的 Issue 列表、读取某个内部 API 的返回数据、或者搜索公司内部的文档库。这些信息不在你的本地文件系统里,需要通过 MCP 服务器去外部系统获取。
最小配置示例(以 context7 这个远程 MCP 服务为例):
{
"$schema": "https://opencode.ai/config.json",
"mcp": {
// 新增:配置一个远程 MCP 服务器
"context7": {
"type": "remote",
"url": "https://mcp.context7.com/mcp",
"enabled": true
}
}
}🤔 为什么要这样做? MCP 服务器会增加 Agent 的上下文窗口消耗,因为它的返回数据会被当作对话的一部分。因此,只在你真正需要外部信息时才启用它,并且只启用最核心的 1-3 个。
✅ 验证:配置完成后,运行 opencode mcp list 命令。你应该能看到 context7 出现在 MCP 服务器列表中。
⚠️ 常见错误:不要用 MCP 来解决本地 grep 能解决的问题。例如,不要为了搜索本地代码而连接一个搜索引擎的 MCP。
第 4 步:启用 LSP 并获得代码理解能力
🎯 目标:启用 LSP,让 Agent 能够理解代码的符号、类型和诊断信息,从而进行更精准的修改。
📝 操作:
安装项目依赖:对于我们的 Node.js 项目,先安装 TypeScript 以获得更好的 LSP 支持。
bash$ npm install --save-dev typescript @types/node配置 LSP:在
opencode.json中,可以定制 LSP 的行为。例如,让 TypeScript LSP 优先使用相对路径导入模块。json{ "$schema": "https://opencode.ai/config.json", "lsp": { // 新增:定制 TypeScript LSP 的初始化选项 "typescript": { "initialization": { "preferences": { "importModuleSpecifierPreference": "relative" } } } } }💡 提示:OpenCode 会自动检测项目文件并启动相应的 LSP 服务器。如果你不想使用某个 LSP,可以将其
disabled设置为true。
🤔 为什么要这样做? LSP 为 Agent 提供了类似 IDE 的代码理解能力,例如“跳转到定义”、“查找所有引用”。这对于大型代码库或跨文件重构任务至关重要,比单纯的全文搜索更可靠。
✅ 验证:在项目中创建一个简单的 TypeScript 文件 src/index.ts,写入 const a: number = 1;。然后,在 OpenCode 中要求 Agent “找到变量 a 的类型定义”。如果 LSP 工作正常,Agent 应该能给出正确的推断。
⚠️ 常见错误:LSP 不是万能的。如果项目依赖没装好、语言服务器配置复杂(如 monorepo),LSP 提供的信息可能不完整。关键改动仍要依赖测试和类型检查来验证。
第 5 步:配置 Formatter 并避免逻辑混淆
🎯 目标:启用并配置 Formatter,让它只做机械格式化,不掩盖代码的逻辑变更。
📝 操作:
启用 Formatter:在
opencode.json中启用所有内置的格式化器。json{ "$schema": "https://opencode.ai/config.json", "formatter": true // 新增:启用所有内置 Formatter }💡 提示:你也可以禁用或覆盖特定的格式化器。例如,禁用 Prettier:
json"formatter": { "prettier": { "disabled": true } }遵循正确的改动流程:
- 让 Agent 完成最小的代码改动。
- 再运行 formatter。
- 检查
git diff,确保改动只包含你预期的范围。
⚠️ 警告:不要一开始就进行全仓库格式化。大范围的格式化会淹没真实的逻辑变更,让代码审查变得困难,也增加了回滚的风险。
✅ 验证:在项目中修改一个文件(例如,添加一些不规范的缩进),然后让 Agent 修改该文件。保存后,你应该能看到文件被自动格式化了。
第 6 步:理解 Custom Tools 的使用场景
🎯 目标:了解何时需要创建自定义工具,并知道如何避免常见的陷阱。
📝 操作:
何时需要? 当一个 shell 命令或一系列操作在项目中反复使用,并且其输出需要被 Agent 稳定地解释时,就可以封装成一个 Custom Tool。
适合封装的例子:
- 查询内部服务状态
- 运行项目专用的诊断脚本
- 读取并解析结构化配置文件
- 生成固定格式的报告
不适合封装的例子:
- ❌ 一次性命令
- ❌ 任何可能删除数据、发布生产、重置数据库的危险操作。即使封装,也必须加上明确的确认步骤和权限校验。
🤔 为什么要这样做? Custom Tool 将复杂的、项目特定的逻辑封装成一个 Agent 易于理解和调用的“原子能力”,可以提高 Agent 的执行效率和准确性。
✅ 验证:理解 Custom Tool 的价值在于“封装重复且边界清晰的操作”,而不是“把一切命令都做成工具”。
总结
恭喜你完成了本教程!🎉
回顾一下我们今天学到的核心内容:
- 工具分层:OpenCode 的工具按风险和能力分层,从内置工具到 MCP,决策原则是“能用内置就不用外部”。
- 权限先行:使用
permission配置来定义工具的访问边界,比在提示词中反复强调“谨慎”更可靠。 - MCP 是外部桥梁:MCP 用于连接外部系统和上下文,不要用它来解决本地文件搜索问题。
- LSP 是代码理解:LSP 提供 IDE 级别的代码分析能力,但不能替代测试和类型检查。
- Formatter 是格式化工具:Formatter 只做机械格式化,先改代码再格式化,最后检查 diff,避免逻辑混淆。
- Custom Tools 是项目封装:用于封装重复的、边界清晰的项目特定操作。
下一步
如果你想继续深入,建议学习:
- 📖 连接 MCP 服务器:学习如何配置和使用真实的 MCP 服务器(如 GitHub、数据库)来扩展 Agent 的能力。
- 📖 安全、分享与团队使用:学习如何在团队中安全地分享 OpenCode 配置,以及更高级的权限和密钥管理。
💡 练习任务:在你的一个真实项目中,检查
opencode.json的permission配置,看看哪些工具可以收紧权限。尝试识别一个可以封装成 Custom Tool 的重复性操作。
## 相关文档
- [Opencode 智能体 (Agent) 与 AGENTS.md 实战教程](/docs/gao-ji-pei-zhi/opencode-zhi-neng-ti-agent-yu-agents-md-shi-zhan-jiao-cheng.html)
- [OpenCode 规则编写实战教程:让 AI 助手稳定遵循你的项目约定](/docs/gao-ji-pei-zhi/opencode-gui-ze-bian-xie-shi-zhan-jiao-cheng-rang-ai-zhu-shou-wen-ding-zun-xun-ni-de-xiang-mu-yue-di.html)