Skip to content

fix(chat): honor the configured steward across default entrypoints - #8677

Open
huangruiteng wants to merge 1 commit into
mainfrom
codex/steward-shared-conversation-20261113
Open

huangruiteng wants to merge 1 commit into
mainfrom
codex/steward-shared-conversation-20261113

Conversation

@huangruiteng

@huangruiteng huangruiteng commented Nov 13, 2026 •

Copy link
Copy Markdown
Collaborator

Goal And Delivered Outcome

配置飞书原管家作为 App 默认来源后,前端会遵守选择,但直接调用 POST /api/chat/sessions 的 manager 入口仍会打开独立本机管家。另一个问题是:机器人身份正常、本人登录缺失时,界面只报“会话不可用”,无法指出恢复步骤。

本改动让默认 API 入口复用现有 Core 选择与原 Session。来源不可用时拒绝创建替代会话;新会话或不同模型的覆盖也不能绕过所选来源。本人登录缺失通过具体错误投影到聊天入口和概览输入框,恢复登录后继续原会话。已明确指定的历史 Session、未选择来源的本机入口及群授权规则保持原有边界。

  • Outcome basis: reproduced entrypoint inconsistency; app-conversation-and-async-inbox-v0 original-conversation contract.
  • Intended base: main at eba8a7f95f54fe09cb3dcc28bb1f55443898bbed.

Author Declaration

  • Written by: model_agent, Codex (OpenAI).
  • Specification: docs/architecture/rfcs/app-conversation-and-async-inbox-v0.md at the base above; bilingual clarification included.
Criterion Disposition Owner / evidence
Selected source must not fall back to a separate conversation implemented open_chat_session reuses app_steward_target; real HTTP/Core smoke
Identity recovery retains original Session and source verification implemented typed provider error, same-Session recovery and revocation tests
No lookup-triggered execution or transcript replay implemented session/message/native-request invariants; original-chat delivery regression

Scope And Continuation

Complete for default-entry consistency and actionable owner-login reporting. Account authorization remains with the original owner; this PR does not add an OAuth UI or migrate historical local conversations. No automatic selection among multiple configured stewards is introduced. The existing explicit App source configuration remains authoritative.

Bounded refactoring: reuse the existing typed source resolver and share the two UI failure messages. The provider error is an HTTP presentation distinction, not a new authorization state or a second decision owner.

Validation

  • Tested revision: f8287cd14f (same source bytes tested before commit).
  • Run state: finished. Inputs: synthetic.
Check kind Result Evidence / limitation
integration / real_backend passed npm run smoke:app-steward: real HTTP/Core and isolated SQLite; default API reuse, owner-login recovery, stale/revoked source refusal, override refusal, explicit clear, no new model work
unit / integration passed 76 focused model/adoption/conversation checks; 8 original-App projection and identity checks
static passed npm run build:chat including TypeScript; Ruff, diff check, bilingual RFC gate
manual passed Packaged UI with real owning backend and synthetic providers: owner-login failure, settings navigation, recovered original transcript; desktop and narrow views
static failed uv run --extra test python -m mypy: the same no-any-return at unchanged loopx/capabilities/decision_context/runtime.py:207 reproduces on both base eba8a7f95f and head f8287cd14f. CI kernel-contracts is therefore not green; no waiver or merge readiness is claimed.
static passed Public-boundary scan: all 12 changed files clean. The broader local registry check reports unrelated legacy-route failures, so it is not claimed as an overall installation-health pass.

The first smoke attempt lacked the built Chat bundle; after building, a test incorrectly expected an existing local manager in a fixture that had none. Corrected that fixture expectation; the final smoke passed. Production provider delivery and OAuth are not established by these synthetic tests. No PostgreSQL or authority-store semantics change.

Frontend / Visual Evidence

UI impact: changed. The primary question is why a configured conversation cannot open. The existing recovery layout now gives the exact owner-login cause and preserves retry/settings actions; no new panels or repeated help blocks. The recovered transcript remains in its original bound route.

All attachments use synthetic state. Before: packaged 185e1e34cc generic source failure (same pre-change entry UI as main). After: packaged f8287cd14f owner-login failure, desktop and narrow. Existing layout and controls remain; no public live-data capture is included.

Before

owner-login-before-synthetic

After

owner-login-recovery-desktop owner-login-recovery-mobile

Type of Change

  • Bug fix
  • Documentation update
  • Test update

LoopX Area

  • Capability or extension
  • Public docs or presentation surface
  • Host or runtime integration

Shared-authority RFC fixture impact

N/A: reuses the existing Core resolver; no storage promotion or new authority semantics.

Boundary Checklist

  • No private state, credentials, raw traces, internal links or local machine paths in the diff or publication.
  • Scope stays within the demonstrated conversation defect.
  • Both RFC languages updated; bilingual check passed.
  • Public-safe first-screen evidence included.
  • Signed-off-by trailer present. No merge authorization claimed.

