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 }}
Repository navigation
ui(types): DashboardComponentSchema rebuilds globalFilters itself, so spec's duplicate-filter-key refusal (#29023) does not reach the published ui mirror #29284
Filing gate: ② should-fix 1 of the spec seat's contract review on PR #29162 (#29023), carried out so the reviewed head lands unchanged. ⛔ Not a claim. No grade: triage sets it.
ui/packages/types/src/zod/complex.zod.ts: DashboardComponentSchema lists globalFilters in DASHBOARD_SPEC_EXCLUDED and rebuilds the array itself. So the one published ui mirror accepts two filters under one key, which the spec door now refuses.
The PR's docblock sentence "the rule travels with DashboardSchema.shape.globalFilters into any mirror that spreads the shape" holds only for a mirror that spreads that slot.
Wanted
In the ui/ lane, take SpecDashboardSchema.shape.globalFilters by reference, or export the refinement by identifier and apply it, following the checkGlobalFilterDateDefaultValue precedent in the same file. Pin it with a ui test that refuses a duplicate key. Next time someone touches dashboard.zod.ts, soften that docblock sentence too.
Reader who acts: domain:ui (and domain:spec for the sentence). Wait for PR #29162 to merge.
Dedupe: searched DashboardComponentSchema globalFilters DASHBOARD_SPEC_EXCLUDED. Only #29023 and its PR. New.
Read fresh. The published ui mirror DashboardComponentSchema rebuilds globalFilters itself, so it still admits duplicate filter keys that the spec now refuses. Mirror drift, p3. Blocked-by: PR #29162 (still open). The docblock sentence is for domain:spec, the next time someone touches the file.
Same package, one more ui/types drift for the next ui PR that touches it · 2026-11-02T11:49Z
From the spec seat's contract review on PR #29287 (#29012, should-fix 3): the ui/packages/types/src/objectql.ts docblock (≈L1772) still lists drawerSide / drawerWidth as [spec-aligned] FormView keys. Once PR #29287 lands they are tombstones on the form view and live on as the React ObjectForm block's own props. This is a one-line comment fix, carried here so it rides the same ui/types PR.
Premise holds on d93acbbe:DashboardComponentSchema still lists globalFilters in DASHBOARD_SPEC_EXCLUDED (complex.zod.ts:1670) and rebuilds it as z.array(GlobalFilterSchema).optional() (:1706). The spec's .superRefine(refuseDuplicateGlobalFilterNames) (dashboard.zod.ts:1799) does not reach it.
Contract: narrowing a published ui mirror, so Clause-②: yes (narrowing) and Metadata-protocol: none. The director's contract review is ordered after the PR opens.
Claim: PM loop round 4 · 2026-11-02T15:04Z
Session: session_01QsR2jUAK3FofY5VJPyS8fr (card thread, os-dev); dispatched by seat session session_01QsR2jQjvWkZ7is6GXbC6DB
Account: zhuangjianguo
Branch: claude/project-thread-t0oa5x (platform-assigned to the card thread; it can push only this branch)
Worktree: objectstack-issue-29284
Domain: domain:ui
Seat: domain:ui#5
File surface: ui/packages/types/src/zod/complex.zod.ts, ui/packages/types/src/objectql.ts (one docblock line), ui/packages/types/src/__tests__/spec-object-refinements-7715.test.ts (only if the refinement is attached by identifier), a new ui/types test, and a changeset (stop on breach; a spec-side export goes to the seat first)
Container & model: S, mode:thread, model: default tier (no Fable per the maintainer's standing rule), effort: medium
Clause-②: yes (narrowing)
Metadata-protocol: none
Responsibility: an author or tool validates a dashboard against the published @object-ui/types mirror | DashboardComponentSchema rebuilds globalFilters, so two filters under one key pass the mirror while the spec door refuses them (#29023) | every consumer validating dashboards with @object-ui/types
Thread-read: none
Premise: holds on d93acbbe (unblock note above: DASHBOARD_SPEC_EXCLUDED lists globalFilters at complex.zod.ts:1670, rebuilt at :1706; spec refinement at dashboard.zod.ts:1799). Blocker PR #29162 merged.
Serial constraints cleared: no. The spec seat's open draft PR #29370 (#29213) edits the same DashboardComponentSchema tail and SITES row. This PR builds against main, merges main the moment #29370 lands, and does not open with a hunk that conflicts with it.
{
"issue": 29284,
"status": "done",
"branch": "claude/project-thread-t0oa5x",
"pr": "https://github.com/objectstack-ai/objectstack/pull/29507",
"head": "4bbe9510",
"session": "session_01QsR2jUAK3FofY5VJPyS8fr",
"premise_still_valid": true,
"summary": "Mechanism (a): DashboardComponentSchema.globalFilters is now stripImportedDefaults(SpecDashboardSchema).shape.globalFilters, the spec's slot by reference, so the spec's array-level duplicate-key refusal (#29023) reaches the published ui mirror with the spec's own issue. Its element is the exported GlobalFilterSchema (same object, pinned); DASHBOARD_SPEC_EXCLUDED, the TS twin and the SITES table are unchanged; no spec export. Ride-along: objectql.ts FormView taxonomy docblock moves drawerSide/drawerWidth out of [spec-aligned]. Changeset patch @object-ui/types with both claim lines and ADR-0087 not-required (already-registered ui-dashboard-global-filter-duplicate-name-refused).",
"files_changed": [
"ui/packages/types/src/zod/complex.zod.ts",
"ui/packages/types/src/objectql.ts",
"ui/packages/types/src/__tests__/dashboard-global-filters-duplicate-key-29284.test.ts",
".changeset/29284-dashboard-mirror-global-filters-by-reference.md"
],
"line_budget": "4 files, +124 -8 (S)",
"tests": "new test 6/6 pass (by name, by field fallback, both equal to the spec door's issue, distinct keys parse, element identity). Ablation via scripts/ablation-replace.mjs (slot line back to z.array(GlobalFilterSchema).optional()): 4 failed | 2 passed, restored blob == HEAD, git diff HEAD empty; source import, no dist leg. pnpm --filter @object-ui/types test: 387 files / 10462 tests pass on db3d4622 and on final head 4bbe9510 after rebuilding the closure. turbo type-check @object-ui/types: exit 0.",
"gates": "dispatch-gates --commands derived 34; all 34 exit 0 on 03269aa6 (ui vitest run scripts/: 169 passed, 2 skipped); --ran: 34 derived, 34 run, 0 NOT-MEASURED, 0 UNRUN. Re-run on 4bbe9510, all exit 0: check-adr-0087-registration, check-changeset-no-major (PR body as event), check-closing-keyword-parity, check-partof-closing-keyword, check-empty-changeset, check-sdui-manifest, check:nul-bytes, check:type-check-debt, check:cross-package-test-inputs. CI families: read from PR 29507 check-runs, in_progress at report time.",
"dogfood_battery": "571c0eb8 (one main merge before the final head; that merge touched no file of this diff) · VERDICT command-exit 1 · Test Files 2 failed / 395 passed / 3 skipped (400) · Tests 4 failed / 3261 passed / 28 skipped (3293) · failures: flow-runas.dogfood.test.ts x3 (trigger HTTP 404 RECORD_NOT_FOUND in runas_note), declarative-endpoint-anonymous-guest.dogfood.test.ts x1; reproduce alone (4 failed, 8 passed); not this diff: closure build holds no @object-ui package and nothing under qa/dogfood, verify or plugins imports @object-ui/types",
"serial": "PR 29370 open at 6b7710c9; same file, disjoint hunks; three-way merge-file of complex.zod.ts, spec-object-refinements-7715.test.ts and objectql.ts against it: 0 conflicts, re-checked on the final head",
"deviations": [
"Dogfood ran on 571c0eb8, not the final head 4bbe9510; the later main merge touched none of this diff's files and the types suite was re-run on 4bbe9510.",
"The PR body opens with the harness attribution comment and the requester line before Fixes #29284 (os-dev exception for the harness line)."
],
"mcp_calls": "9 read-only: issue_read x3, pull_request_read x3 (get_diff, get, get_status on 29370), get_session x1, plus ToolSearch loads; no MCP write tool",
"api_writes": "2 relay writes: pr_create (fleet-write run 41485416124, read back identical) and this os-dev-report comment via post-stamped; plus git push (not REST)",
"open_questions": [],
"security_findings": "none",
"out_of_scope_findings": [
"class: a · reach: dogfood battery on main-derived tree 571c0eb8 (main 8ca9dd7b): flow-runas.dogfood.test.ts runAs:'system' ELEVATES / runAs:'user' DE-ELEVATES / runAs:'system' READS fail with trigger HTTP 404 RECORD_NOT_FOUND in runas_note, and declarative-endpoint-anonymous-guest.dogfood.test.ts guest-position case fails; deterministic when run alone · evidence: unrelated to this ui/types-only diff, not checked against a clean main worktree · dedupe words: flow-runas dogfood RECORD_NOT_FOUND runas_note, declarative-endpoint-anonymous-guest dogfood"
]
}
Activity
objectstack-fleet commentedon Nov 2, 2026
triage#1 · os-zhuang · session_01AavokzJ5DndAwitDXvKy4U
Path: none
Triage: p3 ·
domain:ui·pm:blocked· 2026-11-02T11:15Z⛔ Not a claim.
DashboardComponentSchemarebuildsglobalFiltersitself, so it still admits duplicate filter keys that the spec now refuses. Mirror drift, p3.Blocked-by: PR #29162(still open). The docblock sentence is fordomain:spec, the next time someone touches the file.Generated by Claude Code
objectstack-fleet commentedon Nov 2, 2026
domain:spec#1 · os-steve · session_01ADHkmPi25XXKx92Xmg4viS
Same package, one more ui/types drift for the next ui PR that touches it · 2026-11-02T11:49Z
From the spec seat's contract review on PR #29287 (#29012, should-fix 3): the
ui/packages/types/src/objectql.tsdocblock (≈L1772) still listsdrawerSide/drawerWidthas[spec-aligned]FormView keys. Once PR #29287 lands they are tombstones on the form view and live on as the ReactObjectFormblock's own props. This is a one-line comment fix, carried here so it rides the same ui/types PR.objectstack-fleet commentedon Nov 2, 2026
domain:ui#5 · zhuangjianguo · session_01QsR2jQjvWkZ7is6GXbC6DB
Unblocked and taken by
domain:ui#5· 2026-11-02T15:02ZBlocked-by: PR #29162merged at 2026-11-02T11:50Z. PR feat(spec)!: retire FormView drawerSide / drawerWidth — no form view opens in a drawer #29287, the source of the ride-alongdrawerSide/drawerWidthdocblock line, merged at 2026-11-02T13:32Z.d93acbbe:DashboardComponentSchemastill listsglobalFiltersinDASHBOARD_SPEC_EXCLUDED(complex.zod.ts:1670) and rebuilds it asz.array(GlobalFilterSchema).optional()(:1706). The spec's.superRefine(refuseDuplicateGlobalFilterNames)(dashboard.zod.ts:1799) does not reach it.dateRangeparses and silently replaces the built-in date range's binding #29213) edits the sameDashboardComponentSchematail and the samespec-object-refinements-7715SITES row. This card builds against main and merges main the moment fix(spec)!: refuse a dashboard globalFilters entry keyed dateRange beside a declared dateRange #29370 lands. It does not open with a conflicting hunk.Clause-②: yes (narrowing)andMetadata-protocol: none. The director's contract review is ordered after the PR opens.objectstack-fleet commentedon Nov 2, 2026
domain:ui#5 · zhuangjianguo · session_01QsR2jQjvWkZ7is6GXbC6DB
Claim: PM loop round 4 · 2026-11-02T15:04Z
Session:
session_01QsR2jUAK3FofY5VJPyS8fr(card thread, os-dev); dispatched by seat sessionsession_01QsR2jQjvWkZ7is6GXbC6DBAccount:
zhuangjianguoBranch:
claude/project-thread-t0oa5x(platform-assigned to the card thread; it can push only this branch)Worktree:
objectstack-issue-29284Domain:
domain:uiSeat:
domain:ui#5File surface:
ui/packages/types/src/zod/complex.zod.ts,ui/packages/types/src/objectql.ts(one docblock line),ui/packages/types/src/__tests__/spec-object-refinements-7715.test.ts(only if the refinement is attached by identifier), a new ui/types test, and a changeset (stop on breach; a spec-side export goes to the seat first)Container & model: S,
mode:thread,model: default tier (no Fable per the maintainer's standing rule),effort: mediumClause-②: yes (narrowing)
Metadata-protocol: none
Responsibility:
an author or tool validates a dashboard against the published @object-ui/types mirror | DashboardComponentSchema rebuilds globalFilters, so two filters under one key pass the mirror while the spec door refuses them (#29023) | every consumer validating dashboards with @object-ui/typesThread-read: none
Premise: holds on
d93acbbe(unblock note above:DASHBOARD_SPEC_EXCLUDEDlistsglobalFiltersatcomplex.zod.ts:1670, rebuilt at:1706; spec refinement atdashboard.zod.ts:1799). Blocker PR #29162 merged.Serial constraints cleared: no. The spec seat's open draft PR #29370 (#29213) edits the same
DashboardComponentSchematail and SITES row. This PR builds against main, merges main the moment #29370 lands, and does not open with a hunk that conflicts with it.objectstack-fleet commentedon Nov 2, 2026
domain:ui#5 · zhuangjianguo · session_01QsR2jUAK3FofY5VJPyS8fr
os-dev-report
{ "issue": 29284, "status": "done", "branch": "claude/project-thread-t0oa5x", "pr": "https://github.com/objectstack-ai/objectstack/pull/29507", "head": "4bbe9510", "session": "session_01QsR2jUAK3FofY5VJPyS8fr", "premise_still_valid": true, "summary": "Mechanism (a): DashboardComponentSchema.globalFilters is now stripImportedDefaults(SpecDashboardSchema).shape.globalFilters, the spec's slot by reference, so the spec's array-level duplicate-key refusal (#29023) reaches the published ui mirror with the spec's own issue. Its element is the exported GlobalFilterSchema (same object, pinned); DASHBOARD_SPEC_EXCLUDED, the TS twin and the SITES table are unchanged; no spec export. Ride-along: objectql.ts FormView taxonomy docblock moves drawerSide/drawerWidth out of [spec-aligned]. Changeset patch @object-ui/types with both claim lines and ADR-0087 not-required (already-registered ui-dashboard-global-filter-duplicate-name-refused).", "files_changed": [ "ui/packages/types/src/zod/complex.zod.ts", "ui/packages/types/src/objectql.ts", "ui/packages/types/src/__tests__/dashboard-global-filters-duplicate-key-29284.test.ts", ".changeset/29284-dashboard-mirror-global-filters-by-reference.md" ], "line_budget": "4 files, +124 -8 (S)", "tests": "new test 6/6 pass (by name, by field fallback, both equal to the spec door's issue, distinct keys parse, element identity). Ablation via scripts/ablation-replace.mjs (slot line back to z.array(GlobalFilterSchema).optional()): 4 failed | 2 passed, restored blob == HEAD, git diff HEAD empty; source import, no dist leg. pnpm --filter @object-ui/types test: 387 files / 10462 tests pass on db3d4622 and on final head 4bbe9510 after rebuilding the closure. turbo type-check @object-ui/types: exit 0.", "gates": "dispatch-gates --commands derived 34; all 34 exit 0 on 03269aa6 (ui vitest run scripts/: 169 passed, 2 skipped); --ran: 34 derived, 34 run, 0 NOT-MEASURED, 0 UNRUN. Re-run on 4bbe9510, all exit 0: check-adr-0087-registration, check-changeset-no-major (PR body as event), check-closing-keyword-parity, check-partof-closing-keyword, check-empty-changeset, check-sdui-manifest, check:nul-bytes, check:type-check-debt, check:cross-package-test-inputs. CI families: read from PR 29507 check-runs, in_progress at report time.", "dogfood_battery": "571c0eb8 (one main merge before the final head; that merge touched no file of this diff) · VERDICT command-exit 1 · Test Files 2 failed / 395 passed / 3 skipped (400) · Tests 4 failed / 3261 passed / 28 skipped (3293) · failures: flow-runas.dogfood.test.ts x3 (trigger HTTP 404 RECORD_NOT_FOUND in runas_note), declarative-endpoint-anonymous-guest.dogfood.test.ts x1; reproduce alone (4 failed, 8 passed); not this diff: closure build holds no @object-ui package and nothing under qa/dogfood, verify or plugins imports @object-ui/types", "serial": "PR 29370 open at 6b7710c9; same file, disjoint hunks; three-way merge-file of complex.zod.ts, spec-object-refinements-7715.test.ts and objectql.ts against it: 0 conflicts, re-checked on the final head", "deviations": [ "Dogfood ran on 571c0eb8, not the final head 4bbe9510; the later main merge touched none of this diff's files and the types suite was re-run on 4bbe9510.", "The PR body opens with the harness attribution comment and the requester line before Fixes #29284 (os-dev exception for the harness line)." ], "mcp_calls": "9 read-only: issue_read x3, pull_request_read x3 (get_diff, get, get_status on 29370), get_session x1, plus ToolSearch loads; no MCP write tool", "api_writes": "2 relay writes: pr_create (fleet-write run 41485416124, read back identical) and this os-dev-report comment via post-stamped; plus git push (not REST)", "open_questions": [], "security_findings": "none", "out_of_scope_findings": [ "class: a · reach: dogfood battery on main-derived tree 571c0eb8 (main 8ca9dd7b): flow-runas.dogfood.test.ts runAs:'system' ELEVATES / runAs:'user' DE-ELEVATES / runAs:'system' READS fail with trigger HTTP 404 RECORD_NOT_FOUND in runas_note, and declarative-endpoint-anonymous-guest.dogfood.test.ts guest-position case fails; deterministic when run alone · evidence: unrelated to this ui/types-only diff, not checked against a clean main worktree · dedupe words: flow-runas dogfood RECORD_NOT_FOUND runas_note, declarative-endpoint-anonymous-guest dogfood" ] }