Hermes 不只是一个 CLI 工具。你可以直接导入 AIAgent,并在你自己的 Python 脚本、Web 应用或自动化流水线中以编程方式使用它。本指南将向你展示如何操作。
直接从仓库安装 Hermes:
pip install git+https://github.com/NousResearch/hermes-agent.git或者使用 uv:
uv pip install git+https://github.com/NousResearch/hermes-agent.git你也可以将其固定在 requirements.txt 中:
hermes-agent @ git+https://github.com/NousResearch/hermes-agent.git使用 Hermes 最简单的方法是 chat() 方法 —— 传入一条消息,得到一个字符串返回:
from run_agent import AIAgent
agent = AIAgent( model="anthropic/claude-sonnet-4", quiet_mode=True,)response = agent.chat("What is the capital of France?")print(response)chat() 会在内部处理完整的对话循环 —— 工具调用、重试,所有内容 —— 并且只返回最终文本响应。
警告
在你自己的代码中嵌入 Hermes 时,请始终设置 quiet_mode=True。如果不设置,Agent 会打印 CLI spinner、进度指示器和其他终端输出,从而弄乱你的应用程序输出。
完整对话控制
Section titled “完整对话控制”如果想对对话进行更多控制,请直接使用 run_conversation()。它会返回一个字典,其中包含完整响应、消息历史和元数据:
agent = AIAgent( model="anthropic/claude-sonnet-4", quiet_mode=True,)
result = agent.run_conversation( user_message="Search for recent Python 3.13 features", task_id="my-task-1",)
print(result["final_response"])print(f"Messages exchanged: {len(result['messages'])}")返回的字典包含:
final_response—— Agent 的最终文本回复messages—— 完整的消息历史(system、user、assistant、工具调用)
(你传入的 task_id 会存储在 Agent 实例上,用于 VM 隔离,但不会在返回字典中回显。)
你也可以传入自定义 system message,用于覆盖该次调用的临时 system prompt:
result = agent.run_conversation( user_message="Explain quicksort", system_message="You are a computer science tutor. Use simple analogies.",)使用 enabled_toolsets 或 disabled_toolsets 控制 Agent 可以访问哪些工具集:
# 只启用 Web 工具(浏览、搜索)agent = AIAgent( model="anthropic/claude-sonnet-4", enabled_toolsets=["web"], quiet_mode=True,)
# 启用除终端访问之外的所有功能agent = AIAgent( model="anthropic/claude-sonnet-4", disabled_toolsets=["terminal"], quiet_mode=True,)通过将消息历史传回,可以在多轮之间保持对话状态:
agent = AIAgent( model="anthropic/claude-sonnet-4", quiet_mode=True,)
# 第一轮result1 = agent.run_conversation("My name is Alice")history = result1["messages"]
# 第二轮 —— agent 会记住上下文result2 = agent.run_conversation( "What's my name?", conversation_history=history,)print(result2["final_response"]) # "Your name is Alice."conversation_history 参数接收上一次结果中的 messages 列表。Agent 会在内部复制它,因此你的原始列表永远不会被修改。
启用轨迹保存,可以以 ShareGPT 格式捕获对话 —— 这对于生成训练数据或调试很有用:
agent = AIAgent( model="anthropic/claude-sonnet-4", save_trajectories=True, quiet_mode=True,)
agent.chat("Write a Python function to sort a list")# 保存到 ShareGPT 格式的 trajectory_samples.jsonl每个对话都会作为单独一行 JSONL 追加写入,这使得从自动化运行中收集数据集变得很容易。
自定义 System Prompts
Section titled “自定义 System Prompts”使用 ephemeral_system_prompt 设置自定义 system prompt,用于引导 Agent 的行为,但不会保存到轨迹文件中(保持训练数据干净):
agent = AIAgent( model="anthropic/claude-sonnet-4", ephemeral_system_prompt="You are a SQL expert. Only answer database questions.", quiet_mode=True,)
response = agent.chat("How do I write a JOIN query?")print(response)这非常适合构建专用 Agent —— 代码审查器、文档编写器、SQL 助手 —— 它们都可以使用相同的底层工具。
要并行运行大量提示词,Hermes 包含 batch_runner.py。它会管理并发的 AIAgent 实例,并提供适当的资源隔离:
python batch_runner.py --input prompts.jsonl --output results.jsonl每个提示词都会获得自己的 task_id 和隔离环境。如果你需要自定义批处理逻辑,可以直接使用 AIAgent 构建:
import concurrent.futuresfrom run_agent import AIAgent
prompts = [ "Explain recursion", "What is a hash table?", "How does garbage collection work?",]
def process_prompt(prompt): # 为每个任务创建一个新的 agent,以保证线程安全 agent = AIAgent( model="anthropic/claude-sonnet-4", quiet_mode=True, skip_memory=True, ) return agent.chat(prompt)
with concurrent.futures.ThreadPoolExecutor(max_workers=3) as executor: results = list(executor.map(process_prompt, prompts))
for prompt, result in zip(prompts, results): print(f"Q: {prompt}\nA: {result}\n")警告
始终为每个线程或任务创建一个新的 AIAgent 实例。Agent 会维护内部状态(对话历史、工具会话、迭代计数器),这些状态不适合在线程之间共享。
FastAPI 端点
Section titled “FastAPI 端点”from fastapi import FastAPIfrom pydantic import BaseModelfrom run_agent import AIAgent
app = FastAPI()
class ChatRequest(BaseModel): message: str model: str = "anthropic/claude-sonnet-4"
@app.post("/chat")async def chat(request: ChatRequest): agent = AIAgent( model=request.model, quiet_mode=True, skip_context_files=True, skip_memory=True, ) response = agent.chat(request.message) return {"response": response}Discord Bot
Section titled “Discord Bot”import discordfrom run_agent import AIAgent
client = discord.Client(intents=discord.Intents.default())
@client.eventasync def on_message(message): if message.author == client.user: return if message.content.startswith("!hermes "): query = message.content[8:] agent = AIAgent( model="anthropic/claude-sonnet-4", quiet_mode=True, skip_context_files=True, skip_memory=True, platform="discord", ) response = agent.chat(query) await message.channel.send(response[:2000])
client.run("YOUR_DISCORD_TOKEN")CI/CD 流水线步骤
Section titled “CI/CD 流水线步骤”#!/usr/bin/env python3"""CI 步骤:自动审查 PR diff。"""import subprocessfrom run_agent import AIAgent
diff = subprocess.check_output(["git", "diff", "main...HEAD"]).decode()
agent = AIAgent( model="anthropic/claude-sonnet-4", quiet_mode=True, skip_context_files=True, skip_memory=True, disabled_toolsets=["terminal", "browser"],)
review = agent.chat( f"Review this PR diff for bugs, security issues, and style problems:\n\n{diff}")print(review)关键构造函数参数
Section titled “关键构造函数参数”| 参数 | 类型 | 默认值 | 描述 |
|---|---|---|---|
model | str | "anthropic/claude-opus-4.6" | OpenRouter 格式的模型 |
quiet_mode | bool | False | 抑制 CLI 输出 |
enabled_toolsets | List[str] | None | 白名单指定工具集 |
disabled_toolsets | List[str] | None | 黑名单指定工具集 |
save_trajectories | bool | False | 将对话保存到 JSONL |
ephemeral_system_prompt | str | None | 自定义 system prompt(不会保存到轨迹中) |
max_iterations | int | 90 | 每次对话的最大工具调用迭代次数 |
skip_context_files | bool | False | 跳过加载 AGENTS.md 文件 |
skip_memory | bool | False | 禁用持久化记忆读写 |
api_key | str | None | API key(回退到环境变量) |
base_url | str | None | 自定义 API 端点 URL |
platform | str | None | 平台提示("discord"、"telegram" 等) |
警告
- 线程安全:每个线程或任务创建一个
AIAgent。不要在并发调用之间共享同一个实例。 - 资源清理:当对话结束时,Agent 会自动清理资源(终端会话、浏览器实例)。如果你在长期运行的进程中使用它,请确保每次对话都能正常完成。
- 迭代限制:默认的
max_iterations=90比较宽松。对于简单问答场景,可以考虑降低它(例如max_iterations=10),以防止工具调用循环失控并控制成本。