Signed-off-by: huangruiteng <huangrt01@163.com>

@loopx-agent loopx-agent left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Reviewer: model_agent · gpt-6.1-sol · OpenAI · runtime_reported · reasoning_effort=max

评审提交 f8287cd。GitHub 目标与 merge base 为 eba8a7f,本轮读取的最新主干 7bb1b01 未改动这组变更路径。

[P2] 关闭与打开并发时,默认入口把已关闭会话报为恢复成功。 默认 manager POST 刚完成所选来源核验时,另一请求用现有 DELETE 入口关闭该空闲 Session,再让 POST 继续读取。 DELETE 已成功,候选仍返回 HTTP 200、resumed=true、status=closed、resumable=false。随后的发现 GET 返回 409,新的默认 POST 返回 400。 问题位置

动机 / Motivation

已把飞书原管家设为默认入口,想在 App 或本机 API 继续同一段对话的用户。 在基线,App 会继续飞书里的原记录,但走默认本机接口会打开另一段对话。本人登录失效时,界面只给出通用的不可用提示。 候选在正常情况下让两个入口打开同一个已验证的原会话。登录缺失时显示同一应用的重新登录指引,恢复后按重试即可回到原记录。 打包 Chat 使用合成身份和真实本地 HTTP、Core 与隔离 SQLite。实际飞书 OAuth、已安装 App 和独立概览交互仍待对应入口验证。

改动思路 / Approach

Core 仍拥有显式来源选择和原 Session 的授权。Python HTTP 接入复用该结果,前端展示登录原因和恢复路径。 沿用已核验的绑定会话结果,收拢候选新增的第二次读取,使两个默认入口共享同一可用性结论。 所选来源稳定时,默认 POST 可直接复用原 Session。发现失败时仍由原设置和重试入口处理。 绑定解析器

具体改动 / Changes

关键代码讲解

默认 POST 在 open_chat_session 中取得绑定与 Session ID,随后重读该 Session。这个新分支只判空。飞书适配器在应用身份已验证但本人登录缺失时发出类型化错误,GET 用 error_code 把原因交给两个页面入口。 默认打开 登录错误投影 前端读取

按 docs/architecture/rfcs/app-conversation-and-async-inbox-v0.md 在 eba8a7f 的既有约束,原会话可用性仍有上述缺口。默认入口隔离已通过基线和候选的对照。登录恢复在打包页面验证通过。 已接受的验收依据

对主干的风险 / Risks

基线发现入口认得所选原会话,默认 manager POST 仍继续本机管家。 在同一套隔离 HTTP fixture 中,未选来源时两版都正常创建本机 Session。候选正常打开原 Session 时返回 ready。仅在实际关闭夹在两次读取间时,已关闭对象才被成功返回。 让默认入口从既有绑定解析器返回同一份经过校验的可用 Session,并在返回前拒绝已关闭或身份、选择已变化的结果。 扩展现有 HTTP/Core smoke,在发现和返回之间并发关闭原 Session,断言默认入口拒绝且保留历史,再核正常打开、恢复和显式清除。

语义与 CI 对齐

Chat 构建、现有 app-steward HTTP smoke、95 项身份与来源定向测试和独立浏览器重试通过。Standard premerge 六项直接检查、13 项选中检查均通过。 托管 CI 未查询。

我的整体评价 / Verdict

请求修改。默认入口复用正确,先把一次解析和成功返回之间的 Session 可用性对齐。 1200 × 900 和 390 × 900 的登录提示、重试和设置入口均在首屏,发送控件隐藏。重试回到含 14 条中英混合消息的原会话,两种宽度下正文可换行,输入区保留在下方。 打包 Chat 使用合成身份和真实本地 HTTP、Core 与隔离 SQLite。实际飞书 OAuth、已安装 App 和独立概览交互仍待对应入口验证。

English verdict: REQUEST_CHANGES. On f8287cd, the default manager POST can return resumed=true for a Session that the public close route has already closed.

if target["binding_id"] is not None:
if mode != "resume_latest":
raise ValueError("Continue the selected original steward conversation; start a new conversation from its original source.")
session = controller.store.load_session(target["session_id"])

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

[P2] 关闭与打开并发时,默认入口把已关闭会话报为恢复成功。 默认 manager POST 刚完成所选来源核验时,另一请求用现有 DELETE 入口关闭该空闲 Session,再让 POST 继续读取。 DELETE 已成功,候选仍返回 HTTP 200、resumed=true、status=closed、resumable=false。随后的发现 GET 返回 409,新的默认 POST 返回 400。 让默认入口从既有绑定解析器返回同一份经过校验的可用 Session,并在返回前拒绝已关闭或身份、选择已变化的结果。 扩展现有 HTTP/Core smoke,在发现和返回之间并发关闭原 Session,断言默认入口拒绝且保留历史,再核正常打开、恢复和显式清除。

This branch has not been deployed

No deployments
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.

2 participants