知识引擎/Hermes 知识引擎/Agent 循环内部机制

sidebar position: 3 title: "Agent 循环内部机制" description: "AIAgent 执行、API 模式、工具、回调和回退行为的详细解析" 核心编排引擎是 run agent.py 中的 AIAgent 类——大约 10,700 行代码,负责从 Prompt(提示词)组装到工具

> 📖 本文档翻译自 Agent Loop Internals > 最后更新:2026-04-16


sidebar_position: 3 title: "Agent 循环内部机制" description: "AIAgent 执行、API 模式、工具、回调和回退行为的详细解析"

Agent 循环内部机制

核心编排引擎是 run_agent.py 中的 AIAgent 类——大约 10,700 行代码,负责从 Prompt(提示词)组装到工具分派再到 Provider(提供者)故障转移的所有事务。

核心职责

AIAgent 负责:

  • 通过 prompt_builder.py 组装有效的系统提示词和工具 Schema(模式)
  • 选择正确的 Provider/API 模式(chat_completions、codex_responses、anthropic_messages)
  • 进行支持取消操作的可中断模型调用
  • 执行工具调用(通过线程池顺序或并发执行)
  • 以 OpenAI 消息格式维护对话历史
  • 处理压缩、重试和回退模型切换
  • 跟踪父 Agent 和子 Agent 的迭代预算
  • 在上下文丢失之前刷新持久化内存

两个入口点

# 简单接口 — 返回最终响应字符串
response = agent.chat("Fix the bug in main.py")

# 完整接口 — 返回包含消息、元数据、使用统计的字典
result = agent.run_conversation(
    user_message="Fix the bug in main.py",
    system_message=None,           # 如果省略则自动构建
    conversation_history=None,      # 如果省略则从会话自动加载
    task_id="task_abc123"
)

chat()run_conversation() 的薄封装,从结果字典中提取 final_response 字段。

API 模式

Hermes 支持三种 API 执行模式,根据 Provider 选择、显式参数和 Base URL 启发式规则来确定:

API 模式用途客户端类型
chat_completionsOpenAI 兼容端点(OpenRouter、自定义、大多数 Provider)openai.OpenAI
codex_responsesOpenAI Codex / Responses APIopenai.OpenAI 使用 Responses 格式
anthropic_messages原生 Anthropic Messages APIanthropic.Anthropic 通过适配器

模式决定了消息的格式化方式、工具调用的结构、响应的解析方式以及缓存/流式传输的工作方式。三种模式在 API 调用前后都统一为相同的内部消息格式(OpenAI 风格的 role/content/tool_calls 字典)。

