Skip to content

fix(collaboration): prepare return routes before publishing requests - #5234

Merged
huangruiteng merged 1 commit into
mainfrom
codex/steward-authorized-handoff
Sep 28, 2026
Merged

huangruiteng merged 1 commit into
mainfrom
codex/steward-authorized-handoff

Conversation

@huangruiteng

Copy link
Copy Markdown
Collaborator

Problem and result

A receiver could see a Chat handoff before its original-conversation return route existed. A route write failure or an immediate receiver response then left accepted work unable to return, even though the sender had already published it.

Prepare and verify the existing trusted route inside the request lock before publishing the inbox entry. Failed preparation exposes no work; an interrupted entry write can be retried with the same identity. App steward, Goal Chat and external-audience ingress share this path. Permissions, request identity, receiver planning and return-state transitions remain unchanged.

Validation and scope

  • Reproduced the publication defect before the fix: 9 failing regression cases, 3 passing controls.
  • Final targeted suite: 103 passed, including 18 new real-filesystem cases covering route write/readback failure, immediate receiver results, lost acknowledgement, conflicting destination, exact retry and original App transcript return after restart without another model turn.
  • Ruff, diff checks and public-boundary scan passed. No live group messages, model calls or active Goal mutations were used for qualification.
  • Exact-scope change-quality receipt verified. Premerge result is recorded in the review below.

Placement/future-facing review: this is filesystem IO ordering in the existing Python adapter; it follows the peer request's route-before-entry sequence and creates no second TypeScript state owner or new queue. Existing App/Lark renderers consume unchanged receipts and results, so no frontend bundle change is needed. The RFC records this R3 return-path invariant; native owner selection/execution and the complete A24 journey remain unqualified.

Integration note: #5106 changes these same persistence functions for GoalRef. Preserve route preparation before entry publication in both its legacy and exact-identity paths when integrating these changes.

Signed-off-by: huangruiteng <14976749+huangruiteng@users.noreply.github.com>
@huangruiteng

Copy link
Copy Markdown
Collaborator Author

Validation for head 9e0925a44697907aebef4f1bdf04e35cfe1392b6 against 440a19aab2b69dc23748bb734fa58f2a53e2872f:

  • 103 targeted tests passed; 18 new regression cases use the actual file stores and original-transcript return pump. They inject publication faults and an immediate receiver response, rather than launching live workers or contacting a group.
  • Standard premerge passed: 5 direct checks, 9 catalog checks and 8 risk-profile smokes; no failed, skipped or timed-out checks. Ruff and the public-boundary scan also passed.
  • Exact change-quality receipt: cqr_36738622d465f1f86d81, fingerprint 36738622d465f1f86d813ad812595bfae86ceac3819c2969032f9ee42dc04689.

Author review checked unchanged authorization and immutable ingress identity, request-lock/route-lock ordering, inert route-only recovery, readback before receiver visibility, and once-only original-conversation return. The bounded future-facing pass reuses the peer publication ordering without adding a queue or decision owner. This qualifies a return-path defect, not native owner selection or complete multi-Agent acceptance. No deployment or merge performed; maintainer review remains required. #5106 should carry this invariant into its exact-GoalRef path during integration.

@huangruiteng huangruiteng left a comment

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Approval conclusion (author-owned PR; GitHub blocks formal self-approval)

English verdict: APPROVE - exact head 9e0925a44697907aebef4f1bdf04e35cfe1392b6, immutable base 440a19aab2b69dc23748bb734fa58f2a53e2872f. No blocking finding. The publication/return-preparation defect is reproduced on the base and fixed on this head; full native worker execution and A24 are not certified. This author-owned record is a COMMENTED review, not a formal GitHub self-approval or merge authorization.

动机

这个问题不是“测试少了一项”,而是接收方可能在请求刚发布、发送方还没拿到 receipt 时执行并返回结果,却找不到原会话的回程路由。回程存储失败也可能留下已经可见的工作。独立进程在发布瞬间读取并 report 的对照验证复现了旧问题,所以这是 R3/A8/A9 的实际可靠性增量;不是完整 A24 已完成。

改动思路

复用现有 register、Inbox 原子写入和锁,把路由准备及回读放在 entry 发布之前。请求身份、来源授权和冲突判断都保留;route-only 记录不代表已交办,entry 才是工作可见的边界。原始 session/client turn/channel 来自可信 Chat/provider 状态,不能从接收 Goal 或 source digest 猜一个返回目的地。这里没有新增手填声明、协议版本或 Python 决策源,TypeScript 仍拥有请求规范化与回程状态规则。

具体改动

关键代码讲解

  1. deliver:入口先验证 source/recipient,再在现有 entry lock 内做 identity conflict 检查、register 和 entry 写入。之前先发布 entry、后登记路由;现在路由写入或回读失败时,没有工作被发布。成功 receipt 的字段及“不改优先级、不创建 Todo、不打断执行”保持不变。
  2. register:路由锁内继续校验旧 identity,新增保存后对七个原有稳定字段的精确回读。不是只检查文件存在,也不会把空/错误路由当作成功。entry 写失败留下的准备记录可由同 identity 的 retry 完成,不产生第二份工作。
  3. report:未改动的真实结果消费者先读 exact entry/route,再经共享 Inbox 保存结果。发布瞬间的独立接收进程现在能走通这个入口;初始 receipt 完成后,原 App/Goal Chat transcript 经两次 fresh-store drain 只出现一次结论,不需要第二次模型 Turn。external 仍明确为 queued,测试没有发送真实群消息。

整份 diff 是生产代码 +9/-2、164 行聚焦测试及 12 行规范说明。活跃生产调用是 ChatRunner._run_turn 的 context_handoff;没有新 frontend 配置或 receipt 字段,所以无需配套 UI 改动。现有 Chat/Lark 消费测试已验证,实际打包部署和 live transport 不在本次验收内。

对主干的风险

重点检查了相反两个方向:路由不完整不能放行,但一个坏 route 也不能永久阻断同 Goal 的其他合法请求。route/entry IO 失败、lost ACK、错误目的地、缺失回读、exact retry、新请求、历史 route annotation、completed replay 均有覆盖。23 个无关记录超过 pending 页面上限、顺逆创建顺序及 later-page 读取,也没有改变 exact 请求的交付与回程。entry→route 的嵌套锁没有发现反向锁依赖,真实接收进程在发送方尚未返回时可以完成 report。

独立验证结果:

  • 9 个现有/新增集成文件:129 passed,覆盖 Manager、Goal Chat、peer、Chat 和 Lark return 消费边界。
  • 相同 30-case 发布/恢复 fixture:base 为 21 个预期 invariant failure、9 个合法 control passed;head 全部 30 passed。另有 6 个分页/顺序 control 在两边均通过。
  • 14 个完整可观察结果对照:授权/关闭授权、正常输入、重复请求、历史 annotation、错误全文、拒绝优先级及全部持久 JSON 均一致;只归一化时间戳和合成 runtime 根路径。fixture fingerprint 为 2657adfccfd198d95c2983e258c4a082d4874a6f533683873661a1358cc5e736,base/head observation 均为 9ed1b957d02107e5b0400443eb4cbb5fc7c83acbb3ed0508abe0864d77ec41c7。
  • Ruff、2 个 typed return 测试、最终 premerge 的 5 个 direct + 9 个 catalog + 8 个 risk-profile + 1 个 public-boundary check 全通过,零失败/手动 hold。exact-scope 凭证 cqr_36738622d465f1f86d81 已回读有效。初次 semantic scan 因独立 worktree 未安装 TypeScript 依赖失败,按仓库要求执行 npm ci --ignore-scripts 后,base/head 均通过。

语义与 CI 对齐

没有读取、轮询或等待远端 CI。以上结论来自 exact-head 本地验证;没有改预算或把环境失败归咎于 PR。此次是已有交付路径的默认 IO 顺序修复,不新增 opt-in;external policy 关闭时仍保持原拒绝、提示和无 entry/route 的状态。没有新增子串状态分类、领域特定义务或更宽的 actor/lease authority。RFC 将“发布前回读”写成强制不变量,也明确它不证明 native selection/execution/full A24。

我的整体评价

APPROVE,无阻塞发现。长期运行与用户体验在这个边界得到实际改善:可见工作能保留原会话的结果返回能力,失败后的同 identity 重试不新增请求;正常成功、关闭授权和历史读回契约保持完整对照一致。成本是 entry 写失败可能留一份 inert route,retry 可复用;没有后台执行或重复投递,全局清理仍由原生命周期边界承担。

future-facing pass 的结论是复用现有 publisher/route owner 即可,不加 manager/peer 参数化框架。历史格式仍需读回,不应为了删代码丢掉旧请求;也无需保留一个新的平行版本。#5106 的 GoalRef 集成必须把同样顺序和回读带入 exact 与 legacy 两条 persist_entry 分支,这不是本 PR 的阻塞项。完整 R3/A24、真实部署和 GoalRef migration 仍保留原验收边界;控制面代码留给维护者合并,本次不会自合并。

@huangruiteng

Copy link
Copy Markdown
Collaborator Author

Frame-aligned conclusion — 9e0925a44697907aebef4f1bdf04e35cfe1392b6

对照作者验证记录以及 Accepted capable-manager semantic handoff RFC 的 request/return 路由边界,本次独立确认:可见请求先具备经过 readback 的 return route,再发布 entry;fresh-process receiver 在父进程尚未返回 receipt 时即可 report。冲突、失败、精确重试、历史 annotation、分页和 default-off 拒绝路径已验证;129 个原生测试通过,独立 30-case 对比为 head 全通过、基线 21 个预期失败,14-case 全部状态观察保持基线/head 一致。最终风险型 premerge 集通过。

这是准备/发布顺序的完整可逆修复,不是整个 R3/A24 的 native-worker、真实部署或 live transport 交付证明;这些验收仍保留原 owner 与后续边界。后续集成 #5106 时,其新 GoalRef 与 legacy 两条发布分支都必须保留这里的 route-before-entry/readback 顺序。future-facing pass 已检查现有 typed normalization、return delivery 与文件适配层的归属,复用现有 owner,不建立第二套决策源。

English verdict: APPROVE - the exact-head preparation/publication invariant is independently qualified; broader A24 and the GoalRef companion integration remain separate acceptance boundaries. Published author-owned approval review.

@huangruiteng
huangruiteng merged commit 00be577 into main Sep 28, 2026
29 of 33 checks passed
@huangruiteng
huangruiteng deleted the codex/steward-authorized-handoff branch September 28, 2026 03:35
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.

1 participant