fix: review follow-ups for the session archive set

- WorkspaceRegistry.archiveSession no longer wraps persistence-listing
  failures as WorkspaceUnknownSessionError: only a definite miss (live
  lookup, header index, then a fresh list) maps to session-not-found;
  storage faults propagate as internal errors, with a negative test.
- The archived-current sweep moves from the unary path into the
  projection: any install path (local echo, another tab's frame, a
  reconnect baseline) clears a selection that landed in the archive set.
- An archive set installed while workspace.list is in flight supersedes
  the stale baseline's set instead of being rolled back by it.
- The workspace-management e2e anchors the archived row by its session
  actions button and asserts the single-stray fixture assumption loudly.
- Drop the stale touchSession rows from the workspace READMEs (the
  method was removed with its Agent Note).
This commit is contained in:
imccyu
2026-07-31 03:44:35 +08:00
committed by imccyu
parent c00f0dccda
commit d3e8f17a54
15 changed files with 103 additions and 26 deletions
@@ -15,7 +15,7 @@ Sidebar workspace 浏览区的 session 行菜单里,「Delete session」一直
- 存储:`archivedSessionIds: z.array(sessionId).default([])`,domain version 保持 2——纯增量字段,旧介质经 schema default 解析为空集合,无迁移代码。被归档的 session 保留其 `sessionIds` 席位(未来取消归档恢复原位置),因此与「一个 session 只被一个 workspace 记账」不变式零纠缠。
- Registry:`ctx.workspace.archiveSession(id)` 走 `enqueueOperation` 与 create/delete 串行;未知 session(实时与持久化都查不到)抛 `WorkspaceUnknownSessionError`;已归档 id 不写盘不发事件。`archivedSessionIds` getter 暴露只读集合。
- RPC:`workspace.archiveSession({sessionId}) → {archivedSessionIds}`(应答完整更新后集合);`workspace.list` 响应携带集合作为重连基线;新 host 帧 `host/archived-sessions-changed` 在每次持久变更后推完整快照(与 `host/workspace-changed` 同姿态,从 `domain/changed` 的 global put 分支比对推帧)。未知 session 复用错误码 `session-not-found`。
- client runtime:`WorkspaceListState.archivedSessionIds`(`ReadonlySet`,成员不变不换引用);list 基线、unary 回声、changed 帧三路都整体替换安装。`WorkspacesService.archiveSession` 在归档对象恰为当前 selection 时调 `sessions.clear()` 回 New Session 视图(用户拍板:归档当前打开的 session 主视图回 hero)。
- client runtime:`WorkspaceListState.archivedSessionIds`(`ReadonlySet`,成员不变不换引用);list 基线、unary 回声、changed 帧三路都整体替换安装。投影层在当前 selection 落入归档集合时统一清空回 New Session 视图(用户拍板:归档当前打开的 session 主视图回 hero)——一条规则同时覆盖本地 unary 回声、其他标签页的 changed 帧、以及重连基线恢复出一个离线期间被归档的 selection;帧/回声落在 in-flight `workspace.list` 期间时还会屏蔽旧基线对新集合的回滚。
- UI:菜单项 `delete`(visual-only)改为 `archive`(label「Archive session」,非 danger 样式,无确认对话框——非破坏性操作,误触后果只是列表隐藏);过滤实现为 `tree.ts` 的 `sessionVisible` 判据加一档,`deriveGroups`/`deriveFlat` 增加 `archived` 集合入参,四个视图(分组循环、stray 兜底、搜索、平铺)同源生效。
## 已考虑的替代方案