Skip to content

fix: retire the view-level provider: 'api' readers (objectui#12325) - #12361

Merged
objectstack-fleet[bot] merged 2 commits into
mainfrom
claude/issue-12325-retire-api-view-data
Oct 14, 2026
Merged

objectstack-fleet[bot] merged 2 commits into
mainfrom
claude/issue-12325-retire-api-view-data

Conversation

@objectstack-fleet

Copy link
Copy Markdown
Contributor

Fixes #12325
Clause-②: no

The view-level provider: 'api' data source is retired in @objectstack/spec (objectstack-ai/objectstack#23082 ruling C, PR objectstack-ai/objectstack#23160). Per the maintainer's ruling A on the card (comment 6163115077), this deletes every objectui reader of a ViewData api block now, while objectui still resolves spec 18.0.0-next.0, and keeps the approvals inbox's code-built ApiDataSource.

What changed

  • @object-ui/core resolveDataSource: the api arm is gone. An api block is an unknown provider and gets that answer (the fallback, else null). ResolveDataSourceOptions loses fetch / defaultHeaders, which only that arm read. ApiDataSource stays a class; its docblock and its missing-config error now name ApiDataSourceConfig, not ViewData.
  • @object-ui/core ViewDataProvider (file-surface extension, see below): the api arm, resolveApi, extractRecords and DataFetcher.fetchUrl are gone; an api config resolves as Unknown data provider: api.
  • @object-ui/react useViewData: no api keying and no apiFetch threading.
  • @object-ui/plugin-gantt ObjectGantt: no api adapter input, no apiFetch dependency, the drawer's real-record fetch and the refresh button no longer branch on api.
  • @object-ui/plugin-list ListView: ganttOwnsData (true only for a gantt with an api block) and the matching skeleton branch are deleted, so such a view fetches its bound object like any list.
  • @object-ui/plugin-calendar / @object-ui/plugin-map (file-surface extension): their dataProvider === 'api' branches, which only warned "not yet implemented", are deleted.
  • Docs: content/docs/plugins/plugin-gantt.mdx and plugin-map.mdx sections that prescribed or described the api arm, the core adapters README, the gantt README, the ViewData docblock in @object-ui/types, and the approvals source's docblock.
  • Changeset .changeset/12325-retire-api-view-data.md (minor for the breaking packages, per the no-major rule).

File-surface extensions (bounded in-place fixes, same defect class)

The claim names packages/core/src/adapters/, useViewData.ts, ListView.tsx, ObjectGantt.tsx, packages/types/src/ and the docs. Measurement found more readers of the same retired arm, so these were edited too, each a mechanical deletion of the same kind:

  • packages/core/src/data-scope/ViewDataProvider.ts (a second ViewData union with its own api arm; not caught by a provider === 'api' grep because it is a case 'api').
  • packages/plugin-calendar/src/ObjectCalendar.tsx and packages/plugin-map/src/ObjectMap.tsx: dataProvider === 'api' (capital P, so the PM's case-sensitive grep missed them). Against spec main these are TS2367 once core compiles; the gate's run 38513810543 never reached them because @object-ui/core's build failed first.
  • packages/types/src/__tests__/object-gantt-properties-bag-10859-b6.test.ts and object-grid-properties-bag-11276.test.ts: the TS2352 errors of A2. Their "the parse authors no default" pins rode on the api arm's read.method default; they now ride on navigation's defaults (spec row writes mode: 'page', this face writes nothing).
  • apps/console/src/services/approvalRequestsDataSource.ts: docblock only.

Pins flipped (each asserts the new meaning)

  • resolveDataSource.test.ts: an api block builds no ApiDataSource and is answered exactly like an unknown provider.
  • ViewDataProvider.test.ts: an api config resolves to Unknown data provider: api and fetches nothing.
  • useViewData.test.tsx: an api block falls back to the context DataSource and requests its URL through neither apiFetch nor global fetch.
  • ObjectGantt.apifetch.test.tsx renamed to ObjectGantt.retiredApiProvider-12325.test.tsx: the read URL is requested through neither channel; with a context DataSource the chart queries schema.objectName.
  • ObjectGantt.test.tsx: the api read/write-back case is removed, pointing at the file above.
  • recordSourceInputs-10394.test.tsx (gantt), index.recordSourceInputs-10394.test.tsx (map), ListView.test.tsx: flipped to the retired meaning.
  • ObjectGantt.emptyHostData-7333.test.tsx: the host-array cases now use the bound object as the own source.
  • ObjectGantt.discardedReloadIdentity-10036.test.tsx: the discard pin moves from api to value (the constructing provider that remains); the "host swaps apiFetch" case is removed because apiFetch is no longer an adapter input. The mount baseline is measured rather than assumed (see Acceptance notes).

Verification (head 93d4323)

  • Spec Main Shape Gate reproduced locally: built @objectstack/spec from objectstack b5b1bf7277d6 (contains the retirement; VIEW_DATA_API_PROVIDER_RETIRED present in dist/ui/index.js), packed, injected with node scripts/spec-main-shape-gate.mjs inject, then TURBO_FORCE=true pnpm type-check --continue --concurrency=2: 80 of 81 tasks green, the one red being @object-ui/types (the two TS2352 test casts). After the types-test fix, @object-ui/types + @object-ui/plugin-gantt type-check: 15/15 green on the same injected spec, and the two types test files 193/193 green there. Install then restored with pnpm install --frozen-lockfile --force (marker gone, retirement string 0 hits).
  • Installed spec (18.0.0-next.0): type-check of core, react, types, plugin-gantt, plugin-list, plugin-calendar, plugin-map: 22/22 tasks green; types + plugin-gantt re-run after the last commit 15/15.
  • vitest: every changed test file, 13 files / 460 tests green; approvals inbox (approvalRequestsDataSource*.test.*, 4 files) plus neighbouring api pins (ApiDataSource, record-source neutrality, ObjectView protocol keys, tree inputs, grid data contract, ListView 7477) green; earlier whole-package runs of plugin-gantt, plugin-map, plugin-calendar green.
  • Reverse validation of the narrowed ResolveDataSourceOptions: passing { fetch: undefined } from ObjectGantt gives TS2353 against the rebuilt dist (whose .d.ts has no fetch); restored, hash equals HEAD, git diff HEAD empty.
  • Gates (exit codes): phantom-deps, self-import, unreferenced-sources, doc-example-readers, handler-key-reads, side-effects-array, element-data-source-declaration, spec-symbols, action-forward-parity, designer-field-key-parity, icon-record-names, i18n-keys, i18n-drift, i18n-designer-parity, doc-json, doc-snippets, doc-examples, new-line-citations, changeset-fixed, changeset-presence, changeset-no-major: all 0. check:spec-floors: 1, the known unrelated "scan collapsed" red carried by objectui#12334.
  • Lint narrowed to the 23 changed .ts/.tsx files (count from eslint --format json): 0 errors. The config enables no type-aware linting, so this diff cannot change any untouched file's verdict.

Acceptance notes

  • A block that still says provider: 'api' is not refused by objectui at runtime: under spec 18.0.0-next.0 it parses, and the renderers answer it as an unknown provider (gantt and useViewData fall back to the context adapter and objectName; map and calendar draw nothing). The refusal lands with the spec pin bump, where ViewDataSchema rejects it. Measured: no objectui metadata writes provider: 'api'.
  • An inline value gantt reads its items more than once while mounting (measured in the moved 10036 pin). Pre-existing and unrelated to this change; the pin measures its baseline instead of hard-coding one.
  • Stale prose left alone, outside this file surface: SchemaRendererContext.apiFetch's docblock and packages/react/README.md still say it serves provider: 'api' view data (it still serves other channels); ConsoleShell.tsx, createAuthenticatedFetch.ts and packages/auth/README.md comments likewise; the DataSource required for object/api providers error text (pinned by the schema-catalog render test); the plugin-grid data input description, which still lists { provider: "api", read, write }.
  • Tests that parse provider: 'api' through the spec (gridDataInputContract, objectTreeInputs-11168, the two types probe lists) will need flipping at the spec pin bump; they are not readers.
  • content/docs/plugins/plugin-calendar.mdx lists the api config among shapes the calendar refuses; still true, left as is.

Session: https://claude.ai/code/session_01XVp19E1MYUTFM3dnkwz8gB (dispatched os-dev under the domain:ui#2 claim).


Generated by Claude Code

@objectstack/spec retires the view-level `api` data source
(objectstack#23082, ADR-0049). Delete every objectui reader of a ViewData
`api` block: resolveDataSource's arm, ViewDataProvider's arm, useViewData's
keying, ObjectGantt's adapter inputs / drawer / refresh branches,
ListView's gantt stand-down, and the calendar and map "not yet implemented"
branches. ApiDataSource stays a class for code-built use (the approvals
inbox). Flipped pins assert the new meaning.

Claude-Session: https://claude.ai/code/session_01XVp19E1MYUTFM3dnkwz8gB
Co-authored-by: Claude <noreply@anthropic.com>
…objectui#12325)

The object-gantt / object-grid "parse authors no default" pins rode on the
api arm's read.method default, which does not compile against
@objectstack/spec main (TS2352). They now ride on navigation's defaults.

Claude-Session: https://claude.ai/code/session_01XVp19E1MYUTFM3dnkwz8gB
Co-authored-by: Claude <noreply@anthropic.com>
@github-actions

Copy link
Copy Markdown
Contributor

changeset-claim-re-read

⚠️ 1 pending changeset(s) describe a file this change touches

Their bodies publish verbatim into the CHANGELOG at the next release, so this is a request to re-read them against your diff — addressed here because you are the one seat that can answer it without re-deriving anything.

⛔ Nothing here blocks, and nothing here is a verdict on your change. This gate exits 0, is not a required context, and judges name resolution, never meaning: it asked whether a pending body names a file you touched. "Is this sentence still true?" is the one question it will not answer, and the one you are being asked to answer.

.changeset/12032-approval-requests-data-source.md

  • names apps/console/src/services/approvalRequestsDataSource.ts → apps/console/src/services/approvalRequestsDataSource.ts — edited by this change

    • ApiDataSource.findOne resolves null only on a 404. Every other failure (a 403, a 5xx, a transport error) now rejects, the way ObjectStackAdapter.findOne does. Before, any failure resolved null, so a record page over a provider: 'api' source showed a refused or failed read as "Record not found". It now shows "no access", or "could not load" with Retry (the record page states from objectui#11902). - A console data source for approval requests. apps/console/src/services/approvalRequestsDataSource.ts routes reads of sys_approval_request to the approvals routes through ApiDataSource, and everything else to the console's own adapter. Each source serves one server-side scope: awaiting me, submitted by me, or all. Rows come back as the approvals service serves them, so viewer and (on a single read) decision_progress are fields a view can bind. On a list read, $top, $skip and $search become the route's limit, offset and q, and $select is dropped. Every other parameter, such as a filter, a sort or an expansion, is refused with an UNSUPPORTED_QUERY_PARAM error, so the list shows its error panel and never shows unfiltered rows. Nothing mounts the source yet; the approvals list and detail pages that will use it come later.

Read the paragraph, not the line: both false halves of the objectui#8617 claim sat in one paragraph, and correcting either alone would have left it asserting the same wrong thing.

If a claim did go false, correct the body. That is precedented and prose-only, frontmatter untouched; check-changeset-overwrite.mjs will report the correction as its own case 2 ("correcting a declaration on purpose … legitimate"), which is the intended shape — one gate asks for the read, the other records the write.

Not covered, stated so nobody reads this as more: a born-false claim that spells no line address at all (objectui#9495 coordinated one by ORDINAL — "a grep finds that member first" — and deciding that means reading what the sentence means), a claim spelled as a symbol or a package rather than a backticked file name, and a file named ambiguously.

Compared the checked-out tree with 2312bd9a6 (merge-base with origin/main): 28 file(s) changed outside .changeset/, read against 430 pending declaration(s) that publish a body (446 pending in total). · run

@github-actions

Copy link
Copy Markdown
Contributor

✅ Console Performance Budget

Metric Value Budget
Eager closure (gzip, 72 chunks) 3054.5 KB 3119.4 KB
Main entry chunk (gzip) 73.8 KB 350 KB
Entry file index-BrHvCS8G.js —
Status PASS —

The eager closure is every chunk the entry reaches through static imports — what the browser fetches and parses before the app renders. The entry chunk on its own is a small fraction of it.


📦 Bundle Size Report

Package Size Gzipped
app-shell (consoleActionDispatch.js) 0.20KB 0.19KB
app-shell (index.js) 20.69KB 7.62KB
app-shell (runtime-config.js) 22.59KB 7.89KB
app-shell (types.js) 0.01KB 0.04KB
app-shell (urlParams.js) 10.11KB 3.87KB
auth (ActiveOrganizationStorage.js) 27.95KB 10.04KB
auth (AuthContext.js) 0.31KB 0.24KB
auth (AuthGuard.js) 2.07KB 1.00KB
auth (AuthProvider.js) 40.22KB 10.61KB
auth (AuthShell.js) 3.49KB 1.40KB
auth (ForgotPasswordForm.js) 12.21KB 3.45KB
auth (LoginForm.js) 18.15KB 5.40KB
auth (PreviewBanner.js) 0.90KB 0.50KB
auth (RegisterForm.js) 6.72KB 2.24KB
auth (SocialSignInButtons.js) 9.70KB 3.93KB
auth (UserMenu.js) 3.39KB 1.21KB
auth (auth-gate-events.js) 1.29KB 0.66KB
auth (authStyles.js) 5.04KB 1.72KB
auth (createAuthClient.js) 41.19KB 11.12KB
auth (createAuthenticatedFetch.js) 8.54KB 3.46KB
auth (index.js) 3.63KB 1.64KB
auth (invitation-status.js) 1.22KB 0.70KB
auth (org-roles.js) 6.66KB 2.78KB
auth (phone-identifier.js) 1.11KB 0.66KB
auth (types.js) 0.59KB 0.35KB
auth (useAuth.js) 5.30KB 1.02KB
auth (useWorkspaceAdminStatus.js) 11.08KB 4.58KB
collaboration (CommentThread.js) 27.26KB 8.03KB
collaboration (LiveCursors.js) 3.17KB 1.27KB
collaboration (PresenceAvatars.js) 6.28KB 2.60KB
collaboration (PresenceProvider.js) 2.79KB 1.13KB
collaboration (commentAuthorship.js) 1.39KB 0.78KB
collaboration (index.js) 1.93KB 0.85KB
collaboration (useCollaborationTranslation.js) 6.50KB 2.52KB
collaboration (useCommentSearch.js) 1.98KB 0.88KB
collaboration (useConflictResolution.js) 7.75KB 1.86KB
collaboration (useMentionNotifications.js) 1.81KB 0.68KB
collaboration (usePresence.js) 6.33KB 1.84KB
collaboration (useRealtimeSubscription.js) 7.91KB 2.01KB
components (index.js) 592.14KB 142.83KB
core (index.js) 10.18KB 4.04KB
create-plugin (index.js) 27.94KB 9.51KB
data-objectstack (index.js) 248.41KB 69.48KB
fields (index.js) 283.00KB 72.12KB
i18n (LocalizationContext.js) 2.92KB 1.42KB
i18n (builtinAggregateLabels.js) 0.86KB 0.49KB
i18n (currency.js) 2.59KB 1.22KB
i18n (fallbackInterpolation.js) 6.25KB 2.77KB
i18n (i18n.js) 8.87KB 3.64KB
i18n (index.js) 5.52KB 2.39KB
i18n (pickLocalized.js) 9.86KB 3.95KB
i18n (provider.js) 39.35KB 12.88KB
i18n (translateFn.js) 0.20KB 0.18KB
i18n (useDisplayLocale.js) 3.52KB 1.76KB
i18n (useObjectLabel.js) 36.87KB 9.88KB
i18n (useSafeTranslation.js) 7.14KB 2.92KB
layout (index.js) 40.26KB 11.71KB
mobile (MobileProvider.js) 0.92KB 0.49KB
mobile (ResponsiveContainer.js) 0.94KB 0.38KB
mobile (breakpoints.js) 1.51KB 0.70KB
mobile (createOfflineDataSource.js) 5.61KB 1.75KB
mobile (index.js) 1.99KB 0.87KB
mobile (offlineQueue.js) 3.91KB 1.35KB
mobile (pwa.js) 0.97KB 0.49KB
mobile (serviceWorker.js) 1.48KB 0.62KB
mobile (serviceWorkerSource.js) 3.41KB 1.48KB
mobile (useBreakpoint.js) 1.54KB 0.65KB
mobile (useGesture.js) 6.96KB 1.98KB
mobile (useOfflineSync.js) 1.99KB 0.72KB
mobile (usePullToRefresh.js) 6.62KB 2.45KB
mobile (useResponsive.js) 0.72KB 0.42KB
mobile (useSpecGesture.js) 5.52KB 2.10KB
mobile (useTouchTarget.js) 1.01KB 0.54KB
permissions (MePermissionsProvider.js) 15.35KB 5.51KB
permissions (PermissionContext.js) 0.31KB 0.25KB
permissions (PermissionGuard.js) 0.89KB 0.45KB
permissions (PermissionProvider.js) 6.82KB 2.38KB
permissions (discardProofCache.js) 1.04KB 0.55KB
permissions (evaluator.js) 8.33KB 3.07KB
permissions (index.js) 0.93KB 0.41KB
permissions (store.js) 0.91KB 0.42KB
permissions (useFieldPermissions.js) 1.28KB 0.53KB
permissions (usePermissions.js) 4.83KB 2.27KB
plugin-ai (index.js) 16.04KB 3.92KB
plugin-calendar (index.js) 54.94KB 16.05KB
plugin-charts (index.js) 84.72KB 23.27KB
plugin-chatbot (index.js) 201.72KB 48.07KB
plugin-dashboard (index.js) 143.63KB 38.79KB
plugin-designer (index.js) 233.77KB 50.02KB
plugin-detail (index.js) 259.78KB 68.65KB
plugin-editor (index.js) 2.23KB 1.05KB
plugin-form (index.js) 178.88KB 46.47KB
plugin-gantt (index.js) 178.36KB 45.08KB
plugin-grid (index.js) 258.97KB 72.23KB
plugin-kanban (index.js) 53.23KB 16.71KB
plugin-list (index.js) 123.35KB 31.60KB
plugin-map (index.js) 27.14KB 8.99KB
plugin-markdown (index.js) 13.88KB 4.80KB
plugin-report (index.js) 46.66KB 13.13KB
plugin-timeline (index.js) 39.21KB 11.85KB
plugin-tree (index.js) 15.07KB 5.33KB
plugin-view (index.js) 91.99KB 23.23KB
providers (DataSourceProvider.js) 0.75KB 0.39KB
providers (MetadataProvider.js) 1.37KB 0.59KB
providers (ThemeProvider.js) 1.90KB 0.85KB
providers (UploadProvider.js) 12.07KB 3.68KB
providers (index.js) 0.45KB 0.23KB
providers (types.js) 0.01KB 0.04KB
react-runtime (index.js) 5.62KB 2.34KB
react (LazyPluginLoader.js) 4.47KB 1.63KB
react (SchemaRenderer.js) 120.63KB 39.56KB
react (data-invalidation.js) 5.05KB 2.08KB
react (index.js) 4.50KB 2.06KB
react (schema-input.js) 4.31KB 2.07KB
react (spec-input.js) 0.20KB 0.18KB
sdui-parser (body-dialect.js) 4.50KB 1.99KB
sdui-parser (codegen.js) 9.45KB 3.76KB
sdui-parser (dashboard-widget-options.js) 3.07KB 1.30KB
sdui-parser (index.js) 7.30KB 3.12KB
sdui-parser (input-type.js) 2.84KB 1.40KB
sdui-parser (parse.js) 25.28KB 7.81KB
sdui-parser (provenance.js) 3.84KB 1.90KB
sdui-parser (types.js) 0.29KB 0.24KB
sdui-parser (validate.js) 23.87KB 7.83KB
types (ai.js) 4.39KB 2.17KB
types (api-types.js) 0.20KB 0.18KB
types (app.js) 4.12KB 1.61KB
types (authoring-nodes.js) 0.20KB 0.19KB
types (base.js) 0.20KB 0.18KB
types (blocks.js) 0.20KB 0.18KB
types (cloud.js) 0.20KB 0.18KB
types (complex.js) 4.44KB 2.07KB
types (crud.js) 0.20KB 0.18KB
types (dashboard-filter-alias.js) 6.23KB 2.74KB
types (dashboard-widget-layout.js) 2.06KB 0.96KB
types (data-display.js) 3.75KB 1.85KB
types (data-protocol.js) 0.20KB 0.19KB
types (data.js) 0.20KB 0.18KB
types (designer.js) 1.85KB 0.85KB
types (disclosure.js) 0.20KB 0.18KB
types (error-code.js) 1.54KB 0.88KB
types (expression.js) 0.20KB 0.18KB
types (feedback.js) 0.20KB 0.18KB
types (field-types.js) 1.13KB 0.65KB
types (form.js) 0.20KB 0.18KB
types (http-inflight.js) 8.87KB 3.73KB
types (http-retry.js) 4.32KB 2.02KB
types (icon-key-migration.js) 4.26KB 1.63KB
types (index.js) 5.78KB 2.70KB
types (layout.js) 0.20KB 0.18KB
types (managed-by.js) 0.19KB 0.18KB
types (mobile.js) 5.00KB 2.39KB
types (navigation.js) 0.20KB 0.18KB
types (node-slots.js) 7.18KB 2.34KB
types (objectql.js) 0.20KB 0.18KB
types (overlay.js) 0.20KB 0.18KB
types (permissions.js) 2.52KB 1.31KB
types (plugin-scope.js) 0.20KB 0.18KB
types (record-components.js) 0.20KB 0.19KB
types (record-semantics.js) 1.28KB 0.67KB
types (registry.js) 0.20KB 0.18KB
types (reports.js) 0.20KB 0.18KB
types (select-option.js) 0.20KB 0.19KB
types (spec-report.js) 4.99KB 1.96KB
types (spec-ui-namespace.js) 0.20KB 0.19KB
types (strict-authoring-face.js) 19.93KB 7.26KB
types (system-fields.js) 3.33KB 1.54KB
types (theme.js) 6.28KB 2.87KB
types (ui-action.js) 8.48KB 3.50KB
types (views.js) 0.20KB 0.18KB
types (widget.js) 0.20KB 0.18KB

Size Limits

  • ✅ Core packages should be < 50KB gzipped
  • ✅ Component packages should be < 100KB gzipped
  • ⚠️ Plugin packages should be < 150KB gzipped

@objectstack-fleet

Copy link
Copy Markdown
Contributor Author

Contract review

Served-tier: CONTRACT_REVIEW_TIER
Head-sha: 93d43230c47ff34387d2fecc072f3e47bb7a3bbc
Local-runs: none

Inputs read: card #12325 (body and all 9 comments, the ruling 6163115077, the decision 6161678306, the claim 6163150346, the os-dev-report 6164416718), PR #12361 (body, 29-file list, net diff against base 2312bd9a), the 33 check-runs on this head, and at both head and base the package.json exports plus entry barrels (and the adapters/ and data-scope/ sub-barrels of core) of @object-ui/core, @object-ui/react, @object-ui/types, @object-ui/plugin-gantt, @object-ui/plugin-list, @object-ui/plugin-calendar, @object-ui/plugin-map. Check-runs: 30 success, 3 skipped (dependabot and the two coverage placeholders), 0 failures; Spec Main Shape Gate, Type Check, Changeset Bump Policy, Changeset Declaration, Governed Surface Queue Guard all success.

① Derived judgments

Published-surface reach first: no exports map and no entry barrel changed in any of the seven packages between base and head. Every change below is reachable through an unchanged barrel, so it IS on the published surface where named.

  1. @object-ui/core resolveDataSource: case 'api' deleted; an api block now takes the default arm (fallback, else null). Right — this is the first reader the ruling names, and the test pins it as identical to an unknown provider.
  2. @object-ui/core ResolveDataSourceOptions loses fetch and defaultHeaders (published via adapters/index.ts). Only the deleted arm read them; kept, they would be inert accepted members, which ADR-0049 is the rule against. A caller passing { fetch } as a literal now gets TS2353 (the dev's reverse validation). Right, and within the ruling — the option members were the reader's only input, not a separate feature. Narrowing of a published type: belongs in core's bump (see ②).
  3. @object-ui/core ViewDataProvider (file-surface extension): case 'api', resolveApi, extractRecords deleted; ViewDataConfig loses the api member, ResolvedData.provider narrows to 'object' | 'value', DataFetcher.fetchUrl removed. ViewDataProvider, ViewDataConfig, DataFetcher, ResolvedData are all published through data-scope/index.ts. This is a second reader of the same retired arm (a case, not a provider === 'api' compare, so the card's grep missed it); fetchUrl was called only by resolveApi. Right, within the ruling; Type Check green on this head is the evidence no in-repo DataFetcher literal still supplies fetchUrl.
  4. @object-ui/core ApiDataSource: class, ApiDataSourceConfig (still carrying read/write/fetch/defaultHeaders) and its export from adapters/index.ts unchanged; only the docblock and the missing-config error string ("Ensure the ApiDataSourceConfig has read/write configs.") move. Right — the ruling's "keep the approvals inbox's code-built ApiDataSource" holds; apps/console/src/services/approvalRequestsDataSource.ts changes a docblock only, and the inbox tests are inside the green Test shards.
  5. @object-ui/react useViewData: no apiFetch threading, no api keying in the memo; adapterOptions stays typed ResolveDataSourceOptions, so it inherits the narrowing in 2. The pin shows an api block falls back to the context DataSource and requests its URL through no channel. Right. SchemaRendererContext.apiFetch itself is untouched (it still serves other channels) — nothing deleted beyond the reader.
  6. @object-ui/plugin-gantt ObjectGantt: api branch out of adapterInputsKey, apiFetch out of the adapter memo and both effect dependency lists, drawer needsRealRecord and onRefresh no longer branch on api; ObjectGanttProps unchanged. Right — the three sites the card named at :832, :2064, :2585, nothing more.
  7. @object-ui/plugin-list ListView: ganttOwnsData and its skeleton guard deleted, so a gantt list with an api block fetches its bound object like any list. Right — these are the card's :1605 / :2381 sites; the test flips to the new meaning. The data pass-through to the gantt schema stays, so no object/value block is dropped on the way.
  8. @object-ui/plugin-calendar / @object-ui/plugin-map (file-surface extensions): the dataProvider === 'api' branches that only console.warned and committed an empty set are deleted; an api block now falls off the else if chain exactly as an unknown provider does. No prop or type changes. Right; these would be TS2367 against spec main once core compiles, so the extension is the same defect class, as the dev declared.
  9. @object-ui/types: objectql.ts docblocks only; ViewData, HttpRequest, HttpMethod re-exports stay, objectql.zod.ts untouched. Right — HttpRequest/HttpMethod are the shape ApiDataSourceConfig is built with, so they have a non-view reader and stay (this answers the card body's open question on the HttpMethodSubsetSchema / HttpRequestSchema re-exports, which the PR body does not state outright; the green Spec Main Shape Gate shows spec main still exports both).
  10. Docs (plugin-gantt.mdx, plugin-map.mdx, core adapters README, gantt README) stop prescribing the arm and say what an api block now gets. Prose face, outside the three contract faces; read sentence by sentence, consistent with the code.
  11. Nothing deleted beyond the ruling: ApiDataSource, ApiDataSourceConfig, SchemaRendererContext.apiFetch, the 'DataSource required for object/api providers' error text, the HttpRequest types and every barrel are intact.
  12. Clause-②: no — right. The diff accepts no new key, widens no schema and adds no export; every change removes a reader or narrows a published type. A narrowing, which is why this review exists.

② Semver level

Changeset .changeset/12325-retire-api-view-data.md: minor for core, react, plugin-gantt, plugin-list; patch for plugin-calendar, plugin-map, types, console. objectui AGENTS.md §9 (version-alignment rule): objectui's own breaking changes ship as minor with the break spelled out in the body, and major only on the sync bump that follows an @objectstack major; scripts/check-changeset-no-major.mjs enforces it and Changeset Bump Policy is green.

  • core minor: matches. Published types narrow (ResolveDataSourceOptions, ViewDataConfig, ResolvedData.provider, DataFetcher.fetchUrl) and behaviour changes for an api block — breaking, which under the policy is minor, and the body spells the break out.
  • react minor: matches (useViewData behaviour and the inherited adapterOptions narrowing).
  • plugin-gantt and plugin-list minor: match (behaviour of an authored api block changes; no type-surface change, but the policy's minor is the right bump for a behaviour break).
  • plugin-calendar and plugin-map patch: acceptable. No published type changes; an api block drew nothing and requested nothing before and does the same now; the only difference is the lost dev-facing console.warn. Declaring minor would also have been defensible; patch is not wrong.
  • types and console patch: match — docblock-only source edits in fixed-group packages.

Under the policy no entry could be major, and none is. The levels declared match what is removed.

③ Boundary flags

  1. File-surface extensions (ViewDataProvider.ts, ObjectCalendar.tsx, ObjectMap.tsx + its 10394 test, two packages/types tests, the console docblock): answered — accepted. Each is a reader (or a test riding on the reader's default) of the same retired arm, declared in the PR body with the reason the claim's grep missed it, and the goal of the ruling (the gate green while objectui still runs it) is not met without them: Spec Main Shape Gate is success on this head.
  2. The two packages/types pins re-homed from the api read.method default to navigation's mode: 'page' default: answered — right. The pin's subject is "this face authors no default", and the control line (specOut.navigation.mode is 'page') proves the replacement row still writes one.
  3. Tests that parse provider: 'api' through the spec (gridDataInputContract, objectTreeInputs-11168, the two types probe lists) flip red at the spec pin bump: escalated to the dispatching seat. They are not readers and this card does not own the bump; the carrier is the PR that moves objectui onto a @next refusing api, and that PR must flip them. Whoever files or claims that bump card should carry this list from the dev report.
  4. Stale apiFetch prose (SchemaRendererContext.tsx docblock, packages/react/README.md, ConsoleShell.tsx, createAuthenticatedFetch.ts, packages/auth/README.md) and the plugin-grid data input description that still lists { provider: "api", read, write }: escalated. Add one the dev did not list: packages/types/src/zod/objectql.zod.ts line 2795, the tree data description, still says "the api and schema providers draw none on the tree". None of these is a reader and none changes the accept set, so they do not block this PR; but the two zod describe() strings are published prose that still names the retired arm to authors, so one follow-up card should carry all of them. Not this PR's file surface.
  5. Acceptance-note window: an api block still parses under 18.0.0-next.0 and renders as an unknown provider until the pin bump refuses it. Answered — this is exactly the window the maintainer accepted in ruling A (6163115077); no objectui metadata writes the key (measured in 6161678306).
  6. plugin-calendar.mdx left listing the api config among shapes the calendar refuses: answered — still true, the throw site is unchanged.
  7. The inline value gantt reading its items more than once on mount (observed in the moved 10036 pin): answered — pre-existing, outside this card, correctly measured rather than hard-coded.

Implemented-by: claude/issue-12325-retire-api-view-data
Reviewed-by: session_01XVp19E1MYUTFM3dnkwz8gB

VERDICT: PASS


Generated by Claude Code

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

Projects

None yet

2 participants