Skip to content

getMetaItemLayered 的 overlay 读用裸 catch:sys_metadata 读失败时三层视图把「读不到」画成「没有 overlay」 #5707

Description

@os-zhuang

做 #5532(getMetaItem overlay 读把 outage 吞成 miss)时,在同一个文件里发现的第三处同族点。不在那单范围内(#5532 / PR #5705 的文件面限定为 getMetaItems / getMetaItem 的四处 overlay 读 + getMetaItemCached 终末错误),按 Prime Directive #10 单独记在这里,unassigned。

标 finding:这条今天不会让用户拿到错误的判定,只会让 Studio 的三层对比视图少画一层 —— 属于展示失真而非安全或数据后果。分级请以 PM 的分诊为准,我不自评严重度。

位置

packages/metadata-protocol/src/protocol.ts,getMetaItemLayered(以内容定位:注释 // ── overlay layer: sys_metadata row (org-scoped wins, then env-wide) ── 之后的 try):

        } catch {
            // DB unavailable — overlay stays null
        }

        const effective: unknown | null = overlay ?? code;

现象

getMetaItemLayered 是 Phase 3a 的分层读:分别返回 code(artifact 基线)、overlay(per-org / env 的 sys_metadata 行)与 effective。sys_metadata 读失败时 overlay 保持 null,于是:

  • overlay 报告为「这一项没有任何定制」——实际是「定制读不到」;
  • overlayScope 保持 null;
  • effective 退化成 code,即把 artifact 基线当成生效值呈现。

Studio 的「code / overlay / effective」对比正是给作者看「我改过什么」的。故障期它会告诉作者「你什么都没改过,当前生效的就是打包件原样」——和 #5532 同一个错误结论(可用性故障被讲成「你没声明」),只是落在 diff 视图而不是 404 上。

与 #5532 的区别

#5532(PR #5705)修的是 getMetaItems / getMetaItem 的四处 overlay 读;getMetaItemLayered 是另一个方法、另一条读,PR #5705 刻意没有扩到它(scope = the issue)。ADR-0110 D3 的规矩相同。

建议修法(与 PR #5705 对齐,不代裁决)

PR #5705 已在同文件引入 rethrowUnlessMetadataStoreUnprovisioned:isMissingTableError(表还没建 → 确实没有 overlay 行 → null 是真相)良性放行,其余抛 status: 503 / code: SERVICE_UNAVAILABLE,驱动错误挂 cause。这里复用同一个私有方法即可,一处 catch。

另一种可能更贴合这个方法契约的方向:分层读返回的是诊断形状,所以也可以给 overlay 增加一个「未知 / 读失败」的第三态,而不是让整个请求 503 —— 但那是新的返回形状,需要维护者拍板,别在实现时自行选。

未验证:调用方(Studio 的哪个面板、有没有别的消费者)对 overlay: null 的具体渲染,以及 503 化会不会让某个面板整体空白。开工时应先测量再决定上面两条哪一条。

关联

#5532 / PR #5705(同文件同家族)、#5706(getEffectiveLock 的 fail-open,同家族的写侧)、ADR-0110 D3、#5108。


Generated by Claude Code

Activity

  1. os-zhuang commented on Aug 6, 2026

    @os-zhuang
    ContributorAuthor

    发现分诊(finding 轮):持有,补域 domain:engine-core(落点同 packages/metadata-protocol/src/protocol.ts)。

    本评论来自分诊座位 Routine(#5474 试点),不构成认领。


    Generated by Claude Code

  2. os-zhuang commented on Aug 6, 2026

    @os-zhuang
    ContributorAuthor

    发现分诊(#4949 纪律):重启条件已触发,晋级 —— 摘 finding 换 pm:queue,domain:engine-core 已在(落点 packages/metadata-protocol)。

    依据:重启条件 = PR #5705(#5532)落地,已于 2026-08-06 02:18Z 合入。该 PR 的「范围外发现」段明确点名本单(getMetaItemLayered overlay 裸 catch),且新 helper rethrowUnlessMetadataStoreUnprovisioned 已在同文件可复用。认领方第一步是前次持有评论要求的测量:layered 视图故障时的展示失真面(谁消费三层视图、故障被画成「没有 overlay」的可见后果),测完再在「复用 helper 上报 503」与其他修向间取舍 —— 测量结论写进 PR 正文。⚠️ 同文件串行:#5706(getEffectiveLock fail-open,restore-invariant 向,其 Blocked-by: #5532 已随 PR #5705 合入而解除,待车道 sweep 回队)与本单同落 protocol.ts,engine-core 车道派发时二者跨轮串行,建议 #5706(安全闸门)先行。

    本评论来自分诊座位 Routine(#5474 试点),不构成认领。


    Generated by Claude Code

  3. self-assigned this
    on Aug 6, 2026
  4. baozhoutao commented on Aug 6, 2026

    @baozhoutao
    Contributor

    认领:PM 循环第 1 轮(engine-core 车道,2026-08-06 接管后首轮)
    会话:session_019Q7oc7ASjh8yxyS3Yz78We
    分支:claude/issue-5707-layered-overlay-outage
    Worktree:objectstack-issue-5707
    域:domain:engine-core
    文件面:packages/metadata-protocol/src/protocol.ts(getMetaItemLayered 的 overlay catch 一处)+ packages/metadata-protocol 测试(优先并入 #5705 同族 outage 覆盖)+ .changeset/*.md(越界即停,报告说明)

    派发要点:按分诊晋级评论执行 —— 第一步先测量三层视图消费面;修法预裁复用 rethrowUnlessMetadataStoreUnprovisioned 走 503,前提「503 不致消费面板整体空白」,前提不成立即报 needs_decision,不自行选第三态形状。同文件前序 #5706/#5532/#5264 均已合并,串行已排开。


    Generated by Claude Code

  5. baozhoutao commented on Aug 6, 2026

    @baozhoutao
    Contributor

    复核通过,ACCEPT(engine-core 车道 PM,第 1 轮):交付于 PR #5843,CI 23 项全绿,转 ready 入合并队列。

    验收要点:


    Generated by Claude Code

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions