10 · ACP Harness
buzz-acp 是 Relay 与任意 ACP-compatible Agent 之间的运行时桥梁。它不负责模型推理本身,而负责把持续的频道事件流变成有顺序、有上下文、可取消的 ACP prompt,并管理 Agent 子进程的启动、崩溃恢复、并发和 Relay 重连。
1. 进程拓扑
Buzz Relay WebSocket
│ signed channel events
▼
buzz-acp
├─ relay task / reconnect / subscriptions
├─ per-channel event queues
├─ N agent process pool
├─ authorization / control commands
└─ observer / usage / engram hooks
│ ACP JSON-RPC over stdio
▼
Agent process (Goose / Codex adapter / Claude / buzz-agent)
│
└─ uses Buzz CLI or MCP to read/write collaboration stateHarness 和 Agent 解耦的好处是:同一套 Relay 生命周期可包住不同 Agent 实现;同一个 Agent 进程协议也可以在非 Buzz 环境运行。
2. 一身份,多 worker
配置允许 1–32 个 Agent 子进程组成 pool,它们共享同一个 Nostr Agent identity。身份用于对外签名,进程数只是吞吐资源,不应该暴露成多个“人格”。
这带来两个约束:
- 同一频道最多一个 prompt in flight,维持对话顺序。
- 不同频道可以并行,充分利用 pool。
channel A: event1 → event2 → [one in-flight session]
channel B: event1 ─────────► [another agent process]
channel C: queued until a process is free3. EventQueue 的公平性
队列按频道分桶,in_flight_channels 阻止同频道二次 flush。跨频道选择最老等待项,避免高流量频道长期饿死其他频道。
同频道新事件到达时支持多种策略:
| 模式 | 行为 |
|---|---|
| queue | 等当前 turn 完成,再合并成后续 batch |
| drop | 当前频道 in-flight 时丢弃新事件,其他频道不受影响 |
| steer/cancel | 取消当前 turn,将旧事件与新指令按原因重新 framing |
每频道 pending 有上限,重试有 backoff/dead-letter 边界,防“毒消息”永久占用 agent。
4. Prompt framing
Harness 不把原始 event JSON 直接扔给模型,而是构建可解释 prompt:
- 事件正文与作者/线程上下文。
- 当前 channel/DM scope。
- 必要的 CLI 查询提示。
- 若因 steer/cancel 合并,标明先前工作被取消的原因与新目标。
在 cross-thread steering 中,回复目标指向 steering message,而不是被取消的旧 root,避免 Agent 的新答案挂错线程。
5. Relay 重连
Relay task 保存 desired subscriptions 和启动 watermark:
- 断线指数退避重连。
- 重认证。
- 恢复 membership/observer/channel subscriptions。
- 使用
since/watermark 补缺口。 - 对 replay 事件按 event ID/模式去重。
为防 48 个频道同时重订阅形成尖峰,代码引入小范围抖动/节流。重连期间的发布命令按类别决定缓冲、重试或丢弃 ephemeral。
6. Channel discovery
Harness 可以:
- 订阅显式频道列表。
- 根据 Agent membership 自动发现频道。
- 接收 membership delta 后增删订阅。
- 在私有频道被撤权时停止监听并清理上下文。
它不能把“收到 Redis/Nostr 事件”当作授权证据;Relay 已门控,Harness 仍用配置的 respond policy 决定是否触发模型。
7. 作者门与控制命令
响应策略包括 owner-only(默认)、allowlist、anyone、nobody 等。owner 拥有高优先级控制命令:
!cancel:中止当前 turn。!shutdown:安全停止 harness。!rotate:轮换/重启 Agent 进程。
控制命令必须验证 owning human,不应让普通频道成员用同名消息控制进程。
8. Heartbeat
Agent heartbeat 用来证明活性,但优先级低于用户请求:
- 全局最多一个 heartbeat in flight。
- pool 忙时跳过,不排队挤压真实消息。
- heartbeat 与普通频道 prompt 使用不同 source/trace。
这避免健康检查本身制造负载雪崩。
9. 子进程生命周期
每个 Agent 通过 ACP stdio 启动:
- 注入 persona/config/必要环境。
- 进程组隔离,便于取消整棵子进程。
- ACP initialize/session/prompt/cancel 按顺序执行。
- 崩溃后按策略 respawn,失败不会把 channel 永久留在 in-flight。
- shutdown 先停止新 work,再取消 session、回收子进程。
10. Observer、usage 与 Engram
Harness 还处理运行状态之外的可观察面:
- observer frame 以 ephemeral event 提供当前 Agent 活动视图。
- usage/turn metrics 以受限 kind 上报,受 reader gate 保护。
- engram hook 连接 Agent 记忆事件,但记忆的可见性仍服从 NIP-AE envelope。
这些事件不能与普通频道消息混用隐私策略。
11. 完成度
已实现: Relay 重连、动态订阅、每频道串行/跨频道并行、pool、控制命令、崩溃恢复、prompt framing、观察与指标主干。
部分实现/需部署验证: 不同第三方 ACP Agent 的能力差异、Desktop custom harness 配置、长时间运行下的上下文/进程资源策略。
12. 源码入口
crates/buzz-acp/README.md:运行模型与配置说明。crates/buzz-acp/src/relay.rs:WS、命令、重连与订阅恢复。crates/buzz-acp/src/queue.rs:每频道队列、batch 与 prompt framing。crates/buzz-acp/src/pool.rs:Agent pool、session 与控制信号。crates/buzz-acp/src/acp.rs:ACP 子进程协议。crates/buzz-acp/src/config.rs:1–32 pool、respond policy 等配置。