Skip to content
This repository was archived by the owner on Nov 4, 2026. It is now read-only.
This repository was archived by the owner on Nov 4, 2026. It is now read-only.

finding(types): objectui#7759 groups C and D, decidable subset — five mirror-vs-declaration disagreements settled by spec precedence or read-site truth #10286

Closed

Description

@objectstack-fleet

Execution split of #7759, covering the keys in groups C and D that can be decided now. The split follows the ruling's own instruction to open one PR per group (「按组开 PR」, director ruling issuecomment-5617465269, plus ordering note 5617614225). Priority and domain are inherited from the parent (priority:p2, domain:spec). Filed by the domain:spec @ objectui execution seat, session session_01877XiBYSaRCk2CU7cMSg3S. Siblings: group E is on the parent, group B is objectui#10280, and group A is done (objectui#9364).

The keys (census on origin/main 32bf2d6f; the dev re-derives it)

pair key spec declares it? direction
form.zod.ts#FormSchema mode yes: z.enum(['create','edit','view']) (spec component.zod.ts); the mirror already matches rule 1: align the TS declaration ('edit' | 'read' | 'disabled') to the spec. The two faces share only edit (comment 5770951763). The dev measures whether any reader of FormSchema.mode (not ObjectForm's own mode) consumes read / disabled.
complex.zod.ts#FilterFieldSchema operators yes: the canonical operator vocabulary (objectui#7561) rule 1: the TS face follows the spec
complex.zod.ts#FilterBuilderSchema fields same same
navigation.zod.ts#HeaderBarSchema variant to be measured spec-declared means rule 1; otherwise rule 2 (read-site truth)
layout.zod.ts#ContainerSchema maxWidth no rule 2: true renders nothing at the one read site, so narrow the mirror to false, matching the declaration

⛔ Out of this card:

Done when

These rows leave WiderThanDeclared / WIDER_ARMS and the other ledgers. Each change has a pin that reddens on revert. There is one @object-ui/types changeset (minor, Clause-② yes).

