feat(types): derive ListViewSchema from @objectstack/spec/ui (#2231)#2622
Merged
Conversation
@object-ui/types shipped a hand-written mirror of the spec's UI ListView zod (objectql.zod.ts) plus a parallel hand-written TS interface (objectql.ts). Both had drifted from the authoritative @objectstack/spec/ui ListViewSchema, with nothing enforcing they stay in sync. - zod ListViewSchema now derives from the spec's ListViewSchema: spec-owned fields (filter, sort, selection, navigation, pagination, grouping, rowColor, userActions, appearance, tabs, addRecord, rowHeight, sharing, chart/tree configs, responsive, performance, ...) flow in by reference via BaseSchema.extend(SpecListViewFields.shape) instead of being re-typed. The component envelope (type: 'list-view' discriminator + objectName) and the legacy objectui vocabulary (viewType, fields, filters, the show* toolbar flags, densityMode, color, ...) plus the configs whose objectui shape is intentionally broader than spec's (userFilters, sharing, aria, conditionalFormatting, exportOptions, kanban/calendar/gantt/gallery/timeline) remain as sanctioned local .extend()s. Existing payloads keep validating; spec-canonical payloads (columns/filter/userActions) now validate too. - The hand-written interface ListViewSchema is replaced by z.infer<typeof ListViewSchema> & ListViewRuntimeProps, so the type can no longer drift from the schema. Non-serializable runtime-only props (onNavigate, onDensityChange, refreshTrigger) live in ListViewRuntimeProps. - Added a drift-guard test (list-view-spec-parity.test.ts) that fails if the spec grows a field objectui hasn't triaged, renames an aliased anchor (type/columns/filter), or an objectui-only field is added outside the sanctioned-local set. - Bumped @objectstack/spec ^14.6.0 -> ^15.0.0 across the workspace. Migrating the legacy vocabulary to the spec-canonical keys and adopting spec's narrower sub-shapes are deferred follow-ups (see #2231). No runtime behavior change; build + type-check + plugin-list/plugin-view/cli/core/types test suites all green. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CBAuAYP5j1j5MguKYM84dW
|
The latest updates on your projects. Learn more about Vercel for GitHub. |
Contributor
✅ Console Performance Budget
📦 Bundle Size Report
Size Limits
|
spec 15.0.0's ADR-0089 D3a strict()+transform() pipes exposed a lazySchema
Proxy / z.toJSONSchema identity mismatch ("Cannot set properties of undefined
(setting 'ref')") that broke the spec-derived Page/View inspector JSONSchema
derivation in app-shell (page-schema.test.ts failed in CI). framework#3021
fixed it in spec; 15.1.0 is the first published version carrying the fix.
Verified under 15.1.0: all 202 spec/ui schemas convert via z.toJSONSchema
(9 failed under 15.0.0), full build 43/43, app-shell 1496 tests green,
types/plugin-list/plugin-view 403 tests green.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CBAuAYP5j1j5MguKYM84dW
Contributor
✅ Console Performance Budget
📦 Bundle Size Report
Size Limits
|
os-zhuang
marked this pull request as ready for review
July 17, 2026 00:31
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.
Summary
Closes the
ListViewSchemadrift called out in #2231.@object-ui/typesshipped a hand-written mirror of the spec's UI ListView zod (packages/types/src/zod/objectql.zod.ts) plus a parallel hand-written TSinterface(objectql.ts). Both had drifted from the authoritative@objectstack/spec/uiListViewSchema, with nothing enforcing they stay in sync.This PR makes objectui's
ListViewSchemaderive from the spec's exported schema so spec-owned fields are imported (not re-typed), keeps every objectui-only/legacy field as a sanctioned local.extend()(zero runtime change), and adds a drift-guard test.Per the maintainer decision on this issue, scope is ListViewSchema only, and the legacy objectui vocabulary is kept as local extensions (migration to spec-canonical keys deferred).
What changed
ListViewSchemanow derives from spec (objectql.zod.ts). Spec-owned fields flow in by reference viaBaseSchema.extend(SpecListViewFields.shape)—filter,sort,selection,navigation,pagination,grouping,rowColor,userActions,appearance,tabs,addRecord,rowHeight,sharing,chart/treeconfigs,responsive,performance, … — so they track the protocol automatically..extend()wins): the component envelope (type: 'list-view'discriminator +objectName), the legacy objectui vocabulary (viewType,fields,filters, theshow*toolbar flags,densityMode,color, …), and the configs whose objectui shape is intentionally broader than spec's (userFilters,sharing,aria,conditionalFormatting,exportOptions, and the per-view-typekanban/calendar/gantt/gallery/timeline).SpecListViewSchema.shape.type.removeDefault()) so it can't drift.interface ListViewSchema→z.infer<typeof ListViewSchema> & ListViewRuntimeProps(objectql.ts), so the type can no longer drift from the schema (~470 hand-written lines removed). Non-serializable runtime-only props (onNavigate,onDensityChange,refreshTrigger) live in the newListViewRuntimeProps.__tests__/list-view-spec-parity.test.ts): fails if the spec grows a field objectui hasn't triaged, renames an aliased anchor (type/columns/filter), or an objectui-only field is added outside the sanctioned-local set.@objectstack/specbumped^14.6.0→^15.0.0across the workspace.packages/types/src/zod/README.md; changeset added.Compatibility
columns, legacyfields/filters/show*, legacyuserFilterstab shapes). Spec-canonical payloads (columns/filter/userActions) now validate too. Verified via runtimesafeParsechecks and the existingphase2-schemas.test.tscases.plugin-list,plugin-view,app-shell/src/views/*, …) are untouched.Verification
pnpm build— 43/43 packages build clean.@object-ui/types,plugin-list,plugin-view,app-shell,react,core,cli,plugin-detail/form/gantt/tree/timeline/map(0 errors).types(103, incl. new drift-guard),plugin-list(161),plugin-view(60),cli(33),core(1060).@object-ui/data-objectstack'sexportDownload.test.tshasvi.fn()mock-typing errors (from the freshly-installed vitest 4.x) — reproduces identically with this PR's changes reverted; out of scope.Deferred (follow-ups, per #2231)
ListViewSpeccopy (react/.../spec-bridge/bridges/list-view.ts).show*→userActions,fields→columns,filters→filter) and adopt spec's narroweraria/sub-shapes.objectName→data.provider:'object'; unify the other view schemas (FormViewSchema,ObjectViewSchema, …).🤖 Generated with Claude Code
Generated by Claude Code