This repository has been archived on 2026-08-12. You can view files and clone it. You cannot open issues or pull requests or push a commit.
Files
AskaEth caa9bfced5 docs: 工具调用系统介绍文档
- 17个工具完整列表(共享插件 + AI-Core专属)
- 注册机制 + ToolExecutor接口
- 对话中完整调用流程(含LLM API请求/响应示例)
- 工具调用循环(最多5轮)
- 后台思考白名单机制
- 超时异步处理

Co-Authored-By: Claude <noreply@anthropic.com>
2026-06-23 12:53:23 +08:00

5.4 KiB
Raw Permalink Blame History

Cyrene 工具调用系统

日期2026-06-23
适用范围:对话 + 后台自主思考


概述

昔涟可以调用 16 个工具来完成任务——从搜索互联网、控制智能家居,到创建提醒、检索知识库。

工具调用的核心机制是 OpenAI Function Calling 协议:每次 LLM 请求时,将所有可用工具的名称、描述、参数格式一并发送。LLM 自行判断是否需要调用工具,返回工具名和参数,由服务端执行后把结果送回 LLM 生成最终回复。


注册机制

启动时注册

ai-core/cmd/main.go 在服务启动时将全部工具注册到 ToolRegistry

共享插件 (pkg/plugins)
  calculator     数学表达式求值
  datetime       日期时间计算/格式化
  text           文本处理(统计/截断)
  crypto         哈希/加解密
  random         随机数/字符串
  markdown       Markdown 渲染
  json           JSON 解析/查询
  file           文件读写/列表
  http           HTTP 请求
  web_search     SearXNG 网络搜索
  web_fetch      网页内容提取

AI-Core 专属 (internal/tools)
  iot_query      IoT 设备状态查询
  iot_control    IoT 设备操控
  knowledge_search  知识库 RAG 检索
  knowledge_ingest  知识库文档导入
  reminder_create   创建提醒
  reminder_list     列出提醒
  reminder_delete   删除提醒

工具定义

每个工具实现 ToolExecutor 接口:

type ToolExecutor interface {
    Execute(ctx context.Context, args map[string]interface{}) (*ToolResult, error)
    Definition() ToolDefinition
}

type ToolDefinition struct {
    Name        string                 // 工具名,LLM 用它来选择
    Description string                 // 工具用途描述,LLM 据此判断是否需要调用
    Parameters  map[string]interface{} // JSON Schema 参数定义
}

Description 就是 LLM 的"说明书"——它通过阅读描述来判断当前对话是否需要调用这个工具。


对话中的调用流程

用户: "帮我查一下今天天气"

Synthesizer.Synthesize()
  │
  ├─ 1. buildOpenAITools()
  │    从 ToolRegistry 取出全部工具的定义
  │    转换为 OpenAI Function Calling 格式
  │
  ├─ 2. ChatWithTools(messages, tools)
  │    POST LLM API:
  │    {
  │      "model": "deepseek-v4-flash",
  │      "messages": [
  │        {"role":"system","content":"你是昔涟..."},
  │        {"role":"user","content":"帮我查一下今天天气"}
  │      ],
  │      "tools": [
  │        {
  │          "type": "function",
  │          "function": {
  │            "name": "web_search",
  │            "description": "搜索互联网获取实时信息...",
  │            "parameters": {
  │              "type": "object",
  │              "properties": {
  │                "query": {"type": "string", "description": "搜索关键词"}
  │              },
  │              "required": ["query"]
  │            }
  │          }
  │        },
  │        // ... 其余 15 个工具
  │      ],
  │      "tool_choice": "auto"
  │    }
  │
  │    LLM 判断: 用户要查天气 → 需要 web_search
  │    返回:
  │    {
  │      "choices": [{
  │        "delta": {
  │          "tool_calls": [{
  │            "id": "call_abc123",
  │            "function": {
  │              "name": "web_search",
  │              "arguments": "{\"query\":\"今天天气\"}"
  │            }
  │          }]
  │        }
  │      }]
  │    }
  │
  ├─ 3. ToolRegistry.Execute("web_search", {query: "今天天气"})
  │    → 发送 HTTP 请求到 SearXNG
  │    → 返回: {success: true, data: "晴转多云 22°C..."}
  │
  ├─ 4. 工具结果追加到对话历史
  │    messages += {
  │      role: "tool",
  │      tool_call_id: "call_abc123",
  │      content: "{\"success\":true,\"data\":\"晴转多云 22°C...\"}"
  │    }
  │
  └─ 5. 再次 ChatWithTools
       LLM 读取工具结果 → 生成最终回复:
       "今天晴转多云,22°C♪ 很适合出门走走呢~"

工具调用循环

LLM 可以在一轮对话中多次调用工具,最多 5 轮

第 1 轮: LLM → web_search("今天天气")
第 2 轮: LLM → web_fetch("https://weather.com/detail")
第 3 轮: LLM 综合结果 → 生成回复

每轮 LLM 都可以选择继续调工具或直接回复。达到 5 轮上限后强制生成回复。


后台思考中的工具调用

后台思考器(Thinker)使用相同的工具注册中心,但通过 AutonomousToolPolicy 白名单控制:

AllowedTools: []string{
    "iot_query", "iot_control", "memory_search", "web_search",
    "calculator", "datetime", "web_fetch",
    "reminder_create", "reminder_list", "reminder_delete",
    ...
}

思考循环中只有白名单内的工具可被调用,防止自主思考执行高风险操作。


工具超时与异步

每个工具调用有 8 秒超时。超时的工具转入后台异步执行,结果在下一轮对话中返回。LLM 会收到提示:"该工具正在后台运行,你可以继续聊天"。


如何添加新工具

  1. 实现 ToolExecutor 接口(Definition() + Execute()
  2. main.gotoolRegistry.Register(wrapTool(...))
  3. 如需在思考中可用,加入 AutonomousToolPolicy.AllowedTools

工具注册后,LLM 会在下次请求时自动感知到新工具——无需修改 prompt。