BrainBank

08 - 扩展 Harness 智能体

2026/7/30 21:29:45 · 更新于 2026/7/30 22:47:42

AI 翻译于 2026/7/30 23:28:26 · 使用 Qwen3.6 35B (fast, default)

#agent-architecture#step-by-step#tool-registration#mcp-servers#skills-system#hooks-pattern#extension-design

通过五大内置扩展点(工具、MCP 服务器、技能、钩子和模型)扩展 Harness Agent 系统的实战指南,以及接下来值得构建的结构改进

本文档作为扩展 apps/agent-server 架构的实践实现指南。该系统围绕累加式扩展模式设计,允许通过小型配置文件和注册代码片段集成新功能,而无需修改核心请求或执行循环。以下是现有扩展路径的参考,随后是旨在长期强化系统的架构改进建议。

通过本地工具进行扩展

添加本地工具是最直接的扩展路径。创建 tools/your_tool.py 并导出两个组件:

  • 一个 SCHEMA 字典,用于定义 OpenAI 函数调用模式(参数描述、数据类型和约束条件)。
  • 一个 async def 实现函数,用于执行该工具的业务逻辑。

tools/registry.py 中注册该工具:导入模块,并分别在 SCHEMAS 列表和 _FUNCTIONS 名称到可调用对象的字典中添加一项。由于 agent_loop.pygraph.py 仅通过注册表与工具交互,因此无需进行任何源代码修改。

注入可信上下文: 如果工具需要服务器提供的上下文(例如已认证的用户身份或会话状态),请声明一个与预期名称匹配的参数(遵循现有具备记忆感知功能的工具所使用的 partition_key 模式)。call_tool() 方法会检查函数的真实签名并自动注入这些值。具有相同名称的模型提供参数无法覆盖此设置;服务器提供的上下文始终优先,从而保持针对大语言模型(LLM)欺骗的关键安全边界。

通过 MCP 服务器进行扩展

当某项功能已作为 Model Context Protocol (MCP) 服务器存在时(范围涵盖从网络搜索到特定领域的数据源),将其接入通常比手动编写自定义工具所需的工作量更少。向 apps/agent-server/mcp_servers.json 添加一项(请勿修改 .example.json 配套文件,该文件仅作静态参考)。每项遵循以下结构:

{
  "name": "...",
  "command": "...",
  "args": [...],
  "env": {...}
}

重启服务器,并通过 /health 端点验证连接情况(查看 mcp_tools_registered 计数)。

预飞检查清单: 在将其接入项目之前,务必先在本地进行冒烟测试(根据软件包分发渠道运行 npx <package>uvx <package>)。两台预配置服务器(fetchsecedgar)在已正确安装的情况下,仍因导入时报错无法使用;测试可避免因假设而导致的部署失败。在从头研究新选项之前,请先查阅 MCP_SERVERS_CATALOG.md 中整理的关于网络搜索、PDF 处理、结构化规划及财务数据的调研备选列表。

已知限制:

  • 仅支持 stdio 传输。无法直接连接仅支持 HTTP 或 SSE 的 MCP 服务器;必须先自行构建自定义传输层(如果特定工具需要,这可作为一个独立项目进行开发)。
  • 隔离性是内置功能:失败的服务不会注册任何工具,仅记录警告日志,并允许其他服务正常启动。引入此容错机制的风险确实极低。

通过技能进行扩展

技能代表了架构中阻力最小的扩展方式。只需在 apps/agent-server/skills/ 目录下放置一个 Markdown 文件,文件需包含 YAML frontmatter(description: ...)以及匹配时想要注入系统提示语的指导文本即可。无需编写任何注册代码——文件的存在即代表完成配置。

技能通过关键词重叠与用户消息进行匹配,每个请求精确注入一个技能。如果您的新技能与现有技能共享词汇表,请将指导内容合并到原始文件中,而不是创建互相竞争且都无法赢得注入位置的重叠文件。

