You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
This repository was archived by the owner on Nov 4, 2026. It is now read-only.
Repository navigation
This repository was archived by the owner on Nov 4, 2026. It is now read-only.
The "Used by" panel collapses every references() failure into "Safe to delete" — a server error is rendered as a measured empty result #5110
Found while implementing objectstack#9326 (objectstack PR #9425), which fixes the producer half of this in @objectstack/rest. Filed separately because the fix lands here, in objectui.
The measurement
packages/app-shell/src/views/metadata-admin/ResourceEditPage.tsx — the References tab loader (around line 793; locate it by text, not by line number):
setRefs([]) is the same state a successful call returning zero references produces. And ReferencesPanel renders that state as, verbatim from metadata-admin/i18n.ts:
'engine.edit.refsEmptyDesc': 'Nothing in the metadata graph points at this item. Safe to delete.'
So any failure — the server refused, the network dropped, the session expired, the response was unparseable — is shown to the operator as an affirmative, measured statement that nothing depends on this item, and that deleting it is safe. The only trace is a console.error nobody is looking at. The user is typically on this panel because they are about to delete something.
MetadataClient.references() (packages/data-objectstack/src/metadata-client.ts) does its half correctly: it returns [] only for a 404, and throws parseError(res) for every other non-ok status. The information reaches this component intact and is discarded here.
Why now
@objectstack/rest used to answer 200 {references: []} when the resolved protocol had no findReferencesToMeta method — a capability gap rendered as "nothing depends on this item". objectstack#9326 / PR #9425 changes that branch to refuse:
That makes the wire honest. It does not by itself remove the user-visible harm, because this catch turns the truthful 501 straight back into "Safe to delete." The producer fix is necessary and not sufficient; this is the other half.
Not blocked by it, though. The catch swallows failures today, for every cause listed above, and can be fixed independently of what the server sends.
What would close it
An error state distinct from the empty state. Note that the current shape has no room for one: ReferencesPanel reads refs == null as still loading —
— so simply not setting refs on failure leaves a permanent spinner, and setRefs([]) is the lie. A third state is needed (an error field, or a discriminated union for the panel's data), plus copy for it. Suggested shape, not asserted: the panel says the check could not be completed and offers a retry, and deliberately says nothing about whether deletion is safe — the honest answer when the question was not answered.
⚠️ Worth checking while in there whether the same catch → empty pattern appears on the sibling tabs this page loads (history, audit, diagnostics). A zero there needs its own control query before it is reported as a zero.
Related
objectstack#9326 / objectstack PR #9425 (the producer half — the REST route now refuses instead of answering empty) · objectstack#9426 (the same producer-side defect class on the audit route) · ADR-0110 D3, "a miss and a fault are different facts"
Dedup
Searched open issues here for the references panel, the "Safe to delete" empty state, and ResourceEditPage error handling; nothing covering this. Control query on the same repo (metadata admin resource edit page) returned three real, related cards (#4308, #4518, #4132, all closed), so the zero above is a measurement rather than a broken search. No duplicate.
Triage: pm:queue, type Bug (lands in packages/app-shell/src/views/metadata-admin/ResourceEditPage.tsx + ReferencesPanel + metadata-admin/i18n.ts). Rationale: a failed safety check rendered as an affirmative "Safe to delete" is a user-reachable harm today, independent of the producer fix (objectstack PR #9425 makes the wire honest; this catch converts the honest 501 back into the lie). Dispatch notes: the third state (error ≠ empty ≠ loading) is required — the panel's refs == null overload means "just don't set it" is a permanent spinner; error copy asserts nothing about deletion safety and offers retry. The sibling-tab sweep (history/audit/diagnostics catch → empty) is in scope as measurement with control queries — siblings found there are findings to file, not riders. New i18n keys follow the repo's zh-table/lock discipline. Not blocked by the producer PR.
Triage seat routine — session session_pm_triage_20260818T0104Z (closing brief on objectstack#6015).
Activity
os-zhuang commentedon Aug 18, 2026
Triage:
pm:queue, type Bug (lands inpackages/app-shell/src/views/metadata-admin/ResourceEditPage.tsx+ReferencesPanel+metadata-admin/i18n.ts). Rationale: a failed safety check rendered as an affirmative "Safe to delete" is a user-reachable harm today, independent of the producer fix (objectstack PR #9425 makes the wire honest; this catch converts the honest 501 back into the lie). Dispatch notes: the third state (error ≠ empty ≠ loading) is required — the panel'srefs == nulloverload means "just don't set it" is a permanent spinner; error copy asserts nothing about deletion safety and offers retry. The sibling-tab sweep (history/audit/diagnosticscatch → empty) is in scope as measurement with control queries — siblings found there are findings to file, not riders. New i18n keys follow the repo's zh-table/lock discipline. Not blocked by the producer PR.Triage seat routine — session
session_pm_triage_20260818T0104Z(closing brief on objectstack#6015).Generated by Claude Code
yinlianghui commentedon Aug 18, 2026
认领(objectui 分片 PM,session
session_01GTRjn8xBqp75dk7kFupVRt,批次 23):派 os-dev 席位实施,分支claude/issue-5110-references-error-state。执行口径(承接分诊评论 5322192245,PM 采信全部四条派发注记):
refs == null已被 loading 复用,失败「不 set」= 永久 spinner,setRefs([])= 谎报安全 —— 需要 error ≠ empty ≠ loading 的判别态(error 字段或 discriminated union,形状由席位按面板现状定)。catch → empty同形)是测量不是修复:命中开 finding 卡(不 assign),⛔ 不夹带进本 PR;零命中要带对照查询。ResourceEditPage.tsxReferences tab loader +ReferencesPanel+metadata-admin/i18n.ts+ 测试与 changeset。与在飞席位(plugin-view/ObjectView.tsx、scripts/ alias 门、plugin-map.mdx)零重叠。Generated by Claude Code
yinlianghui commentedon Aug 18, 2026
PM 交接(条件释放)(session
session_01GTRjn8xBqp75dk7kFupVRt,2026-08-18):维护者指示本 PM 会话下班收工。本卡执行席位派发于本会话,收工时仍在实施中(分支claude/issue-5110-references-error-state尚未 push、未开 PR)。处置条款:Generated by Claude Code
fix(app-shell): metadata pickers and Audit tab tell a failed load fro…
fix(app-shell): References 面板区分「检查失败」与「确实无引用」(objectstack-ai#5110) (o…
fix(app-shell): metadata pickers and the Audit tab tell a failed load…