Repository navigation
fix(data-objectstack): a plain list read of a missing object shows the server's 404 code and sentence, not an empty list - #29839
Merged
Conversation
… of reading as an empty list The plain find path degraded every 404 to an empty result and memoised the resource. The empty answer and the memo now apply only to names in the platform registry (isPlatformProvidedObjectName); any other object's 404 is rethrown with its code and sentence and not memoised. Co-Authored-By: Claude <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01QsR2jUqz12Aiuvrkaw5SJa
…rror panel over the real adapter Co-Authored-By: Claude <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01QsR2jUqz12Aiuvrkaw5SJa
Contributor
Author
|
domain:ui#3 · zhuangjianguo · session_01QsR2jV4dWohojjbTJTQq5m 席位核对 · ACCEPT · 2026-11-03T07:13ZHead-sha:
|
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Requested by Steedos · project thread
Fixes #29782
Clause-②: no
Metadata-protocol: none
维护者速读
OBJECT_NOT_FOUND),不再显示「这里还没有数据」。平台自带的可选集合(如sys_presence、sys_activity)在未安装时仍然安静地当作空集,并且只请求一次。ui/packages/data-objectstack/src/index.ts中find的 404 分支(新增isPlatformProvidedObjectName(resource)条件),以及新测试ui/packages/data-objectstack/src/findMissingObject-29782.test.ts。/api/v1/data/showcase_account的请求改为返回 404{"success":false,"error":{"code":"OBJECT_NOT_FOUND","message":"Object 'showcase_account' is not registered"}},应看到「无法加载记录」、服务器原句、OBJECT_NOT_FOUND和「重试」,而不是「这里还没有数据」。What changes
ObjectStackAdapter.find, plain SDK path: a 404 that is not anenable-block denial now degrades to{ data: [], total: 0 }and enters themissingResourcesmemo only whenisPlatformProvidedObjectName(resource)(@objectstack/spec/system, the curated platform registry) is true. Any other object's 404 is rethrown as the client threw it (httpStatus,code, message) and is not memoised, so the next read asks the server again.sys_presenceand a list's own unregistered object both answer 404OBJECT_NOT_FOUND. The split is by name, against the registry, never a prefix guess. The short-circuit at the top offindcan now only ever hold platform names.enable-block denials (OBJECT_API_DISABLED,OBJECT_API_METHOD_NOT_ALLOWED) are rethrown and unmemoised as before. The raw$expand/$searchpath is unchanged.answeredLoadFailure).Why
The memo exists for optional platform collections, whose absence means "this deployment does not install the feature". It also swallowed the 404 of a list's own object, so an object that failed to register (#29673) read as 这里还没有数据, and only the list's expand read reached the error panel.
Caller census (ui src at the base, tests excluded). Every literal or constant
findtarget inui/is in the registry (sys_activity,sys_presence,sys_comment,sys_comment_reaction,sys_audit_log,sys_attachment,sys_user,sys_user_position,sys_user_permission_set,sys_user_preference,sys_member,sys_personal_view,sys_approval_action,sys_notification_receipt,sys_inbox_message,sys_metadata,sys_environment). The non-registrysys_literals (sys_favorite,sys_claim,sys_view,sys_dashboard, …) are action names or update targets, neverfindtargets. Every non-platform caller that relied on the empty answer reads its own surface's object, and now shows its existing load-failure state on a missing object.Tests
ui/packages/data-objectstack/src/findMissingObject-29782.test.ts:findon a non-registry object answered 404OBJECT_NOT_FOUNDrejects with that code,httpStatus404 and the server sentence;findissues a second request (no memo);@objectstack/client: the wrapped{ success: false, error: { code, message } }404 reaches the caller ascode+httpStatus, twice, two requests;sys_presence) answered 404OBJECT_NOT_FOUNDanswers empty and the second call is short-circuited (one request);enable-block denial still rethrows, on a platform name and on any other, and is not memoised;ui/packages/app-shell/src/views/objectListApiDisabled-4408.test.tsx(the shared "realObjectStackAdapterfeeding the realListView" harness): a new top-leveldescribefor data-objectstack: a plain list read answered 404 OBJECT_NOT_FOUND reads as an empty list ("no data yet"), so the list never shows the server's reason #29782. A list overcrm_invoiceanswered 404OBJECT_NOT_FOUNDshows the server sentence and thelist-error-codechip, with no empty state and no network sentence, and every data read it made took the plain path. The harness'smakeAdapterkeeps a handle on its fetch stub (ds.__fetch) for that last check. Its existing bare-404 control onsys_jwksstays green, sincesys_jwksis a registry name.Moved pin
ui/packages/data-objectstack/src/apiAccessDenied.test.ts, "CONTROL: a 404 RECORD_NOT_FOUND is not an enable-block denial": its resource moves fromaccounttosys_comment. Its point is thatRECORD_NOT_FOUNDis not an enable-block denial, so it still takes the optional-collection branch. Onaccount, a non-registry object, the 404 is now rethrown by design. That case is pinned in the new file.Ablation (one-shot, not kept):
scripts/ablation-replace.mjsdeleted the&& isPlatformProvidedObjectName(resource)line (anchor 1 to 0, blobf82eb0b7to8dd44be3). The new adapter file and the new ListView describe went red: 6 tests failed, 8 passed, including "REJECTS a plain find answered 404 OBJECT_NOT_FOUND…". The file was restored to the HEAD blobf82eb0b7, andgit diff HEADcame back empty. The ui vitest aliases@object-ui/data-objectstacktosrc, so no rebuild leg was owed.Acceptance notes
aggregateViaFindreads throughfind, so a dashboard figure over a missing object now fails instead of reading 0. This is the intended direction, and it is named in 风险与回滚.sys_presenceread on the screens it visited (RecordDetailView's comment records that its presence probe was retired). So the shell's boot-time plain reads ofsys_activityandsys_inbox_messageserved as the live optional-collection control.Verification
All readings below were taken at head
6834710a(this branch merged withorigin/mainb0ef25f) unless a different head is named.Unit and consumer tests (locked, maxWorkers=2)
packages/data-objectstack/(114 files), the plugin-listListView.loadErrorKind, and the 22 test files outside the package that build a realObjectStackAdapterand answer 404 (includingobjectListApiDisabled-4408): 137 files, 1530 tests passed at6834710a.a9f52f3e: the four touched files gave 50/50, and the same consumer set gave 135/135.pnpm exec turbo run type-check --filter=@object-ui/data-objectstack --filter=@object-ui/app-shell: 66/66 tasks. data-objectstack's program includes its tests, and app-shell runstsconfig.test.json.eslinton the four touched ui files: 0 errors.Derived gate union (dispatch-gates --commands, 36 families)
6834710a: every one of the 36 exited 0, includingnode scripts/check-sdui-manifest.mjs(and--self-test),pnpm --dir ui exec vitest run scripts/(170 files passed, 2 skipped),pnpm check:undeclared-dep-imports,pnpm check:cross-package-test-inputs,pnpm check:test-source-aliasandpnpm check:query-options-erasure.dispatch-gates --ran: 36 derived, 36 run, 0 NOT-MEASURED.a9f52f3e, before the merge.Live run (showcase backend + Console Vite, zh-CN, Playwright)
node shots.cjs before|afteragainstpnpm dev -- --freshand the Console Vite proxied to it. Every/api/v1/data/showcase_accountread is fulfilled with 404{ success: false, error: { code: 'OBJECT_NOT_FOUND', message: "Object 'showcase_account' is not registered" } }. This list reads only on the plain path:?top=0and?top=50&select=…, with 0 raw reads.origin/maincopy, blob7ddcc01a): no error state. The list shows 这里还没有数据 and a· 0count.OBJECT_NOT_FOUND· 重试, with no 这里还没有数据. It was re-probed after the source was restored (blob back to HEADf82eb0b7), with the same reading.sys_activity,sys_inbox_messageandsys_notification_receiptanswer 404OBJECT_NOT_FOUND. After boot and four SPA navigations (home, contacts, home, products, home), the Console made exactly 1 request each forsys_activityandsys_inbox_message(sys_notification_receiptwas not read on this path), and showed 0 error panels or alerts.Human Minimum
packages/specholds no runtime logic.pnpm lintpasses. (eslint on the touched files: 0 errors; the repo-wide run is CI's.)main, one pull request..changeset/29782-missing-object-list-read.md, patch), and both declaration lines are filled in here and in the changeset.packages/spectouched: n/a, not touched.content/docs/references/,packages/*/CHANGELOG.mdorcontent/docs/releases/.Generated by Claude Code