注意: 注册新技能文件或修改现有技能文件需要重启服务器。与每次请求时重新读取的 AGENT.md 不同,技能在进程启动时被缓存。

通过钩子进行扩展

钩子在生命周期中的两个精确时刻执行:工具立即执行之前,以及真实(非阻塞)工具调用返回之后。创建 hooks/your_hook.py、定义相应的签名,并通过 register_pre_tool()register_post_tool() 注册它。在 hooks/__init__.py 中添加单行导入以激活它。

钩子签名:

  • 前置钩子: fn(tool_name, arguments) -> dict | None。返回 dict 会阻止实际工具调用,并将该字典作为结果返回(非常适合策略执行,类似于现有的写入路径守卫)。
  • 后置钩子: fn(tool_name, arguments, result) -> None。专用于副作用场景(例如,在成功写入后触发后台重新索引,可以参考知能库自动同步钩子作为模板)。

所有钩子均以防御方式运行:单个钩子抛出异常会被捕获、记录并跳过。错误仅隔离到钩子本身,而不会导致活跃请求或服务崩溃。

使用或添加新模型

模型路由和切换完全通过配置传递管理 Ollama,无需更改源代码。有关详细的配置和选择策略,请参阅 07_Switching_LLM_Models_Guide.md

值得优先实施的架构改进

除了上述增量式扩展点之外,还有几个能够显著增强系统的结构改进。以下按影响力大致排序:

功能增强描述与实现路径
服务端模型路由目前需要调用方显式指定。在 agent_loop.run() / run_streaming() 早期(_prepare_upstream_body() 之前)实现一个轻量级路由器,按能力(例如,当存在图像时自动选择视觉模型)或延迟配置文件进行路由。该逻辑已有清晰的接口点可在此处插入。
统一流式/非流式路径两种执行模式目前都重复实现了“先规划器后工具”的控制流,导致未来对工具预算、钩子或记忆记录的修改需要双重维护。重构 graph.py 的波次执行器以支持增量/原生流输出。实施成本较高,但长期收益显著。
技能匹配器路由优化将第 5.9/10 步的“正则先行、嵌入相似度校验”机制直接应用于 skills/loader.py。嵌入基础设施已存在并在其他地方使用;应用此模式可彻底杜绝重复的假阳性匹配问题。这是理解代码库路由层体系的极佳实操练习。
人工审批写入关卡当前防护机制仅限制了写入发生的 位置,但缺少暂停等待确认的机制。最小化实现方案(记录预期操作 → 要求调用方再次显式调用工具以确认执行)即可在无需外部 UI 或通知系统的情况下弥补工作流漏洞。
共享缓存/限流层目前属于前瞻性设计,但对横向扩展必不可少。内存限流器、MCP 会话池及多个缓存均需迁移至共享后端(Redis 是标准选择;正确加锁的 SQLite 在此规模下也能胜任)。在突破单进程进行水平扩展前,需先完成架构规划。

系统扩展的核心原则

每一个扩展点的存在,都源于原始架构有意将**“经常变更的部分”(工具、技能、钩子、MCP 服务器、模型)与“保持不变的部分”**(请求流水线、图执行器、授权层)进行了分离。

在构建扩展时,验证你方案正确性的最强依据是:它仅需编写一个全新的文件以及寥寥数行注册代码即可实现。若某项扩展要求修改 agent_loop.py 的核心控制流或 graph.py 的执行器本身,请暂停并评估是否可以通过扩展现有的注册表/钩子/技能模式来实现。正是这种有意的分离设计,使得代码库能够在四天内的八个构建阶段中始终保持紧凑、可审计且稳定。

关键要点

  • **设计即支持可扩展:**新功能通过小型隔离文件和注册绑定进行集成,无需改动核心编排循环。
  • **服务端强制安全:**受信任的上下文注入使用真实的 Python 函数签名,从结构上杜绝了大模型伪造参数的可能。
  • **存在硬性限制:**MCP 完全依赖 stdio 传输方式;Skills 于启动时完成缓存,并基于关键词重叠情况,每次仅注入一个匹配项。
  • **钩子优雅降级:**前置与后置钩子均采取防御性运行机制,将异常隔离于主执行流之外。
  • **优先利用架构杠杆:**在服务端进行模型路由,在预算变更前统一流式传输路径,并尽早规划共享缓存架构,以避免扩展性债务。

学习地图

扩展 Harness Agent — 学习路线图

第一阶段 — 基础(理解架构)

  • 理解核心设计原则:将"变化的部分"与"不变的部分"分离
  • 探索 agent_loop.pygraph.py,了解核心循环处理的内容
  • 研究 tools/registry.py——所有扩展遵循的中心模式

第二阶段 — 加法扩展(无需修改核心代码)

  1. 添加本地工具 —— 编写 tools/your_tool.py,在注册表中注册,通过 /health 端点测试
  2. 添加 MCP 服务器 —— 编辑 mcp_servers.json,在终端中进行冒烟测试,确认工具注册
  3. 添加技能(Skill) —— 将带有 YAML 前端的 Markdown 文件放入 skills/ 目录(无需编写代码)
  4. 添加钩子(Hook) —— 编写工具前或工具后的逻辑,通过 hooks/__init__.py 注册

第三阶段 — 模型集成

  • 配置 Ollama 的模型透传(无需修改代码)
  • 详见 07_Switching_LLM_Models_Guide.md

第四阶段 — 结构增强(大型项目)

  • 实现服务端模型路由 (agent_loop.run())
  • 统一 graph.py 中的流式和非流式请求路径
  • 复用正则表达到嵌入的匹配模式用于技能(Skill)匹配
  • 为文件写入添加人工审批关卡
  • 在水平扩展之前,规划共享缓存/速率限制层

动手实践——分步指南

I can see the knowledge bank's structure, but apps/agent-server does not exist within the allowed directory /Volumes/AI_DATA/knowledge-bank. The accessible directories are:

  • /Volumes/AI_DATA/knowledge-bank/DOD-FM-Knowledge-Bank/ (DOD-FM regulations PDFs)
  • /Volumes/AI_DATA/knowledge-bank/K12-Knowledge-Bank/ (K12 curricula PDFs)
  • /Volumes/AI_DATA/knowledge-bank/Wiki/ (markdown reference docs)
  • /Volumes/AI_DATA/knowledge-bank/_inbox/ and /_index/

These are read-only knowledge files — they don't contain agent-server source code, tools, skills configuration, or the project directories you referenced.

To proceed with steps 1–11, I would need access to the actual agent-server project directory. Could you:

  1. Place the agent-server repo inside the allowed path (e.g., create /tmp/agent-server if /tmp is accessible, or confirm a different allowed path), or
  2. Paste the contents of the key files (tools/registry.py, mcp_servers.json.example, an existing tool file, an existing skill file) so I can write new ones for you locally?

Without filesystem access to apps/agent-server/ or its sibling directories, I cannot explore it or create any extension files.

三大推荐资源

  1. 1
    OpenAI function calling documentation

    The canonical reference for OpenAI function-calling schemas — defines what a SCHEMA dict should contain and how the model decides when to call tools.

    https://platform.openai.com/docs/guides/function-calling

  2. 2
    Model Context Protocol (MCP) Specification

    The official MCP specification — explains server transport types (stdio vs HTTP/SSE), tool protocols, and the standard server format used in mcp_servers.json.

    https://github.com/modelcontextprotocol/specification

  3. 3
    LangChain Agent Patterns

    A well-known agent framework demonstrating tool integration patterns, hook-like callbacks, and extensibility architectures similar to those in Harness Agent.

    https://python.langchain.com/docs/modules/agents/

链接由 AI 推荐——使用前建议快速核实。