模式解析优先级:

  1. 显式 api_mode 构造参数(最高优先级)
  2. Provider 特定检测(例如,anthropic provider → anthropic_messages
  3. Base URL 启发式规则(例如,api.anthropic.comanthropic_messages
  4. 默认值:chat_completions

轮次生命周期

Agent 循环的每次迭代遵循以下序列:

run_conversation()
  1. 如果未提供则生成 task_id
  2. 将用户消息追加到对话历史
  3. 构建或复用缓存的系统提示词 (prompt_builder.py)
  4. 检查是否需要预检压缩(>50% 上下文)
  5. 从对话历史构建 API 消息
     - chat_completions: 直接使用 OpenAI 格式
     - codex_responses: 转换为 Responses API 输入项
     - anthropic_messages: 通过 anthropic_adapter.py 转换
  6. 注入临时提示词层(预算警告、上下文压力)
  7. 如果使用 Anthropic 则应用提示词缓存标记
  8. 进行可中断的 API 调用 (_api_call_with_interrupt)
  9. 解析响应:
     - 如果是 tool_calls: 执行它们,追加结果,循环回到步骤 5
     - 如果是文本响应: 持久化会话,必要时刷新内存,返回

消息格式

所有消息在内部使用 OpenAI 兼容格式:

{"role": "system", "content": "..."}
{"role": "user", "content": "..."}
{"role": "assistant", "content": "...", "tool_calls": [...]}
{"role": "tool", "tool_call_id": "...", "content": "..."}

来自支持扩展思考(Extended Thinking)的模型的推理内容存储在 assistant_msg["reasoning"] 中,可选通过 reasoning_callback 显示。

消息交替规则

Agent 循环强制执行严格的消息角色交替:

  • 系统消息之后:User → Assistant → User → Assistant → ...
  • 工具调用期间:Assistant (带 tool_calls) → Tool → Tool → ... → Assistant
  • 绝不连续两条 assistant 消息
  • 绝不连续两条 user 消息
  • 只有 tool 角色可以有连续条目(并行工具结果)

Provider 会验证这些序列,并拒绝格式错误的历史记录。

可中断的 API 调用

API 请求被封装在 _api_call_with_interrupt() 中,该函数在后台线程中运行实际的 HTTP 调用,同时监控中断事件:

┌──────────────────────┐     ┌──────────────┐
│  主线程              │     │  API 线程     │
│  等待:              │────▶│  HTTP POST   │
│  - 响应就绪          │     │  发送到       │
│  - 中断事件          │     │  Provider    │
│  - 超时              │     └──────────────┘
└──────────────────────┘

当被中断时(用户发送新消息、/stop 命令或信号):

  • API 线程被放弃(响应被丢弃)
  • Agent 可以处理新输入或干净地关闭
  • 不会将部分响应注入对话历史

工具执行

顺序执行 vs 并发执行

当模型返回工具调用时:

  • 单个工具调用 → 直接在主线程中执行
  • 多个工具调用 → 通过 ThreadPoolExecutor 并发执行
    • 例外:标记为交互式的工具(例如 clarify)强制顺序执行
    • 结果按原始工具调用顺序重新插入,不论完成顺序如何

执行流程

对于 response.tool_calls 中的每个 tool_call:
    1. 从 tools/registry.py 解析处理器
    2. 触发 pre_tool_call 插件钩子
    3. 检查是否为危险命令 (tools/approval.py)
       - 如果危险:调用 approval_callback,等待用户确认
    4. 使用 args + task_id 执行处理器
    5. 触发 post_tool_call 插件钩子
    6. 将 {"role": "tool", "content": result} 追加到历史

Agent 级工具

某些工具在到达 handle_function_call() 之前就被 run_agent.py 拦截

工具拦截原因
todo读/写 Agent 本地任务状态
memory写入带字符限制的持久化内存文件
session_search通过 Agent 的会话数据库查询会话历史
delegate_task生成具有隔离上下文的子 Agent

这些工具直接修改 Agent 状态并返回合成的工具结果,不经过注册表。

回调接口

AIAgent 支持平台特定的回调,实现 CLI、Gateway(网关)和 ACP 集成中的实时进度显示:

回调触发时机使用方
tool_progress_callback每次工具执行前后CLI 旋转器、Gateway 进度消息
thinking_callback模型开始/停止思考时CLI "thinking..." 指示器
reasoning_callback模型返回推理内容时CLI 推理显示、Gateway 推理块
clarify_callback调用 clarify 工具时CLI 输入提示、Gateway 交互消息
step_callback每次完整 Agent 轮次后Gateway 步骤跟踪、ACP 进度
stream_delta_callback每个流式 Token(启用时)CLI 流式显示
tool_gen_callback从流中解析出工具调用时CLI 旋转器中的工具预览
status_callback状态变更(thinking、executing 等)ACP 状态更新

预算和回退行为

迭代预算

Agent 通过 IterationBudget 跟踪迭代次数:

  • 默认值:90 次迭代(可通过 agent.max_turns 配置)
  • 每个 Agent 有自己的预算。子 Agent 获得独立预算,上限为 delegation.max_iterations(默认 50)——父 Agent + 子 Agent 的总迭代次数可以超过父 Agent 的上限
  • 达到 100% 时,Agent 停止并返回工作摘要

回退模型

当主模型失败时(429 速率限制、5xx 服务器错误、401/403 认证错误):

  1. 检查配置中的 fallback_providers 列表
  2. 按顺序尝试每个回退 Provider
  3. 成功后,使用新 Provider 继续对话
  4. 遇到 401/403 时,在故障转移之前尝试刷新凭据

回退系统还独立覆盖辅助任务——视觉、压缩、网页提取和会话搜索各自有独立的回退链,可通过 auxiliary.* 配置部分进行配置。

压缩和持久化

何时触发压缩

  • 预检(API 调用前):如果对话超过模型上下文窗口的 50%
  • Gateway 自动压缩:如果对话超过 85%(更激进,在轮次之间运行)

压缩期间发生什么

  1. 内存首先刷新到磁盘(防止数据丢失)
  2. 中间的对话轮次被摘要为紧凑的摘要
  3. 最后 N 条消息完整保留(compression.protect_last_n,默认:20)
  4. 工具调用/结果消息对保持在一起(不会被拆分)
  5. 生成新的会话世系 ID(压缩创建一个"子"会话)

会话持久化

每轮结束后:

  • 消息保存到会话存储(通过 hermes_state.py 的 SQLite)
  • 内存变更刷新到 MEMORY.md / USER.md
  • 会话可稍后通过 /resumehermes chat --resume 恢复

关键源文件

文件用途
run_agent.pyAIAgent 类——完整的 Agent 循环(约 10,700 行)
agent/prompt_builder.py从内存、技能、上下文文件、个性设置组装系统提示词
agent/context_engine.pyContextEngine ABC——可插拔的上下文管理
agent/context_compressor.py默认引擎——有损摘要算法
agent/prompt_caching.pyAnthropic 提示词缓存标记和缓存指标
agent/auxiliary_client.py用于辅助任务(视觉、摘要)的辅助 LLM 客户端
model_tools.py工具 Schema 集合、handle_function_call() 分发

相关文档

Continue Exploring

继续探索

这不是课程式的上一篇下一篇,而是从当前节点向外继续漫游。

开发者指南

Provider 运行时解析

sidebar position: 4 title: "Provider 运行时解析" description: "Hermes 如何在运行时解析 Provider、凭据、API 模式和辅助模型" Hermes 有一个共享的 Provider 运行时解析器,在以下场景中使用: - CLI

开发者指南

提示词组装

sidebar position: 5 title: "提示词组装" description: "Hermes 如何构建系统提示词、保持缓存稳定性和注入临时层" Hermes 刻意将以下两者分离: - 缓存的系统提示词状态 - 临时的 API 调用时添加内容 这是项目中最关键的设计决策之一,因为它影响:

开发者指南

上下文压缩与缓存

Hermes Agent 使用双重压缩系统和 Anthropic 提示词缓存,在长对话中高效管理上下文窗口的使用。 源文件:agent/context engine.py(ABC)、agent/context compressor.py(默认引擎)、agent/prompt caching.py、gateway/run

开发者指南

工具运行时(Tools Runtime)

原文链接:Tools Runtime sidebar position: 9 title: "Tools Runtime" description: "Runtime behavior of the tool registry, toolsets, dispatch, and terminal environments

开发者指南

架构

本页面是 Hermes Agent 内部结构的顶层地图. 使用它来了解代码库的整体结构,然后深入子系统文档获取实现细节。 如果你是首次接触此代码库: 1. 本页面 — 了解整体结构 2. Agent 循环内部机制 — AIAgent 如何工作 3. 提示词组装 — 系统提示词构建

开发者指南

贡献指南

感谢你对 Hermes Agent 的贡献!本指南涵盖开发环境设置、理解代码库以及如何让你的 PR 被合并。 我们按以下顺序重视贡献: 1. Bug 修复 — 崩溃、不正确行为、数据丢失 2. 跨平台兼容性 — macOS、不同 Linux 发行版、WSL2 3. 安全加固 — Shell 注入、Prompt 注入、路

Developer Guide

开发者指南

面向二次开发者,解释架构、运行时、上下文引擎、插件、工具与扩展机制。

20 篇文档20 个节点

当前节点

Agent 循环内部机制

同主题继续探索

架构

本页面是 Hermes Agent 内部结构的顶层地图. 使用它来了解代码库的整体结构,然后深入子系统文档获取实现细节。 如果你是首次接触此代码库: 1. 本页面 — 了解整体结构 2. Agent 循环内部机制 — AIAgent 如何工作 3. 提示词组装 — 系统提示词构建

贡献指南

感谢你对 Hermes Agent 的贡献!本指南涵盖开发环境设置、理解代码库以及如何让你的 PR 被合并。 我们按以下顺序重视贡献: 1. Bug 修复 — 崩溃、不正确行为、数据丢失 2. 跨平台兼容性 — macOS、不同 Linux 发行版、WSL2 3. 安全加固 — Shell 注入、Prompt 注入、路

提示词组装

sidebar position: 5 title: "提示词组装" description: "Hermes 如何构建系统提示词、保持缓存稳定性和注入临时层" Hermes 刻意将以下两者分离: - 缓存的系统提示词状态 - 临时的 API 调用时添加内容 这是项目中最关键的设计决策之一,因为它影响:

上下文压缩与缓存

Hermes Agent 使用双重压缩系统和 Anthropic 提示词缓存,在长对话中高效管理上下文窗口的使用。 源文件:agent/context engine.py(ABC)、agent/context compressor.py(默认引擎)、agent/prompt caching.py、gateway/run

网关内部机制

sidebar position: 7 title: "网关内部机制" description: "消息网关如何启动、授权用户、路由会话和投递消息" 消息网关是一个长运行进程,通过统一架构将 Hermes 连接到 14+ 个外部消息平台。 当消息从任何平台到达时: 1. 平台适配器 接收原始事件,将其规范化为 Mess

会话存储

Hermes Agent 使用 SQLite 数据库( /.hermes/state.db)来持久化会话元数据、完整消息历史和模型配置,覆盖 CLI 和网关会话。这取代了早期基于每个会话 JSONL 文件的方式。 源文件:hermes state.py 关键设计决策: - WAL 模式 用于并发读取 + 单个写入器(网

相关节点

Provider 运行时解析

sidebar position: 4 title: "Provider 运行时解析" description: "Hermes 如何在运行时解析 Provider、凭据、API 模式和辅助模型" Hermes 有一个共享的 Provider 运行时解析器,在以下场景中使用: - CLI

提示词组装

sidebar position: 5 title: "提示词组装" description: "Hermes 如何构建系统提示词、保持缓存稳定性和注入临时层" Hermes 刻意将以下两者分离: - 缓存的系统提示词状态 - 临时的 API 调用时添加内容 这是项目中最关键的设计决策之一,因为它影响:

上下文压缩与缓存

Hermes Agent 使用双重压缩系统和 Anthropic 提示词缓存,在长对话中高效管理上下文窗口的使用。 源文件:agent/context engine.py(ABC)、agent/context compressor.py(默认引擎)、agent/prompt caching.py、gateway/run

工具运行时(Tools Runtime)

原文链接:Tools Runtime sidebar position: 9 title: "Tools Runtime" description: "Runtime behavior of the tool registry, toolsets, dispatch, and terminal environments

架构

本页面是 Hermes Agent 内部结构的顶层地图. 使用它来了解代码库的整体结构,然后深入子系统文档获取实现细节。 如果你是首次接触此代码库: 1. 本页面 — 了解整体结构 2. Agent 循环内部机制 — AIAgent 如何工作 3. 提示词组装 — 系统提示词构建

贡献指南

感谢你对 Hermes Agent 的贡献!本指南涵盖开发环境设置、理解代码库以及如何让你的 PR 被合并。 我们按以下顺序重视贡献: 1. Bug 修复 — 崩溃、不正确行为、数据丢失 2. 跨平台兼容性 — macOS、不同 Linux 发行版、WSL2 3. 安全加固 — Shell 注入、Prompt 注入、路