Activity

  1. added
    domain:specobjectui spec stream: fix lands on packages/types, schema corpus or spec pin coupling — spec lane
    on Sep 24, 2026
  2. objectstack-fleet commented on Sep 24, 2026

    @objectstack-fleet
    ContributorAuthor

    Claim: PM loop round 7 — objectui#10286 (#7759 groups C and D, decidable subset): FormSchema.mode, FilterFieldSchema.operators, FilterBuilderSchema.fields, HeaderBarSchema.variant, ContainerSchema.maxWidth
    Session: session_01877XiBYSaRCk2CU7cMSg3S
    Branch: claude/issue-10286-7759-groups-cd
    Worktree: objectui-issue-10286
    Domain: domain:spec
    Seat: domain:spec#1
    File surface: packages/types/src/form.ts and zod/form.zod.ts (FormSchema only, about :882 / :1763), complex.ts and zod/complex.zod.ts (FilterFieldSchema / FilterBuilderSchema, about :471-491, only), navigation.ts and zod/navigation.zod.ts (HeaderBarSchema only), layout.ts and zod/layout.zod.ts (ContainerSchema only, about :297), the matching rows of the parity ledger, pins, and one .changeset/10286-…md
    Container & model: S, mode:subagent, model: opus (TIER_DEFAULT)
    Clause-②: yes
    Thread-read: none
    Serial constraints cleared: re-measured at 2026-09-24T15:56Z.

    Dispatch authority: objectstack-ai/objectstack#19980 (lane-scoped gate), and 「任务很多,并发保持3」 (the maintainer, in this seat's session). This fills the slot freed by #7924's dev (PR objectui#10285).

  3. objectstack-fleet commented on Sep 24, 2026

    @objectstack-fleet
    ContributorAuthor

    os-dev-report

    {
      "issue": 10286,
      "status": "done",
      "branch": "claude/issue-10286-7759-groups-cd",
      "pr": "https://github.com/objectstack-ai/objectui/pull/10300",
      "session": "session_01877XiBYSaRCk2CU7cMSg3S (the PM seat's id; this dev ran as its subagent)",
      "premise_still_valid": true,
      "summary": "Three of the five keys are settled; the fourth key, FormSchema.mode, is STOPPED and left ledgered. (1) FilterField.operators, and through its element FilterBuilderSchema.fields: both faces now state the spec's VIEW_FILTER_OPERATORS, 20 members, the same in installed spec 17.4.0 and on objectstack origin/main 67ebc84. The TS face takes the spec type by reference. The mirror spells the list out, because a raw spec value read inside a mirror would trip the objectui#8317 import boundary. It is pinned against the spec's array at runtime. (2) ContainerSchema.maxWidth: the spec does not declare it, and the renderer draws no max-w class for `true`, so the mirror's z.boolean() narrows to z.literal(false). (3) HeaderBarSchema.variant: the spec does not declare it, and the renderer reads no variant, so both faces retire it (ruling D(ii)). A real-SchemaRenderer probe rendered all four spellings byte-identical to the variant-less header. Ledger rows leave KnownDrift, WiderThanDeclared and WIDER_ARMS, and the header figures and history sentences follow. The FormSchema.mode premise is FALSIFIED for this key: the spec's create/edit/view belongs to ObjectFormPropsSchema (object-form), and there is no spec `form` node. The same probe shows no reader of any mode spelling; the only HTML difference is a leaked DOM mode attribute. That points at retirement, which changes the dispatch's direction, so it goes to open_questions. Deviations: labels and assignees were untouched, as instructed. `origin/main` moved during the run (8b1f06619), so I merged it before the final push, with no conflicts. One stray `git checkout origin/main --` with no path detached the worktree's HEAD for one step. The tree was clean and my commit was already pushed. I re-checked-out the branch at once and verified HEAD cb0cca085, a clean status and the remote sha. Nothing was lost.",
      "tests": "Final head 1ff5f45cf (merge of origin/main 8b1f06619), all under os-verify-lock. [1] `pnpm --workspace-concurrency=2 --filter '@object-ui/components^...' build` (8 projects), then `pnpm --filter @object-ui/types type-check` (tsc build + examples + tsconfig.test.json), then `pnpm --filter @object-ui/components type-check`: all exit 0. Chained under `set -e`, so each _OK marker printed only after its part exited 0. [2] `pnpm exec vitest run --maxWorkers=2 packages/types/ examples/schema-catalog/` plus 7 header-bar and container renderer tests: Test Files 255 passed (255), Tests 7307 passed (7307). [3] Gates, each exit 0: check-changeset-presence ('7 source file(s) of 1 released package(s) changed, and this change declares 1 changeset(s)'), check-changeset-no-major, check:spec-symbols, check:new-line-citations ('0 new citation(s)'), check:control-bytes, check:doc-types. Also run: check:component-surface-parity (report-only, no rows for these keys), check:changeset-claims (report-only), check:pending-changeset-literals, check:handler-key-reads. [4] ESLint narrowed to the 7 changed .ts files (`--no-inline-config --format json`): 7 files, 0 errors, 13 warnings, all pre-existing no-explicit-any on untouched lines. Population: eslint.config.js `files: ['**/*.{ts,tsx}']`. Invariance: no parserOptions.project or projectService, so no type-aware linting, and this diff cannot move any untouched file's verdict. [5] Pin mirror-groups-cd-10286.test.ts: 12/12 green. [6] Reverse verification from committed cb0cca085 via objectstack scripts/ablation-replace.mjs (anchor hit x1, blob moved, restored blob == HEAD, `git diff HEAD` empty, trap on EXIT/INT/TERM): operators leg 3/12 red; maxWidth leg 1/12 red; variant leg 2/12 red; lit controls stayed green in each leg. No rebuild was needed, because the pin imports the mirrors by relative path (src). The TS halves are @ts-expect-error lines checked by tsc -p tsconfig.test.json (green = each is refused). NOT MEASURED: plugin-form and app-shell type-check, reason: neither imports the changed types. Their FilterField / ContainerSchema hits are other same-named symbols, and FormSchema is unchanged.",
      "mcp_calls": "0",
      "api_writes": "2 — both through the fleet-write relay (objectstack-fleet[bot]): pr_create → POST /repos/objectstack-ai/objectui/pulls (draft, PR #10300); comment → POST /repos/objectstack-ai/objectui/issues/10286/comments (this report). git push is not a REST write.",
      "open_questions": [
        {
          "question": "FormSchema.mode (type 'form'): the dispatch said to align the TS face to the spec's create/edit/view, but the spec does not declare this key for the `form` node. Its create/edit/view is ObjectFormPropsSchema, the object-form block; element:form is retired whole; 'form' is in PAGE_TYPE_ROADMAP. No reader consumes any spelling. ObjectForm, ModalForm and DrawerForm read their OWN mode, and the FormSchema objects they build carry none. A real-SchemaRenderer probe shows absent / edit / read / disabled / create / view render identical HTML apart from a leaked DOM `mode` attribute on the form element. Which direction?",
          "options": [
            "A. Retire on both faces, per ruling D(ii) (both faces dead, no spec declaration): TS `mode?: never` and mirror retirementTombstone, then remove the KnownDrift and WIDER rows. Cost: one small follow-up PR, and a minor-with-breaking-note changeset (documents authoring mode on a plain form node fail validation).",
            "B. Do what the card asked: align TS to create/edit/view. Cost: both faces then declare a vocabulary nothing honours, the class ADR-0049 removes, and the key keeps leaking onto the DOM.",
            "C. Implement mode in the `form` renderer (view/read disables the inputs and hides submit). Cost: a renderer behaviour change and new product semantics for plain forms, which the card excludes."
          ],
          "recommendation": "A, because it is the ruling's own D(ii) outcome for an objectui-own key with no read site, and it matches how HeaderBarSchema.variant was settled in this PR. B would ship a declared-but-inert vocabulary. C invents behaviour no reader asked for."
        }
      ],
      "out_of_scope_findings": [
        "No class a/b/c findings. Acceptance notes only, not filed (carrier: none): (1) The condition operator vocabulary still diverges: FilterBuilderOperator has is_empty/is_not_empty and FilterOperatorSchema has is_null/is_not_null, on FilterBuilderCondition.operator, already recorded in the parity file's objectui#7760 note. (2) FilterField.operators has no read site: the vocabulary is settled, but whether to honour or retire the key is open. (3) header-bar declares title/logo/nav/left/center/right/sticky/height, which its renderer does not read. That is from source reading only; the runtime probe covered only variant. Dedupe words: filter-builder condition operator is_null is_empty; header-bar unread keys; FilterField operators unread."
      ]
    }

    Generated by Claude Code

  4. objectstack-fleet commented on Sep 24, 2026

    @objectstack-fleet
    ContributorAuthor

    ACCEPT: objectui#10286 (#7759 groups C and D, decidable subset), delivered by PR objectui#10300 at head f31d5c2. Session session_01877XiBYSaRCk2CU7cMSg3S, domain:spec @ objectui seat.

    All four keys are settled:

    key rule result
    FilterField.operators / FilterBuilderSchema.fields rule 1 both faces now state the spec's VIEW_FILTER_OPERATORS (20 members). The TS face takes it by reference; the mirror spells it out and a pin checks it against the spec array.
    ContainerSchema.maxWidth rule 2 the mirror narrows to false
    HeaderBarSchema.variant D1-(ii) retired
    FormSchema.mode D1-(ii) retired. The seat decided this after the dev's stop: the spec's create/edit/view belongs to object-form, and no reader exists. The refusal names object-form and disabled: true.

    Review: Clause-② yes. The isolated contract review record at this head, on the PR, says PASS.

    Tests: 7581 tests (types, schema-catalog and form renderers). The types, components and plugin-form type-checks pass. Every leg was reverse-verified.

    Not filed; acceptance notes only:

    • An unvalidated document still leaks the DOM mode attribute. The fix is one entry in form.tsx's strip list.
    • About 46 tests pass an inert mode: 'create' to the form component.
    • The condition operator vocabulary still diverges (objectui#7760).
    • FilterField.operators has no read site.

    HeaderBarSchema.logo (group F) still stands in this region, and objectui#10296's dev stopped on it. It follows this PR.

    Landing: flip ready and enqueue once every check on this head is green or an expected skip. ⚠️ The Spec Main Shape Gate is red on every objectui head until objectui#10287 lands.


    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

Labels

domain:specobjectui spec stream: fix lands on packages/types, schema corpus or spec pin coupling — spec lanepriority:p2

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions