编程 自进化AI Agent的工程真相:Hermes Agent三层记忆架构、GEPA算法与技能自生成机制深度解析

2026-07-25 16:15:43 +0800 CST views 11

Hermes Agent 深度解剖:21万星背后的自进化闭环——从三层记忆架构到 GEPA 算法的工程真相

前言

2026年的开源AI Agent赛道热闹非凡。从OpenClaw的跨平台助手,到各类垂直场景的专用Agent,开发者们似乎已经习惯了"每次会话从零开始"这个宿命。但有一个项目从发布第一天起就走了一条完全不同的路——它不仅能帮你干活,还会在每次干活之后反思:这次有什么坑?下次怎么做得更好?然后自动把这个经验写进自己的"操作手册",下次遇到同类问题时直接调用。

这个项目叫 Hermes Agent,来自一家在开源社区久负盛名、但大多数人并不熟悉的团队——Nous Research。截至2026年7月,GitHub Star数已突破21万,是GitHub历史上增长最快的AI Agent项目之一。

很多人听说过它的名号,但真正读懂它工程实现的人并不多。"自进化"听起来像是AGI的前奏,但技术实现往往比产品叙事更克制、更复杂。本文将彻底拆开Hermes Agent的源码和架构设计,从三层记忆架构、Skill自生成引擎、GEPA进化算法、多终端后端设计、到ACP通信协议,手把手带你理解一个真正"会成长"的AI Agent是怎么炼成的。


一、项目全景:它到底是什么?

1.1 一句话定义

Hermes Agent 是一个内置完整学习闭环的开源自进化AI Agent框架。它的核心理念浓缩在项目README的第一句话里:

"The only agent with a built-in learning loop — it creates skills from experience, improves them during use, nudges itself to persist knowledge, searches its own past conversations, and builds a deepening model of who you are across sessions."

翻译过来:它是唯一一个内置完整学习闭环的Agent——它从经验中创建技能、在使用中改进技能、主动提醒自己把重要知识写入持久化记忆、检索自己历史会话中的相关内容,并跨会话对你这个用户建立越来越精确的画像。

这不是一个"包装了一层LLM API的聊天机器人",而是一套完整的Agent Harness(智能体运行时)。它内部维护了68个内置工具、完整的会话存储(SQLite + FTS5全文检索)、上下文压缩、Provider故障切换、密钥池、多终端后端,以及最核心的——自我改进的学习引擎

1.2 关键数据一览

属性详情
开发者Nous Research
许可证MIT(完全自由,可商用)
主语言Python(占比88.5%)+ TypeScript/TSX(Web UI,占比8.1%)
Python版本要求≥ 3.11(硬性要求,不兼容3.10)
总文件数~1717
测试用例~3000个
内置工具数量40+
消息平台支持~10个(Telegram/Discord/Slack/WhatsApp/QQ/飞书等)
内置技能数量288个
可选技能数量116个
支持模型Provider200+(OpenAI/Anthropic/OpenRouter/GLM/Kimi/MiniMax/DeepSeek/Qwen等)
最低运行配置$5 VPS
最高运行配置GPU集群、Daytona/Modal Serverless

1.3 Hermes Agent vs 其他主流Agent框架

市面上类似的工具有不少,但定位差异巨大:

特性Hermes AgentOpenClawLangChain AgentsAutoGPT
自进化能力✅ 内置闭环❌ 依赖手写Skill❌ 无❌ 无
记忆持久化✅ SQLite FTS5✅ 有(追加模式)❌ 无❌ 无
技能自动生成✅ GEPA算法驱动❌ 纯手动❌ 无❌ 无
研究/训练支持✅ 内置RL环境❌ 无❌ 无❌ 无
多终端后端✅ 6种✅ 多种✅ 可扩展❌ 仅本地
Skill格式MarkdownMarkdownLangChain格式纯Prompt
代码规模~1700文件~14000文件框架级较小
学习曲线中等较高

关键差异:OpenClaw的Skill是手写的——你写多少它会多少,你不写它就不会。Hermes做了一件OpenClaw架构上做不了的事:Agent干完活之后,会自动把踩坑经验提炼成可复用的Skill文件,下次遇到同类问题直接调用。用得越久,能力越强。这不是功能差异,是设计哲学的分野——一个靠人喂,一个自己长。


二、整体架构:一张图看懂全貌

2.1 架构分层全景

Hermes Agent的架构可以划分为五个层次,从上到下依次是:

┌─────────────────────────────────────────────────────────┐
│                    Interface Layer(接口层)              │
│  ┌──────────┐  ┌──────────┐  ┌──────────┐  ┌─────────┐  │
│  │  CLI TUI │  │ Telegram │  │ Discord  │  │ Slack   │ ... │
│  └──────────┘  └──────────┘  └──────────┘  └─────────┘  │
├─────────────────────────────────────────────────────────┤
│                    Agent Core(核心Agent层)              │
│  ┌─────────────────┐                                    │
│  │   AIAgent       │  ← run_agent.py,同步对话循环      │
│  │   (主Agent循环)  │                                    │
│  └────────┬────────┘                                    │
│           │                                             │
│  ┌────────┴────────────────────────────────────────┐   │
│  │ Tool Registry │ Memory Manager │ Skills System   │   │
│  │ Model Meta    │ Cron Scheduler │ Context Compressor│  │
│  └─────────────────────────────────────────────────┘   │
├─────────────────────────────────────────────────────────┤
│                 Tool Implementations(工具实现层)        │
│  terminal │ file │ web │ browser │ code_exec │ delegate│
│  mcp │ vision │ tts │ cron │ delegate │ ... (40+)     │
├─────────────────────────────────────────────────────────┤
│              Terminal Backends(终端执行后端)            │
│  local │ docker │ ssh │ daytona │ modal │ ... (6种)   │
├─────────────────────────────────────────────────────────┤
│              Persistence & Research(持久化与研究层)     │
│  ┌─────────────┐  ┌──────────────────────────────────┐  │
│  │ SessionDB   │  │ RL Training Environment (Atropos) │  │
│  │ (SQLite     │  │ 轨迹记录 │ 批量运行器 │ SWE-bench │  │
│  │  + FTS5)    │  └──────────────────────────────────┘  │
│  └─────────────┘                                        │
└─────────────────────────────────────────────────────────┘

2.2 五个关键架构决策

决策一:同步Agent循环

run_agent.py中的AIAgent是一个完全同步的while循环,没有使用async/await。这个选择看似"保守",实则蕴含深意:

# 来自 run_agent.py 的核心循环(简化版)
while api_call_count < self.max_iterations and self.iteration_budget.remaining > 0:
    response = client.chat.completions.create(
        model=model,
        messages=messages,
        tools=tool_schemas
    )
    if response.tool_calls:
        for tool_call in response.tool_calls:
            result = handle_function_call(
                tool_call.name,
                tool_call.args,
                task_id
            )
            messages.append(tool_result_message(result))
        api_call_count += 1
    else:
        return response.content

相比OpenClaw复杂的异步架构,同步设计大大降低了理解和调试的复杂度。对于一个需要快速迭代的开源项目来说,可理解性 > 理论性能。用户实时交互这条链路关心的不是"能跑通",而是"跑不通以后怎么办"——上下文压缩、Provider容错、用户中断、预算耗尽后的Grace Call,这些逻辑在同步模型下更容易推理。

决策二:中心化工具注册

所有工具通过tools/registry.py统一注册和分发。添加一个新工具只需两步:

# 第一步:在 tools/your_tool.py 中定义handler
from tools.registry import registry

@registry.register(
    name="your_tool",
    description="做什么的",
    schema={...}
)
def your_tool_handler(args, context):
    # 业务逻辑
    return result
# 第二步:在 toolsets.py 中注册
# toolsets.py
TOOLSETS = {
    "default": [
        # ... 已有工具
        "your_tool",  # ← 加一行即可
    ]
}

这种设计让工具体系高度可插拔,新增Provider不需要修改核心代码。

决策三:OpenAI消息格式统一

无论使用哪个LLM Provider(Claude、GPT、DeepSeek等),内部统一使用OpenAI兼容的消息格式:

# 统一的消息格式(OpenAI兼容)
messages = [
    {"role": "system", "content": "系统提示词"},
    {"role": "user", "content": "用户输入"},
    {"role": "assistant", "content": "模型回复", "tool_calls": [...]},
    {"role": "tool", "tool_call_id": "...", "content": "工具执行结果"}
]

这使得多Provider适配的复杂度大幅降低,新增一个Provider只需实现一个adapter。

决策四:Profile多实例隔离

通过HERMES_HOME环境变量实现完全隔离的多实例支持。代码中有119+处引用get_hermes_home()确保路径隔离:

# 来自 hermes_state.py
def get_hermes_home() -> Path:
    return Path(os.environ.get("HERMES_HOME", "~/.hermes")).expanduser()

这对于多租户场景至关重要——同一台机器上可以运行多个完全隔离的Hermes实例,每个实例有独立的记忆、技能和配置。

决策五:研究导向的模块设计

RL训练环境、轨迹压缩、批量运行器这些模块不是"后来加的",而是从一开始就融入架构设计的核心组件。如果你在做Agent相关的学术研究或模型训练,Hermes Agent几乎是目前最开箱即用的研究平台。


三、三层记忆架构:让Agent"越用越懂你"

Hermes Agent的记忆系统是其区别于所有其他开源Agent的核心。这套系统借鉴了认知科学中经典的记忆三分法理论,将Agent的记忆划分为三个层次:

3.1 第一层:工作记忆(Working Memory)

工作记忆相当于人类的"工作台"——存储当前会话的即时上下文。生命周期与当前会话相同,容量受限于模型的context window大小,作用是维持单次对话的连贯性。

在代码层面,工作记忆由agent/memory_manager.py管理:

# 简化版工作记忆管理逻辑
class MemoryManager:
    def __init__(self, session_id: str):
        self.session_id = session_id
        self.working_memory = []  # 当前会话的消息历史
    
    def add_turn(self, role: str, content: str):
        """添加一轮对话到工作记忆"""
        self.working_memory.append({
            "role": role,
            "content": content,
            "timestamp": time.time()
        })
    
    def compress_if_needed(self, max_turns: int = 50):
        """当上下文过长时自动压缩"""
        if len(self.working_memory) > max_turns:
            # 保留首尾关键信息,中间部分做摘要
            compressed = self.compress_middle(self.working_memory)
            self.working_memory = compressed

当context window快用满时,系统会自动触发上下文压缩——将中间轮次的对话压缩为语义摘要,保留关键决策点和用户偏好信息。这解决了大模型context window有限的问题,让Agent在长会话中依然保持高效。

3.2 第二层:情景记忆(Episodic Memory)

情景记忆相当于人类的"日记本"——记录跨会话的事实、偏好和经历。生命周期为永久保存,存储方式为SQLite + FTS5全文检索,作用是跨会话记住你的项目、偏好和习惯。

# ~/.hermes/ 目录结构
~/.hermes/
├── memories/
│   ├── MEMORY.md      # Agent的个人笔记(环境事实、项目约定、工具怪癖)
│   └── USER.md        # Agent对用户的认知(偏好、沟通风格、工作习惯)
├── sessions/
│   └── *.db           # SQLite会话数据库(带FTS5全文索引)
└── skills/
    ├── built-in/      # 288个内置技能
    └── user/          # 用户创建的技能

这里有一个非常精妙的设计:容量上限故意设得很紧。MEMORY.md限制2200字符,USER.md限制1375字符。这种"容量有限就迫使Agent挑重要的记"的机制,比OpenClaw的纯追加模式(用几个月就膨胀成几万行的怪兽文件)要健康得多。

举一个实际场景:

第1天:
你:"我的项目用的是Next.js 14 + TypeScript + TailwindCSS"
Hermes Agent:[自动写入USER.md] 用户偏好: Next.js 14, TypeScript, TailwindCSS

第30天:
你:"帮我加一个新页面"
Hermes Agent:[自动检索USER.md] 检测到用户项目技术栈 → 直接用Next.js 14创建页面组件,样式用TailwindCSS

这就是跨会话记忆的实际价值——你不需要重复解释自己的技术栈和环境,Agent会自己记住。

3.3 第三层:程序记忆(Procedural Memory)

程序记忆相当于人类的"肌肉记忆"——将反复执行的复杂操作固化为自动化技能。这是Hermes Agent最独特的设计,也是其"自进化"能力的基础。

当Agent完成一个复杂任务后,它会评估:这次操作是否值得沉淀为可复用技能?

# 自生成技能的简化逻辑(来自源码概念)
def evaluate_and_create_skill(self, task: Task, result: Result):
    # 1. 评估:这个任务是否有复用的价值?
    if self.is_reusable(task, result):
        # 2. 提取:把这次的经验提炼成结构化的Skill文件
        skill_content = self.extract_skill(task, result)
        
        # 3. 写入:生成Markdown格式的Skill文件
        skill_path = self.skills_dir / f"{skill.name}.md"
        with open(skill_path, "w") as f:
            f.write(skill_content)
        
        # 4. 注册:让系统知道这个新技能
        self.skill_registry.register(skill)
        
        # 5. 优化:如果已有同名技能,比较并选择更好的版本
        self.gepa_optimize(skill.name)

生成的Skill文件是Markdown格式,人类可读可编辑:

---
name: deploy-nextjs-to-vercel
description: 一键将Next.js项目部署到Vercel平台
trigger_keywords: ["部署", "vercel", "发布", "deploy"]
---
# 部署Next.js到Vercel

## 适用场景
当用户要求将Next.js项目部署上线时使用此技能。

## 操作步骤

### 1. 检查项目环境
\`\`\`bash
cd /path/to/project
# 确认是Next.js项目
ls package.json | grep next
\`\`\`

### 2. 安装Vercel CLI(如未安装)
\`\`\`bash
npm i -g vercel
\`\`\`

### 3. 执行部署
\`\`\`bash
vercel --yes
\`\`\`

### 4. 生产环境部署
\`\`\`bash
vercel --prod
\`\`\`

## 注意事项
- 首次部署需要登录Vercel账号
- 环境变量需要在Vercel控制台配置
- 部署完成后会自动生成生产URL

这种"任务完成 → 经验沉淀 → 技能固化 → 持续优化"的闭环,让Hermes Agent真正实现了"越用越聪明"。

3.4 Honcho用户建模系统

除了三层记忆架构,Hermes Agent还集成了Honcho——一个跨会话的用户画像系统。Honcho通过分析用户的历史对话,自动构建用户的偏好模型:

# Honcho用户建模的核心逻辑
class HonchoUserModeling:
    def analyze_conversation(self, messages: list) -> UserProfile:
        profile = UserProfile()
        
        # 分析编程语言偏好
        profile.languages = self.extract_language_preferences(messages)
        
        # 分析工具偏好
        profile.tools = self.extract_tool_preferences(messages)
        
        # 分析沟通风格
        profile.communication_style = self.analyze_style(messages)
        
        # 分析工作习惯
        profile.work_habits = self.extract_work_habits(messages)
        
        return profile
    
    def build_context(self, profile: UserProfile) -> str:
        # 将用户画像注入到系统提示词中
        return f"""
        用户画像:
        - 常用语言:{', '.join(profile.languages)}
        - 偏好工具:{', '.join(profile.tools)}
        - 沟通风格:{profile.communication_style}
        - 工作习惯:{', '.join(profile.work_habits)}
        """

这样,每次新的会话开始时,Agent就已经知道你是谁、你喜欢用什么工具、你习惯怎么沟通,从而提供更个性化的服务。


四、Skill自进化引擎:从经验中长出能力

4.1 技能系统的基本结构

Hermes Agent的技能系统兼容agentskills.io开放标准,所有技能都是Markdown格式,人类可读、可编辑、可版本控制。内置288个技能,覆盖了文件操作、代码编写、终端命令、网页搜索、数据处理等常见场景。

技能文件的完整结构:

---
name: skill-name                    # 技能唯一标识
description: 简短描述               # 用于Agent检索
trigger_keywords:                   # 触发关键词
  - "关键词1"
  - "关键词2"
version: "1.0.0"                    # 版本号
author: "auto-generated"            # auto-generated表示自动生成
created_at: "2026-07-25"           # 创建时间
---

# 技能标题

## 描述
详细的技能描述,说明适用场景和使用方法。

## 前置条件
使用此技能前需要满足的条件。

## 执行步骤

### 步骤1:XXX
\`\`\`bash
command_or_code
\`\`\`

### 步骤2:XXX
...

## 注意事项
- 注意事项1
- 注意事项2

## 示例
\`\`\`example
输入: xxx
输出: xxx
\`\`\`

4.2 闭环学习循环的五个阶段

Hermes Agent的学习闭环分为五个阶段,形成一个完整的自进化循环:

┌─────────────────────────────────────────────────────────┐
│                                                         │
│  阶段1:执行任务                                         │
│  Agent接收用户请求,调用工具链完成任务                   │
│       ↓                                                 │
│  阶段2:观察结果                                         │
│  记录执行轨迹、耗时、错误信息、中间状态                 │
│       ↓                                                 │
│  阶段3:提取经验                                         │
│  分析执行过程中的关键决策点、踩过的坑、有效的策略       │
│       ↓                                                 │
│  阶段4:创建/改进技能                                    │
│  生成或更新Skill文件,提炼可复用的操作流程              │
│       ↓                                                 │
│  阶段5:持久化知识                                       │
│  将重要事实写入MEMORY.md/USER.md,跨会话保留            │
│                                                         │
│       ↑                                                 │
│       └────────────── 下一轮任务使用改进后的技能 ←──────┘
└─────────────────────────────────────────────────────────┘

4.3 Nudge Engine:定时触发的"反思闹钟"

光有闭环还不够——Agent可能会"忘记"反思。Hermes Agent内置了Nudge Engine,定时提醒Agent反思和沉淀:

# Nudge Engine的核心逻辑
class NudgeEngine:
    def __init__(self):
        self.nudge_interval = timedelta(hours=2)  # 每2小时提醒一次
        self.last_nudge = None
    
    def should_nudge(self) -> bool:
        """判断是否应该触发Nudge"""
        if self.last_nudge is None:
            return True
        return datetime.now() - self.last_nudge >= self.nudge_interval
    
    def generate_nudge(self, agent_state: AgentState) -> str:
        """生成Nudge提示"""
        return f"""
        [Nudge] 你已经运行了一段时间。请检查:
        
        1. 有什么重要的环境信息值得写入MEMORY.md吗?
           当前工作目录:{agent_state.cwd}
           检测到的技术栈:{agent_state.detected_stack}
        
        2. 有什么用户偏好值得写入USER.md吗?
           用户最近请求:{agent_state.recent_requests[-3:]}
        
        3. 有什么操作流程值得固化为Skill吗?
           最近执行的复杂任务:{agent_state.complex_tasks[-1]}
        """

4.4 GEPA算法:进化式的技能优化

当同一个Skill被多次调用后,Hermes Agent会启动GEPA(Generative Evolutionary Performance Assessment)算法来优化它。这套算法是Hermes区别于所有其他Agent框架的核心技术创新。

GEPA的工作原理:

# GEPA算法的核心流程(简化版)
class GEPA:
    def optimize_skill(self, skill_name: str):
        # 1. 读取当前Skill文件
        current_skill = self.read_skill(skill_name)
        
        # 2. 从历史会话中采样或合成评估数据集
        eval_dataset = self.build_evaluation_dataset(skill_name)
        
        # 3. 生成多个候选变体
        candidates = []
        for i in range(5):  # 生成5个变体
            variant = self.mutate_skill(current_skill)
            candidates.append(variant)
        
        # 4. 评估每个候选变体
        results = []
        for candidate in candidates:
            score = self.evaluate(candidate, eval_dataset)
            results.append((candidate, score))
        
        # 5. Pareto前沿选择:不选全局最优,而是选每个评估样本上的最优
        pareto_optimal = self.pareto_selection(results)
        
        # 6. 如果有改进,创建PR供人工审查
        if pareto_optimal.score > current_skill.score:
            self.create_pull_request(skill_name, pareto_optimal)
    
    def mutate_skill(self, skill: Skill) -> Skill:
        """对Skill进行变异操作"""
        mutations = [
            self.simplify_steps,           # 简化步骤
            self.add_error_handling,       # 增加错误处理
            self.optimize_command_order,   # 优化命令顺序
            self.add_alternatives,         # 增加替代方案
            self.reduce_token_usage,       # 减少token使用
        ]
        mutation = random.choice(mutations)
        return mutation(skill)

Pareto前沿选择是GEPA的核心创新点。传统的优化算法会选择"平均分最高"的变体,但GEPA认为:一个Skill的价值不在于平均表现,而在于它是否在某些场景下表现最好。只要一个候选在任意一个评估样本上表现最好,就会被保留到下一代。

def pareto_selection(self, candidates: list) -> list:
    """
    Pareto前沿选择算法
    一个解不被另一个解在所有维度上支配,则该解在Pareto前沿上
    """
    pareto_front = []
    for candidate, score in candidates:
        is_dominated = False
        for other, other_score in candidates:
            if other is candidate:
                continue
            # 如果other在所有维度上都不比candidate差,且至少一个维度更好
            if self.dominates(other_score, score):
                is_dominated = True
                break
        if not is_dominated:
            pareto_front.append((candidate, score))
    return pareto_front

4.5 DSPy + GEPA集成

Hermes Agent的技能优化引擎底层集成了DSPy框架,用于自动优化提示词和工具描述:

优化目标引擎许可证集成方式
技能文件GEPAMIT原生集成
系统提示词DSPyMIT原生集成
工具描述DSPyMIT原生集成
指令模板GEPAMIT原生集成

这种"进化式优化"的方法论,让技能系统不是静态的,而是活的——随着使用次数的增加,每个技能都在持续改进。


五、多终端后端:一张命令跨所有环境执行

5.1 六种执行后端

Hermes Agent支持六种不同的终端执行后端,让同一套Agent代码可以运行在任何环境中:

后端说明适用场景
local直接在本地执行命令本地开发、快速测试
docker在Docker容器中执行隔离环境、生产部署
ssh通过SSH连接到远程服务器执行远程服务器、云计算
daytonaDaytona云开发环境云端开发、团队协作
modalModal Serverless平台弹性计算、按需扩展
inference推理专用后端模型服务、AI计算

这个设计解决了Agent部署的一个核心痛点:同一套Agent代码,在本地调试时用local后端,生产部署时切换到docker后端,完全无需修改业务逻辑

5.2 后端抽象层设计

所有后端都实现了统一的抽象接口:

from abc import ABC, abstractmethod

class TerminalBackend(ABC):
    @abstractmethod
    def execute(self, command: str, cwd: str = None) -> ExecutionResult:
        """执行命令并返回结果"""
        pass
    
    @abstractmethod
    def upload_file(self, local_path: str, remote_path: str) -> bool:
        """上传文件"""
        pass
    
    @abstractmethod
    def download_file(self, remote_path: str, local_path: str) -> bool:
        """下载文件"""
        pass
    
    @abstractmethod
    def get_env_info(self) -> EnvInfo:
        """获取环境信息(操作系统、Python版本等)"""
        pass

# 具体实现
class DockerBackend(TerminalBackend):
    def execute(self, command: str, cwd: str = None) -> ExecutionResult:
        # Docker特有的实现
        container = self.get_container()
        result = container.exec_run(
            cmd=f"bash -c 'cd {cwd} && {command}'"
        )
        return ExecutionResult(
            stdout=result.output.decode(),
            stderr=result.stderr.decode(),
            exit_code=result.exit_code
        )

5.3 工具链的跨环境适配

不同后端环境下,同一个工具可能需要不同的实现。Hermes Agent通过工具适配器模式解决这一问题:

# 工具的跨环境适配
class FileTool(AgentTool):
    def __init__(self, backend: TerminalBackend):
        self.backend = backend
    
    def execute(self, operation: str, path: str, content: str = None):
        if self.backend.type == "docker":
            # Docker环境下的文件操作需要特殊处理
            return self._docker_file_op(operation, path, content)
        elif self.backend.type == "ssh":
            # SSH环境下通过SFTP操作文件
            return self._ssh_file_op(operation, path, content)
        else:
            # 本地环境直接操作
            return self._local_file_op(operation, path, content)

六、消息网关:从终端到全平台的覆盖

6.1 ACP协议:Agent Communication Protocol

Hermes Agent通过**ACP(Agent Communication Protocol)**连接各种消息平台。ACP是一种专为AI Agent设计的通信协议,支持:

  • 多轮对话管理:支持上下文连续性
  • 工具调用传递:将Agent的工具调用结果回传给用户
  • 多租户隔离:每个用户/群组独立会话
  • 消息格式标准化:统一Telegram/Discord/Slack/WhatsApp的消息格式
# ACP适配器的核心接口
class ACPAdapter(ABC):
    @abstractmethod
    def send_message(self, chat_id: str, message: ACPMessage) -> str:
        """发送消息到指定渠道"""
        pass
    
    @abstractmethod
    def on_message(self, raw_message: Any) -> ACPMessage:
        """将原始消息转换为ACPMessage格式"""
        pass
    
    @abstractmethod
    def build_reply_context(self, message: ACPMessage) -> dict:
        """构建回复上下文"""
        pass

# 支持的平台
PLATFORMS = {
    "telegram": TelegramACPAdapter,
    "discord": DiscordACPAdapter,
    "slack": SlackACPAdapter,
    "whatsapp": WhatsAppACPAdapter,
    "qq": QQACPAdapter,
    "feishu": FeishuACPAdapter,
}

6.2 Gateway架构

消息网关采用插件化架构,每个平台是一个独立的插件:

gateway/
├── __init__.py
├── base.py              # 网关基类
├── message_router.py    # 消息路由器
└── platforms/
    ├── telegram/
    │   ├── bot.py       # Telegram Bot实现
    │   ├── handlers.py  # 消息处理器
    │   └── config.py    # 配置
    ├── discord/
    │   └── ...
    ├── slack/
    │   └── ...
    └── ...

新增一个消息平台只需实现对应的Adapter即可,核心逻辑无需修改。

6.3 ACP Registry服务发现

Hermes Agent还支持ACP Registry——一个服务发现机制,让多个Agent实例之间可以互相通信和协作:

# ACP Registry的简化实现
class ACPRegistry:
    def __init__(self):
        self.services = {}
    
    def register(self, agent_id: str, endpoint: str, capabilities: list):
        """注册一个Agent服务"""
        self.services[agent_id] = {
            "endpoint": endpoint,
            "capabilities": capabilities,
            "registered_at": time.time()
        }
    
    def discover(self, capability: str) -> list:
        """发现提供特定能力的Agent"""
        return [
            agent for agent in self.services.values()
            if capability in agent["capabilities"]
        ]
    
    def delegate_task(self, task: Task, target_capability: str) -> str:
        """将任务委托给具备特定能力的Agent"""
        candidates = self.discover(target_capability)
        if not candidates:
            raise NoAgentFoundError(f"No agent with capability: {target_capability}")
        # 选择最合适的Agent(负载最低、响应最快)
        target = self.select_best(candidates)
        return self.forward_task(task, target["endpoint"])

这使得多Agent协作成为可能——一个Agent发现自己的记忆里有相关信息,可以自动委托给另一个专门处理该领域的Agent。


七、代码实战:构建你的第一个自进化Skill

7.1 场景设定

让我们通过一个具体场景来理解Skill的生成和使用过程。假设用户向Hermes Agent提出以下请求:

"帮我把这个Python脚本改成并发版本,要求用asyncio实现。"

7.2 Agent执行过程

# 第一步:理解任务
user_request = "帮我把这个Python脚本改成并发版本,要求用asyncio实现"
task_analysis = agent.analyze_task(user_request)
# 输出:Task(type="code_rewrite", lang="python", pattern="concurrent", framework="asyncio")

# 第二步:检查是否有相关Skill
existing_skill = agent.skill_registry.find("python-asyncio-concurrent")
if existing_skill:
    # 直接复用已有Skill
    steps = existing_skill.execute(original_code)
else:
    # 执行任务(这里省略具体实现)
    steps = agent.execute_code_rewrite(original_code, "asyncio")

# 第三步:执行工具调用
for step in steps:
    result = agent.tools.execute(step)
    agent.memory.add_turn("tool", result)
    if result.status == "error":
        agent.handle_error(result)

# 第四步:任务完成,评估是否需要生成Skill
if agent.should_create_skill(task_analysis, result):
    # 生成新的Skill文件
    new_skill = agent.generate_skill_from_experience(
        task=task_analysis,
        execution_trace=agent.get_trace(),
        result=result
    )
    agent.skill_registry.register(new_skill)
    print(f"✅ 已生成新技能:{new_skill.name}")

7.3 生成的Skill文件示例

---
name: python-async-concurrent-rewrite
description: 将同步Python代码改写为asyncio并发版本
trigger_keywords:
  - "asyncio"
  - "并发"
  - "concurrent"
  - "异步改写"
version: "1.0.0"
author: auto-generated
created_at: "2026-07-25"
---

# Python asyncio 并发改写技能

## 适用场景
当用户要求将同步Python代码改写为异步并发版本时使用。

## 改写规则

### 规则1:同步函数 → 异步函数
\`\`\`python
# 改写前
def fetch_data(url):
    response = requests.get(url)
    return response.json()

# 改写后
async def fetch_data(url: str, session: aiohttp.ClientSession) -> dict:
    async with session.get(url) as response:
        return await response.json()
\`\`\`

### 规则2:for循环 → asyncio.gather
\`\`\`python
# 改写前
results = []
for url in urls:
    results.append(fetch_data(url))

# 改写后
async def fetch_all(urls: list) -> list:
    async with aiohttp.ClientSession() as session:
        tasks = [fetch_data(url, session) for url in urls]
        return await asyncio.gather(*tasks)
\`\`\`

### 规则3:time.sleep → asyncio.sleep
\`\`\`python
# 改写前
import time
time.sleep(1)

# 改写后
import asyncio
await asyncio.sleep(1)
\`\`\`

### 规则4:requests → aiohttp
\`\`\`python
# 改写前
import requests
response = requests.get(url)

# 改写后
import aiohttp
async with aiohttp.ClientSession() as session:
    async with session.get(url) as response:
        return await response.json()
\`\`\`

## 完整改写模板
\`\`\`python
import asyncio
import aiohttp

async def async_main(urls: list):
    async with aiohttp.ClientSession() as session:
        tasks = [fetch_data(url, session) for url in urls]
        return await asyncio.gather(*tasks)

if __name__ == "__main__":
    urls = ["https://api.example.com/data/1", ...]
    results = asyncio.run(async_main(urls))
\`\`\`

## 注意事项
- 异步函数内部不能直接调用同步阻塞代码(如time.sleep)
- 需要安装aiohttp:`pip install aiohttp`
- 并发数过多可能导致请求被限流,需要添加信号量控制并发数

7.4 在实际场景中使用

下次用户再说"帮我把data_fetcher.py改成并发"时,Agent会:

  1. 检索Skill Registry,找到python-async-concurrent-rewrite
  2. 读取Skill文件,加载到工作记忆
  3. 按照Skill定义的改写规则处理原始代码
  4. 输出改写后的完整代码

整个过程无需人工介入,Agent自动完成了经验积累和能力提升。


八、部署实践:从$5 VPS到GPU集群

8.1 一键安装

Hermes Agent的安装非常简单,一条命令搞定所有依赖:

curl -fsSL https://raw.githubusercontent.com/NousResearch/hermes-agent/main/scripts/install.sh | bash
source ~/.bashrc  # 或 source ~/.zshrc
hermes --version

安装脚本会自动检测操作系统(Linux/macOS/WSL2/Termux),并安装Python、Node.js、ripgrep等所有依赖。

8.2 不同场景的部署方案

场景1:本地开发(推荐配置)

# 使用local后端,本地执行所有命令
hermes setup
# 选择 "1. Quick setup"
# 配置API Key(支持OpenAI/Anthropic/OpenRouter等多种Provider)

hermes start
# 启动Web面板和CLI界面

场景2:$5 VPS生产部署

# 使用docker后端,隔离运行环境
hermes config set backend docker
hermes config set docker_image nousresearch/hermes-agent:latest

# 配置开机自启
sudo systemctl enable hermes-agent

# 启动服务
hermes start

场景3:GPU集群训练

# 使用ssh后端连接GPU服务器
hermes config set backend ssh
hermes config set ssh_host gpu-cluster.example.com
hermes config set ssh_user deploy

# 启动RL训练
hermes train --model hermes-3-llama-3-8b --episodes 10000

8.3 环境变量配置

# ~/.hermes/.env
HERMES_HOME=~/.hermes                    # 数据目录
LLM_PROVIDER=openrouter                  # 模型提供商
OPENROUTER_API_KEY=sk-or-...             # API Key
DEFAULT_MODEL=anthropic/claude-3-5-sonnet # 默认模型
BACKEND=docker                           # 执行后端
LOG_LEVEL=INFO                           # 日志级别
MAX_ITERATIONS=100                       # 最大迭代次数
SESSION_TIMEOUT=3600                     # 会话超时(秒)

九、与OpenClaw的横向对比

作为2026年最火的两款开源Agent框架,Hermes Agent和OpenClaw经常被拿来比较。下面从五个维度进行深度对比:

9.1 记忆系统对比

维度Hermes AgentOpenClaw
存储方式SQLite FTS5 + 纯文本纯文本(MEMORY.md)
容量控制硬性上限(2200/1375字符)无限制(追加模式)
跨会话检索FTS5全文搜索线性扫描
用户建模Honcho自动分析手动维护
记忆质量自我策展(Agent决定记什么)被动记录

结论:Hermes Agent的记忆系统更智能,OpenClaw的记忆系统更简单。

9.2 安全架构对比

维度Hermes AgentOpenClaw
危险命令检测47条规则自动拦截配置化
执行后端隔离docker/ssh多种后端主要本地
多租户隔离HERMES_HOME环境隔离Workspace隔离

9.3 技能插件对比

维度Hermes AgentOpenClaw
Skill生成自动+GEPA优化纯手动
Skill格式Markdown(人类可读)Markdown
技能市场Skills Hub在线市场Skill文件本地管理
技能数量288+116可选依赖用户创建

9.4 选择建议

  • 选择Hermes Agent:如果你想要一个"越用越聪明"的Agent,重视自动化的经验积累,或者在做Agent相关的学术研究
  • 选择OpenClaw:如果你需要更丰富的多渠道支持(语音、Canvas等),或者需要一个开箱即用的多模态助手

十、总结与展望

10.1 Hermes Agent的核心价值

Hermes Agent之所以能在不到半年内积累21万Star,本质上是因为它解决了一个根本问题:传统Agent是"无状态的",每次会话从零开始;Hermes Agent是"有记忆的",每次会话都在积累经验

这种"自我进化"的设计哲学,让AI Agent从"工具"进化成了"数字同事"。你不是在"使用"一个AI,而是在"培养"一个越来越懂你的AI伙伴。

10.2 技术亮点总结

  1. 三层记忆架构:工作记忆、情景记忆、程序记忆,模拟人类认知科学的记忆模型
  2. GEPA进化算法:用进化计算的思想持续优化Skill,让能力随使用次数增长
  3. 六种终端后端:统一的抽象接口,让同一套代码运行在任何环境
  4. ACP通信协议:标准化的多平台消息网关,支持多Agent协作
  5. 研究就绪:内置RL训练环境、轨迹记录、批量评估器,是Agent研究的最佳平台

10.3 未来展望

从目前的发展趋势来看,Hermes Agent可能会在以下几个方向持续演进:

  1. 多Agent协作:ACP Registry的完善,支持多个Hermes实例之间的任务分工
  2. 更强大的推理能力:集成更多推理模型,提升复杂任务的规划能力
  3. 技能市场的繁荣:随着用户贡献的Skill越来越多,Skills Hub可能成为AI Agent的"GitHub"
  4. 端侧部署:针对移动端和嵌入式设备的轻量化优化

参考资料


本文基于Hermes Agent v0.10.0源码分析,项目持续迭代中,具体实现可能随版本更新而变化。如有疏漏,欢迎指正。

推荐文章

jQuery中向DOM添加元素的多种方法
2024-11-18 23:19:46 +0800 CST
PHP 压缩包脚本功能说明
2024-11-19 03:35:29 +0800 CST
Golang - 使用 GoFakeIt 生成 Mock 数据
2024-11-18 15:51:22 +0800 CST
使用 Git 制作升级包
2024-11-19 02:19:48 +0800 CST
Python 基于 SSE 实现流式模式
2025-02-16 17:21:01 +0800 CST
程序员茄子在线接单