最近 coding agent 的一个明显趋势是:大家不再满足于“模型调用一次工具,然后回答”。真正能做复杂任务的 agent,必须能持续推进、验证、修复、恢复,并在该停的时候停。
这就是 Agent Loop 工程。
最表层看,它像一句 while true:不断把同一个目标交给模型,直到完成。但源码看多了会发现,真正难的不是循环本身,而是循环周围的工程边界:
- 目标怎么定义,怎么持久化?
- 模型什么时候应该继续,什么时候应该停?
- 完成是模型自己说了算,还是要测试、review、benchmark、completion audit?
- 一次上下文耗尽后,下一轮如何继承进度?
- 失败、阻塞、预算耗尽、用户打断时,状态怎么收口?
- 多个 worker 并行时,谁分配任务、谁验证、谁合并?
这篇文章调研几个代表项目和机制:
- Codex Goal:Codex 里的长期目标机制。
- Claude Code Goal:Claude Code 的 session 级 goal / completion condition。
jthack/claude-goal:Codex-style/goalfor Claude Code。snarktank/ralph:PRD 驱动的 Ralph 循环。Th0rgal/open-ralph-wiggum:多 coding agent 的 Ralph wrapper。Yeachan-Heo/oh-my-claudecode:team-first multi-agent orchestration。SWE-agent/SWE-agent:面向 GitHub issue / SWE-bench 的 agent loop。OpenHands/OpenHands:应用级 AI software agent runtime。- LangGraph、Temporal、CrewAI、AutoGen:通用 agent loop / workflow 编排框架。
本文的源码快照时间是 2026-06-28。相关项目更新很快,下面的 commit 只作为本文分析基线。
| 项目 | 定位 | Star / Fork | 主语言 | 本文快照 |
|---|---|---|---|---|
| claude-goal | Codex-style /goal for Claude Code | 103 / 13 | Python | cacea1b |
| Ralph | PRD-driven autonomous AI agent loop | 20,658 / 2,023 | TypeScript / Shell | 6c53cb0 |
| Open Ralph Wiggum | Multi-agent CLI loop wrapper | 1,823 / 142 | TypeScript | 7559f26 |
| oh-my-claudecode | Claude Code team runtime | 37,094 / 3,350 | TypeScript | 6c59219 |
| SWE-agent | GitHub issue fixing agent | 19,649 / 2,146 | Python | abd7d69 |
| OpenHands | AI-driven development platform | 78,540 / 9,997 | Python | de4e2eb |
| LangGraph | Build resilient agents | 35,925 / 6,013 | Python | GitHub 状态:2026-06-28 |
| AutoGen | Agentic AI programming framework | 59,306 / 8,939 | Python | GitHub 状态:2026-06-28 |
| CrewAI | Multi-agent orchestration | 54,483 / 7,632 | Python | GitHub 状态:2026-06-28 |
| Temporal | Durable execution substrate | 21,282 / 1,685 | Go | GitHub 状态:2026-06-28 |
01 Agent Loop 工程到底在解决什么?
图 1:Agent Loop 工程的六层结构。循环只是外壳,可靠性来自目标、计划、执行、验证、状态和控制面。
一个最小 agent loop 可以写成:
while not done:
action = model(history, goal)
observation = tools.run(action)
history.append(action, observation)
但真实工程里,这个循环会立刻遇到六类问题。
| 层 | 工程问题 | 常见实现 |
|---|---|---|
| Goal / Objective | 长期目标是什么?完成条件是什么? | /goal、PRD、spec、task list、issue |
| Planner / Task Graph | 大目标怎么拆?依赖如何表达? | PRD JSON、任务图、计划文件、handoff |
| Executor Loop | 每一轮如何调用模型和工具? | action/observation、shell/browser/MCP、sandbox |
| Verifier / Critic | 模型说完成是否可信? | tests、typecheck、review、benchmark、evaluator |
| State / Memory | 下一轮从哪里接着做? | thread、SQLite、JSONL、git history、trajectory |
| Control Plane | 如何暂停、恢复、中止、防 runaway? | budget、max iteration、Stop hook、health、restart |
因此,Agent Loop 工程的重点不是“让模型多跑几轮”,而是把“继续推进”变成一个受控系统。
我更倾向于把它定义为:
Agent Loop 工程是围绕长期目标构建的一套外部控制系统:它把目标、状态、工具、验证和停止条件从模型上下文里抽出来,让 agent 可以跨多轮、跨上下文、跨进程地可靠推进任务。
02 Codex Goal vs Claude Goal:两个原生 goal 的差异
图 2:Codex Goal 更像 thread-scoped 目标账本;Claude Goal 更像 session-scoped completion condition。
Codex 和 Claude Code 都开始提供“Goal”能力,但这两个设计并不完全一样。
2.1 Codex Goal:线程里的长期目标账本
Codex Goal 的关键不是一个传统 CLI 子命令。本地 codex --help 里没有单独的 goal command,它更像交互线程或桌面线程里的长期目标控制能力。
从 Codex 当前暴露给 Agent 的工具接口可以看出它的核心模型:
create_goal(objective, token_budget?):创建长期目标。get_goal():读取当前 goal、状态、预算和使用情况。update_goal(status=complete|blocked):只有目标真正完成或连续阻塞时才能更新。
它的设计重点有几个:
- 目标是 thread-scoped 的:目标绑定在当前线程里,而不是每次 CLI 进程启动时重建。
- 预算是目标的一部分:可以设置 token budget,并跟踪 token / elapsed-time usage。
- 状态有明确语义:complete 代表已达成,blocked 代表连续多轮无法推进,不是“我累了先停”。
- 完成需要真实达成:不能因为预算快用完就标记 complete。
- 阻塞有阈值:同一个 blocking condition 需要重复出现多轮,才算真正 blocked。
这类设计说明 Codex Goal 想解决的不是“模型又说了一句继续”,而是把一个长期任务变成可治理对象:有目标、有预算、有状态、有生命周期。
2.2 Claude Code Goal:Stop 时刻的完成条件判定
Claude Code 的 Goal 更偏 session-scoped。用户设置 goal 后,Claude Code 在模型准备停止时,用一个 completion condition 判断“这个目标是否真的完成”。
从公开说明和社区实现看,Claude Goal 的工程关键点是:
- goal 作用于当前 session。
- Stop hook 会在模型准备停止时触发。
- 系统会用较小/较快模型做 yes/no evaluator。
- 如果 evaluator 判定 goal 未完成,Claude Code 继续运行。
- 如果目标完成,session 才正常停下。
这和 Codex Goal 的差异在于:Claude Goal 更像“停止条件拦截器”,Codex Goal 更像“持久目标账本”。
2.3 为什么这个差异重要?
如果你只是想避免 Claude Code 半途停下,Claude Goal 的 Stop hook 模型很自然:每次停下前检查一下是否达到 goal,没达到就继续。
如果你要做一个跨很多轮、带预算、可暂停/恢复/阻塞判定的任务系统,Codex Goal 的目标账本模型更完整。
一个简单对比:
| 维度 | Codex Goal | Claude Code Goal |
|---|---|---|
| 状态边界 | thread-scoped durable objective | session-scoped completion condition |
| 核心动作 | create / get / update goal | set goal + Stop hook evaluator |
| 预算治理 | token budget / usage 是一等状态 | 更偏 session 行为控制 |
| 完成判断 | Agent 显式 complete,要求真实达成 | Stop 时用 evaluator 判断是否继续 |
| 最适合 | 长线程、长任务、产品化任务跟踪 | 单会话持续执行,避免过早停止 |
03 claude-goal:用 SQLite + Stop hook 复刻 Codex-style /goal
jthack/claude-goal 是一个很好的工程切片:它不实现完整 coding agent,而是专门给 Claude Code 补 /goal。
它安装后做两件事:
- 把
goal/作为 Claude skill symlink 到~/.claude/skills/goal。 - 在
~/.claude/settings.json安装用户级 Claude CodeStophook。
状态存储在:
~/.claude/goal/goals.sqlite
3.1 数据模型
goal/scripts/claude_goal.py 里用 SQLite 建两张表:
| 表 | 作用 |
|---|---|
goals | 当前 session 的目标、状态、预算、时间、metadata |
events | set、pause、resume、complete、stop_continue 等事件 |
goals 里比较关键的字段包括:
session_id:把 goal 绑定到当前 Claude session。objective:目标文本。status:active、paused、budget_limited、complete。token_budget/tokens_used:预算字段,虽然当前 Claude skill 无法可靠拿到 live token。time_used_seconds/active_started_at:本地时间追踪。
它在 session_id() 里做了一个很实际的处理:优先用 CLAUDE_GOAL_SESSION_ID / CLAUDE_SESSION_ID,其次用 TERM_SESSION_ID / ITERM_SESSION_ID,最后才退回 cwd hash。原因是 Claude Code 执行脚本时 cwd 可能漂移,如果只按 cwd 绑定 goal,很容易找不到原来的状态。
3.2 Stop hook 逻辑
当 Claude Code 准备停止时,Stop hook 调用脚本的 hook 模式:
- 找当前 session 的 active goal。
- 如果没有 active goal,允许停止。
- 如果有 active goal,统计
stop_continue事件次数。 - 未超过 runaway guard 时,返回
decision: block。 - block reason 里注入继续执行的 prompt。
默认 runaway guard 是 500 次 Stop-hook continuation。这个数字很大,说明它的目标就是支持长任务,而不是短暂重试。
3.3 完成审计
goal/SKILL.md 要求 /goal complete 前必须做 completion audit:
- 把目标拆成可验证 deliverables。
- 建 prompt-to-artifact checklist。
- 检查文件、命令输出、测试结果、repo state 等真实证据。
- 找出缺失或弱验证项。
- 如果缺失,继续工作。
- 审计通过后才能运行
claude_goal.py complete。
这点很重要。很多 loop 失败的原因是“模型自己觉得做完了”。claude-goal 通过 completion audit 把完成判断从一句自然语言变成证据检查。
3.4 这个项目的价值和边界
claude-goal 的价值在于:用很少代码,把 goal state、Stop hook、状态控制、完成审计串起来。它说明一个可靠 /goal 不一定要重写 agent runtime。
边界也很明显:
- token budget 只是 soft budget,因为 Claude Code skill 拿不到可靠 live token。
- 它没有任务图、worker、验证器、自动测试调度。
- 它把“继续”做好了,但不负责“怎么拆任务”和“怎么并行”。
一句话总结:
claude-goal 是 Goal loop 的最小可用工程实现:SQLite 管目标,Stop hook 管续跑,completion audit 管停机可信度。
04 Ralph:最朴素但有效的外层循环
Ralph 的思路来自 Geoffrey Huntley 的 Ralph Wiggum pattern:不断启动一个新的 agent 实例,让它看同一个目标、当前文件系统和 git 历史,直到输出完成信号。
snarktank/ralph 的 README 说得很直接:
每次 iteration 都是 fresh instance with clean context,记忆通过 git history、
progress.txt和prd.json持久化。
4.1 ralph.sh 的核心循环
ralph.sh 本质上是一个 Bash loop:
- 读取
prd.json和progress.txt。 - 按 max iteration 循环。
- 每轮启动 Amp 或 Claude Code。
- 捕获输出。
- 如果输出包含
<promise>COMPLETE</promise>,退出。 - 否则 sleep 2 秒,进入下一轮。
它的运行形态非常有代表性:
OUTPUT=$(claude --dangerously-skip-permissions --print < "$SCRIPT_DIR/CLAUDE.md" 2>&1 | tee /dev/stderr) || true
if echo "$OUTPUT" | grep -q "<promise>COMPLETE</promise>"; then
exit 0
fi
这个循环简单,但抓住了一个关键事实:对很多 coding agent 来说,最容易坏的是上下文,而不是代码仓库。每轮 fresh context 可以避免模型被前几轮对话污染。真正的记忆放在文件系统里:代码、git commit、progress.txt、prd.json。
4.2 PRD 驱动
Ralph 不建议直接给一个巨大目标,而是先把 PRD 转成 prd.json:
{
"project": "...",
"branchName": "ralph/feature-name",
"userStories": [
{
"id": "US-001",
"title": "...",
"acceptanceCriteria": ["Typecheck passes"],
"priority": 1,
"passes": false
}
]
}
每轮 agent 只处理最高优先级且 passes: false 的 story。完成后:
- 跑 typecheck / tests。
- commit。
- 把 story 标成
passes: true。 - 把经验写进
progress.txt和 AGENTS.md。
这个设计的本质是:Ralph 把大目标拆成一串可以单轮完成的小 story,再用外层循环保证每个 story 得到多次尝试机会。
4.3 Ralph 的优缺点
优点:
- 极轻,不依赖复杂 runtime。
- fresh context 降低长上下文漂移。
- git history 和文件状态是天然 durable memory。
- PRD JSON 让进度可观察。
缺点:
- promise tag 是弱完成信号,依赖 agent 遵守。
- 没有内置强验证器,质量取决于 prompt 和项目测试。
- 单 worker 顺序推进,不适合复杂并行。
- runaway 主要靠 max iteration 控制。
一句话总结:
Ralph 是最小外层循环:重复启动新 agent,把记忆留给 repo,把完成交给 promise tag 和测试。
05 Open Ralph Wiggum:把 Ralph 泛化成多 agent wrapper
Th0rgal/open-ralph-wiggum 是 Ralph pattern 的泛化版本。它支持 Claude Code、Codex、Copilot CLI、Cursor Agent、Qwen Code、OpenCode。
相比 snarktank/ralph,它不再是一个项目内脚本,而是一个独立 CLI。
5.1 核心状态
ralph.ts 里把状态集中存在 .ralph/:
| 文件 | 作用 |
|---|---|
.ralph/ralph-loop.state.json | 当前 loop 的 active state |
.ralph/ralph-history.json | iteration history 和 metrics |
.ralph/ralph-context.md | 中途注入的下一轮 context |
.ralph/ralph-tasks.md | tasks mode 的任务列表 |
.ralph/ralph-questions.json | agent 提问处理 |
.ralph/codex-goal-ledger.jsonl | Codex goal mode 的 durable audit ledger |
这比原始 Ralph 多了两个关键能力:
- 可以从另一个终端
ralph --status观察 loop。 - 可以
ralph --add-context "hint"给下一轮注入指导,不用停止 loop。
5.2 多 agent 适配层
它定义了 AgentConfig:
command:实际二进制,比如claude、codex、opencode。buildArgs():不同 CLI 的参数模板。buildEnv():不同 CLI 的环境变量。parseToolOutput():解析工具调用输出。
例如:
- Claude Code 用
claude -p <prompt> --dangerously-skip-permissions。 - Codex 用
codex exec <prompt> --full-auto。 - Cursor Agent 用
cursor-agent -p ... --force。 - Qwen Code 用
qwen -p ... --yolo。
这说明 Open Ralph Wiggum 的价值不是新的 agent 推理能力,而是把多种 coding agent 的 headless CLI 统一接入同一个 loop harness。
5.3 Codex Goal mode:内外两层 loop
它有一个很有意思的设计:--codex-goal。
README 写得很清楚:Open Ralph 仍然拥有外层 loop,包括 max iterations、process restarts、promise detection、.ralph/ralph-history.json、git/file-system state、auto-commits。每个 Ralph iteration 内部,Codex backend 的最终 prompt 以 /goal 开头,让 Codex Goal 负责单次 session 内的持续推进。
也就是说:
- 外层 Ralph:跨进程、跨 iteration、fresh context。
- 内层 Codex Goal:单个 Codex thread/session 内持续推进。
这是一种很合理的组合:Goal 解决“本轮别停”,Ralph 解决“本轮失败了就重启新上下文继续”。
一句话总结:
Open Ralph Wiggum 把 Ralph 从一个脚本升级成多 agent loop harness,并开始把原生 Goal 能力嵌入每个 iteration。
06 OMC Team:从单循环到阶段化多 Agent Runtime
Ralph 系项目的核心是“重复启动 agent”。oh-my-claudecode 的 team runtime 则进一步:它把 loop 拆成阶段,把执行拆成 worker,把完成拆成 verify/fix。
我之前已经详细调研过 OMC,这里只看它和 Agent Loop 工程相关的部分。
6.1 Team pipeline
skills/team/SKILL.md 定义了 canonical team runtime:
team-plan -> team-prd -> team-exec -> team-verify -> team-fix
每个阶段都有专门 agent:
| 阶段 | 主要 Agent | 作用 |
|---|---|---|
team-plan | explore、planner、architect | 分析代码库,形成任务图 |
team-prd | analyst、critic | 补齐需求和验收边界 |
team-exec | executor、debugger、designer | 实现任务 |
team-verify | verifier、security-reviewer、code-reviewer | 验证和评审 |
team-fix | executor、debugger | 修复验证失败项 |
这里的 loop 不再是简单的“执行失败就重试”,而是:
exec -> verify -> fix -> exec -> verify
直到验证通过,或者达到明确的 failed / blocked terminal state。
6.2 runtime-v2:事件驱动而不是 done.json 轮询
src/team/runtime-v2.ts 注释里写明:它替代 polling watchdog,不再靠 done.json 轮询。完成状态来自:
- CLI API lifecycle transitions。
- event-driven monitor snapshots。
- worker heartbeat/status files。
同时它保留:
- sentinel gate。
- circuit breaker。
- failure sidecars。
- worker heartbeat。
- shutdown request / ack。
- worker commit cadence。
- worktree isolation。
这说明 OMC 要解决的是“团队运行时”问题:worker 会死、会卡、会重复、会冲突,系统必须有健康检查、重启、合并、取消和恢复。
6.3 Goal 与 Team 的关系
OMC 最新文档里明确提到:Team 是并行阶段执行的 authority。如果任务提到 Claude Code /goal、Ralph、UltraQA 或 artifact-only Ultragoal,默认仍然保持 Team 作为 primary loop authority,除非 lead 显式 handoff。
这点很关键。多个 loop 同时存在时,必须明确谁是外层控制器。
否则会出现:
- Goal 觉得还没完成,继续跑。
- Team verifier 觉得失败,要进入 fix。
- Ralph 外层检测不到 promise,又重启一轮。
没有 loop ownership,系统会变成多重自动化互相拉扯。
一句话总结:
OMC 的价值在于把 Agent Loop 从“单 agent 重试”升级成“阶段化、多 worker、可验证、可恢复的团队 runtime”。
07 SWE-agent:标准 action/observation loop 与 trajectory
SWE-agent 是另一类典型:它不是给 Claude/Codex 外面套 loop,而是自己实现一个面向软件工程任务的 agent runtime。
7.1 DefaultAgent loop
sweagent/agent/agents.py 里 DefaultAgent.run() 的结构非常标准:
setup(env, problem_statement, output_dir)。- 触发
on_run_start()hook。 - 初始化
StepOutput()。 while not step_output.done。- 每轮调用
self.step()。 - 每轮保存 trajectory。
- 结束后触发
on_run_done()。
step() 做的事情是:
- 调用
forward_with_handling()获取模型动作。 - 执行动作,得到 observation。
- 把 action/observation 加入 history。
- 更新
info,包括 submission、exit_status、edited files、model_stats。 - 把 step 写入 trajectory。
这是教科书式 agent loop:模型输出 action,环境返回 observation,直到 done。
7.2 SWEEnv:环境是 loop 的一等对象
sweagent/environment/swe_env.py 里,环境负责:
- 启动 deployment,默认 Docker。
- 创建 bash session。
- clone/copy repo。
- reset repository 到 base commit。
- 执行命令并返回 stdout。
- 支持 timeout、interrupt、hard_reset。
这和 Ralph 最大不同是:Ralph 默认信任当前 repo 环境;SWE-agent 把环境封装成一个可重置的对象。对 benchmark、批量评测、issue fixing 来说,这非常重要。
7.3 RetryAgent:多 attempt + reviewer
SWE-agent 还有 RetryAgent:
- 每个 attempt 都 setup 一个新的 sub-agent。
- attempt 失败后 hard reset environment。
- 把每次 attempt 的 trajectory 保存起来。
- reviewer / retry loop 选择是否继续,以及最终选择哪个 attempt。
这已经很接近“tournament / evaluator loop”。它不是盲目重试,而是把每次尝试作为可评审的轨迹保存。
一句话总结:
SWE-agent 的 loop 工程重点是环境可重置、轨迹可审计、attempt 可评审,适合 benchmark 和自动修 issue。
08 OpenHands:应用级 conversation / sandbox runtime
OpenHands 更像完整产品,而不是一个单纯 loop 库。
从最新源码看,应用层 LiveStatusAppConversationService 负责把用户、conversation、sandbox、event callback、pending messages、secrets、LLM profile、workspace、agent settings 等拼起来。它依赖 openhands.sdk 的 Agent、AgentContext、LocalWorkspace、LLM,并通过 sandbox service 管理实际执行环境。
它的 loop 工程重点不是一个文件里的 while,而是完整运行时边界:
- conversation info / start task / pending messages。
- sandbox spec / sandbox status / docker or remote sandbox。
- event service / callback service。
- LLM profile resolution。
- workspace / plugin / tool preset。
- planning agent 与 code agent 的角色边界。
- export / status / title callback / webhook。
OpenHands 这种项目说明,agent loop 一旦产品化,会自然长成“三层结构”:
| 层 | 作用 |
|---|---|
| App Conversation | 用户会话、消息、状态、权限、设置 |
| Agent SDK | 模型、工具、上下文、agent 行为 |
| Sandbox Runtime | 文件系统、shell、环境隔离、执行状态 |
它和 SWE-agent 的区别是:SWE-agent 更像 benchmark/CLI runtime,OpenHands 更像多用户、多会话、可视化的 agent 应用平台。
一句话总结:
OpenHands 的 loop 工程重点是 conversation state、event stream 和 sandbox runtime 的产品化治理。
09 通用框架:LangGraph、Temporal、CrewAI、AutoGen
图 3:不同项目在“轻量 wrapper”到“完整 runtime”、从“重复执行”到“强验证目标”的光谱位置。
除了 coding-agent 专用项目,还有一类通用框架也在解决 loop 工程。
9.1 LangGraph:状态图 + durable execution
LangGraph 的核心不是“自动写代码”,而是把 agent workflow 建成 graph:
- node 表示模型调用、工具调用、验证、人工介入等步骤。
- edge 表示控制流。
- state 在节点之间传递。
- checkpoint / persistence 支持恢复。
- interrupt / human-in-the-loop 支持人工确认。
它适合需要明确状态机的 agent:比如 research agent、客服 agent、审批 agent、多步骤工具 agent。
如果说 Ralph 是“进程级 loop”,LangGraph 是“状态图级 loop”。
9.2 Temporal:durable execution substrate
Temporal 本身不是 agent 框架,但它非常适合作为 agent loop 的底层执行引擎。它解决的是:
- workflow state 持久化。
- activity retry。
- timeout。
- signal。
- long-running workflow。
- crash 后 replay / resume。
Agent loop 一旦进入生产系统,最怕进程挂掉、网络失败、工具超时、人工审批等待几小时。Temporal 的 durable execution 正好补这层。
它的问题是重:你要接受 Temporal server、worker、activity、workflow 的工程模型。
9.3 CrewAI:角色化多 Agent 编排
CrewAI 更偏 role-playing agents 和 task orchestration:
- agent 有 role、goal、backstory。
- task 有 description、expected output。
- crew 负责顺序或层级执行。
- flows 支持事件驱动控制流。
它适合业务流程型 agent,但对 coding agent 的低层执行治理,比如 git、sandbox、trajectory、patch review,不如 SWE-agent / OpenHands 这类专门项目直接。
9.4 AutoGen:多 Agent 对话与终止条件
AutoGen 的重点是 agent conversation:
- 多个 assistant/user/tool agent 互相发消息。
- team / group chat 管理协作。
- termination condition 控制停止。
- 可以插入工具、人工、代码执行。
它适合研究和快速搭多 agent 协作原型。工程化时仍然需要补状态持久化、环境隔离、验证器和部署控制面。
10 横向对比:谁解决了哪一层?
| 项目 / 机制 | Goal 状态 | 外层 loop | 验证闭环 | 状态持久化 | 环境隔离 | 多 Agent | 适合场景 |
|---|---|---|---|---|---|---|---|
| Codex Goal | 强 | 中 | 依赖 Agent 审计 | thread | Codex harness | 可结合 subagent | 长线程目标 |
| Claude Goal | 中 | Stop hook 续跑 | evaluator + session | session | Claude harness | 可结合 teams | 防止过早停止 |
| claude-goal | 中 | Stop hook 续跑 | completion audit | SQLite | Claude harness | 无 | Claude Code 补 /goal |
| Ralph | PRD JSON | 强 | 测试/promise | git + progress + prd | 当前 repo | 无 | 小 story 顺序推进 |
| Open Ralph Wiggum | prompt/tasks | 强 | promise + history | .ralph | 当前 repo | agent rotation | 多 CLI agent wrapper |
| OMC Team | handoff/task | 强 | verify/fix loop | .omc + team state | worktree/tmux | 强 | 多 worker 长任务 |
| SWE-agent | issue/problem | action loop | submission/reviewer | trajectory | Docker/SWE-ReX | retry attempts | benchmark/issue fixing |
| OpenHands | conversation | app runtime | event/callback/tool result | DB/files/event | sandbox | 支持 | 产品级软件 agent |
| LangGraph | graph state | graph loop | 自定义节点 | checkpoint | 外接 | 支持 | 状态机型 agent |
| Temporal | workflow state | workflow retry | activity result | event history | 外接 | 支持 | 生产 durable loop |
11 我对 Agent Loop 工程的判断
11.1 while true 只是原型,不是工程
最原始的 Ralph loop 证明了一个很重要的点:重复运行 agent 确实有效。但一旦任务变复杂,必须补:
- max iteration。
- completion promise。
- task list。
- history。
- status。
- mid-loop context injection。
- auto-commit。
- 验证命令。
否则 loop 只是把一次不可靠调用变成 N 次不可靠调用。
11.2 目标状态必须外部化
Agent 最容易丢的是“我到底在完成什么”。把 goal 放在 prompt 里不够,必须外部化:
- Codex 放在线程 goal state。
- claude-goal 放在 SQLite。
- Ralph 放在
prd.json。 - Open Ralph 放在
.ralph/。 - SWE-agent 放在 problem statement + trajectory。
- OMC 放在 team task/handoff/state。
- LangGraph/Temporal 放在 graph/workflow state。
这是 Agent Loop 工程的第一原则:目标不能只活在模型上下文里。
11.3 完成判定不能只听模型自报
Completion promise 很方便,但它是弱信号。更可靠的完成判定通常需要组合:
- 模型自报:
<promise>COMPLETE</promise>。 - 静态检查:typecheck、lint。
- 动态测试:unit/integration/e2e。
- 人工或模型 reviewer。
- benchmark score。
- artifact checklist。
- repo state / diff / CI。
Claude Goal 的 evaluator、claude-goal 的 completion audit、SWE-agent 的 reviewer、OMC 的 verify/fix loop,本质上都在解决这个问题。
11.4 要明确谁拥有外层 loop
当多个 loop 叠在一起时,必须明确 loop ownership:
- Ralph 外层 + Codex Goal 内层:合理。
- OMC Team 外层 + Claude Goal 内层:需要明确 handoff。
- LangGraph 外层 + agent CLI 内层:要约束 CLI 的停止条件。
- Temporal 外层 + LangGraph 内层:Temporal 管 durable retry,LangGraph 管 agent state。
如果没有这个边界,系统会出现重复重试、状态打架、预算失控、worker 无法停止。
11.5 生产级 loop 一定需要控制面
能长期跑的 agent loop,最终都会长出控制面:
- pause / resume / cancel。
- status / history / metrics。
- budget / timeout / max retry。
- health / heartbeat / restart。
- sandbox / permission。
- audit log / trajectory。
- notification / callback。
这也是为什么 OpenHands、OMC、Temporal 这类项目看起来“重”:它们不是在堆功能,而是在补生产化必需的控制边界。
12 选型建议
如果只是个人用 Claude Code / Codex 做长任务,我会这样选:
| 需求 | 推荐 |
|---|---|
| 想让当前会话别半途停 | Claude Goal 或 Codex Goal |
Claude Code 想要 Codex-style /goal | claude-goal |
| 想把一个大 PRD 拆成小 story 自动跑 | Ralph |
| 想在 Claude/Codex/Cursor/Qwen/OpenCode 间切换 loop | Open Ralph Wiggum |
| 想要多 worker 并行、verify/fix、handoff | OMC Team |
| 想做 SWE-bench / issue fixing / 可复现实验 | SWE-agent |
| 想做产品级 Web IDE / 多用户软件 agent | OpenHands |
| 想把 agent workflow 做成状态图 | LangGraph |
| 想把 agent loop 跑进生产系统 | Temporal |
我的建议是不要一开始就选最重的。
最实用的演进路径是:
- Goal 层:先用 Codex Goal / Claude Goal 解决“别停太早”。
- 任务层:复杂后用 PRD / task list / spec 把目标拆小。
- 验证层:加 typecheck、tests、review、completion audit。
- 外层 loop:需要跨上下文时引入 Ralph。
- 团队层:需要并行 worker 时引入 OMC Team。
- 平台层:需要多用户、sandbox、事件流、生产恢复时,考虑 OpenHands / LangGraph / Temporal。
13 总结
Agent Loop 工程已经从“写一个 while true”演进成一套完整 harness。
不同项目解决的是不同层:
- Codex Goal 和 Claude Goal 解决 goal-scoped continuation。
- claude-goal 证明 SQLite + Stop hook 可以实现最小持久目标。
- Ralph 证明 fresh context + repo state 是非常有效的外层循环。
- Open Ralph Wiggum 把这种循环泛化到多种 coding agent。
- OMC 把 loop 做成 team runtime。
- SWE-agent 把 loop 做成可评测、可重置、可审计的 issue fixing harness。
- OpenHands 把 loop 做成应用级 conversation/sandbox runtime。
- LangGraph / Temporal / CrewAI / AutoGen 则提供更通用的工作流和多 Agent 编排基础。
最终判断一个 Agent Loop 项目好不好,不是看它能不能“自动继续”,而是看它有没有回答六个问题:
- 目标在哪里?
- 状态在哪里?
- 谁决定继续?
- 谁证明完成?
- 失败怎么恢复?
- 谁拥有外层控制权?
这六个问题回答清楚了,loop 才是工程;回答不清楚,就只是模型在原地反复尝试。