Skip to content

feat(agent): 结构化依赖等待、环检测与可恢复唤醒 - #66

Merged
Qiyuanqiii merged 4 commits into
mainfrom
codex/issue-50-structured-dependency-waiting
Aug 15, 2026
Merged

Qiyuanqiii merged 4 commits into
mainfrom
codex/issue-50-structured-dependency-waiting

Conversation

@Qiyuanqiii

Copy link
Copy Markdown
Member

背景

issue #50(父任务 #36):child 生命周期与 waitgraph 已有基础,但缺少完整的"任务 A 等待任务 B"结构化合同、持久唤醒和业务层死锁处理。等待关系此前只有进程内同步 waitgraph(单次调用栈内检测)和 inbox 通知消息,没有持久化的等待边、deadline、唯一唤醒收据;进程在"写 edge → 目标完成 → 提交唤醒"之间崩溃时,等待方可能永久挂起或被重复唤醒,父等子/子反等父/Tool-RAG 反向依赖也没有稳定诊断。

本次改动

  • schema v101:agent_dependency_edges(版本化边:source/target、reason、deadline、generation、failure_policy fail|notify,五态 wait|satisfied|failed|cancelled|expired,open 边按 run+source+target+generation 唯一)、agent_dependency_wakes(每条边至多一张唤醒收据,UNIQUE(edge_id))、agent_dependency_edge_operations(操作键幂等)。
  • 写前图校验(internal/waitgraph 持久图):在写入事务内、基于已持久化的 open 边拒绝自环、两节点环、多节点环、下层运行时(tool/retriever/store/runner)→Agent 反向等待、跨 Run 端点与超过 64 的最长链深度;环映射 CONFLICT、反向等待 POLICY_DENIED、容量 RESOURCE_EXHAUSTED。
  • 恰好一次唤醒与幂等恢复:结算目标、父取消扇出、deadline 过期与崩溃恢复共用同一 settle 事务——先插唯一唤醒收据(回放返回已有收据、绝不二次唤醒),再 CAS 边状态,随后投递依赖通知消息;等待中的 agent 源按既有 wake 语义转 ready,fail 策略下转 failed(带 finished_at)。ReconcileDependencyEdges 以目标终态/run 终态/deadline 决定结局;RunService 终态钩子自动扇出取消。
  • 稳定 deadlock/livelock 诊断:无进展 deadline 过期发出 dependency.deadlock_detected(含边数);同一源 wake→rewait 超过 64 次判定轮询活锁,发出 dependency.livelock_detected 并以稳定 LIVELOCK 错误拒绝新等待;新增 apperror 码 DEADLOCK/LIVELOCK,DetectDependencyStalls 提供只读诊断投影。
  • Activity 折叠展示:Run Activity 新增 dependency kind(七种事件),只显示 source→target 与 reason,绝不透传 raw child output;Web 时间线新增状态标签与图标;OpenAPI kind 枚举与 docs/openapi.json/schema.d.ts 同步。
  • 附带 cherry-pick 已合并的 PR test(analyzer): 宿主机低完整性令牌初始化限制的显式 opt-in 跳过 #65(analyzer 0xc0000142 宿主机限制 opt-in 跳过)以保证本分支全量测试可复现通过。

测试覆盖

  • internal/waitgraph:自环/两节点环/多节点环/反向等待/深度边界/移除恢复插入。
  • internal/store:记录+幂等回放+意图冲突;写前环/跨 Run/非 agent 端点拒绝;satisfied 恰好一次(重放不重复唤醒、通知消息送达);fail/notify 策略传播;取消扇出;deadline 过期 + deadlock 事件;崩溃恢复幂等(目标完成、run 终态扇出后再次 reconcile 零唤醒);轮询活锁诊断;只读 stall 检测不改账本。
  • internal/runactivity:七种依赖事件投影 + raw output 不透传 + 折叠边界。
  • Web:时间线新增依赖 kind/状态(59 文件 235 用例通过)、typecheck、build、check:api。
  • 迁移链:v101 逆迁移 helper 补齐;README schema 时间线审计(101 行)通过。

验证结果

  • go build ./...、go vet ./... 通过。
  • go test -timeout 30m ./...(含 analyzer opt-in)全部通过,无 FAIL。
  • go test -race(waitgraph/domain/store 依赖路径)通过。
  • Web:typecheck、vitest(235 passed)、build 通过;docs/openapi.json 与 web/src/api/schema.d.ts 重新生成且与源码一致。

安全边界与非目标

  • 模型只能提出依赖意图;Go 在写入前验证图、预算、Scope 与 owner。外部 Tool/RAG 结果不能反向调用等待中的同一 Agent(反向等待写入前拒绝)。
  • 不在本 Issue 让模型创建任意 child(feat(agent): 模型驱动的有界 child 调度与总预算复核 #51 消费本合同的 open 边、唤醒收据与诊断投影);不实现分布式跨机器调度;不用 goroutine/thread lock 代替业务依赖图。
  • v1 端点限定为 run 内真实 agent 节点;非 agent 端点与跨 Run 边写入前拒绝。

Closes #50

- 提取 analyzerIsolationHostLimitationSkip 决策函数:仅当 helper 空输出且退出码恰为 0xc0000142(STATUS_DLL_INIT_FAILED)时才考虑跳过
- GitHub-hosted Windows runner 逃生门不变;新增 CYBERAGENT_ANALYZER_ISOLATION_CONFORMANCE_ACCEPT_HOST_LIMITATION=1(仅 _test.go 读取、只接受精确值 1)将同一失败转为带原因的 t.Skip
- 其他退出码/有输出/未显式确认一律保持大声失败,产品权威保持关闭
- 新增决策函数单元测试覆盖 GitHub 逃生门、opt-in 精确匹配与不可放宽条件
- schema v101:agent_dependency_edges(五态 wait|satisfied|failed|cancelled|expired、failure_policy、deadline、generation)+ agent_dependency_wakes(每条边至多一张唯一唤醒收据)+ 操作键幂等表
- internal/waitgraph 新增持久图校验:写前拒绝自环、两节点/多节点环、下层运行时→Agent 反向等待、跨 Run 端点与超 64 深度链
- 结算/父取消扇出/deadline 过期/崩溃恢复共用 settle 事务,回放与并发绝不二次唤醒;等待中的源按 fail|notify 策略转 failed 或唤醒转 ready
- 无进展 deadline 发出 dependency.deadlock_detected;轮询活锁(wake→rewait 超限)以稳定 LIVELOCK 错误拒绝并发事件;新增 DEADLOCK/LIVELOCK apperror 码
- RunService 终态钩子自动扇出取消;Run Activity 新增 dependency 折叠 kind(只显示 source→target 与 reason,不透传 raw child output)
@Qiyuanqiii
Qiyuanqiii merged commit 51f92b4 into main Aug 15, 2026
5 checks passed
@NanaseInori
NanaseInori deleted the codex/issue-50-structured-dependency-waiting branch September 16, 2026 09:09
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

feat(agent): 结构化依赖等待、循环检测与可恢复唤醒

1 participant