Skip to content
签到签到

进阶第 4 章:工具系统

业务问题

AI 编码助手会读文件、写文件、执行命令。客服 Agent 会查询订单、调用知识库。工具系统必须保证参数正确、执行安全、结果可回放。

交互图解:工具执行、权限与批准流程 · 查看图解导读

核心原理

工具包含:

  • name
  • description
  • parameters
  • output schema
  • execute
  • 可选 finalizeContent
  • 可选 presentCall / presentResult

执行链路:

text
model tool call
-> parse args
-> pre-execute
-> guard
-> execute
-> post-execute
-> materialize result
-> notify observers

真实项目中的映射

编码助手工具可以分为:

  • 只读:读文件、搜索代码。
  • 修改:写文件、编辑文件。
  • 执行:运行命令、运行测试。
  • 检索:搜索知识库。
  • 控制:创建任务、调用子 Agent。

不同工具需要不同权限和 UI。

DeepSeek Harness 对应实现

DeepSeek Harness 的 ToolRuntime 负责工具注册和执行。

关键事件:

  • tools/pre-execute
  • tools/execute
  • tools/post-execute
  • tools/result

工具结果必须是 lossless JSON,模型和前端都能消费。

进一步阅读:

  • packages/core/tools/src/index.ts
  • docs/cookbook/adding-a-tool.md

代码示例

ts
interface ToolDefinition {
  name: string
  description: string
  parameters: Record<string, unknown>
  execute(args: unknown): Promise<unknown>
}

type PreToolDecision =
  | { kind: 'allow' }
  | { kind: 'deny'; reason: string }
  | { kind: 'ask'; reason: string }

async function executeTool(
  tool: ToolDefinition,
  args: unknown,
  pre: (tool: ToolDefinition, args: unknown) => Promise<PreToolDecision>,
): Promise<unknown> {
  const decision = await pre(tool, args)

  if (decision.kind === 'deny') {
    throw new Error(decision.reason)
  }

  if (decision.kind === 'ask') {
    throw new Error('approval required')
  }

  return tool.execute(args)
}

真实实现还需要超时、取消、输出校验和结果规范化。

面试追问

问:为什么工具参数不能完全信任模型?

回答要点:

  • 模型可能生成错误类型。
  • 参数需要 schema 校验。
  • 日志和回放需要稳定结构。

问:pre-execute、execute、post-execute 分别适合什么?

回答要点:

  • pre-execute 适合 allow/deny/ask。
  • execute 适合超时、重试、指标包装。
  • post-execute 适合替换或阻止结果。

问:工具结果为什么要可序列化?

回答要点:

  • 需要回传给模型。
  • 需要持久化。
  • 需要前端渲染。
  • 需要回放和审计。

实践任务

为一个“查询订单”工具定义 schema、execute 和 pre-execute 策略,并画出失败结果如何回传给模型。

验收标准

  • 能写一个简单 ToolDefinition。
  • 能解释工具执行链路的阶段。
  • 能说明工具失败如何回传。