Filed by the domain:spec @ objectui PM seat, session session_01Jmxdo7bmeqCQHLSfmLVX9w, as option C of the ruling recorded on this shift.
Maintainer ruling, 2026-09-09: "A now, C as the follow-up card." ⇒ ⛔ this card is not asking whether to do it. It is asking the implementing seat to do exactly C and nothing wider.
What happened
Retiring the bare kanban node type (objectui#8802, PR #8865) removed the only schema face that judged several things. The dev surfaced this as an open question during execution rather than after — the right time.
KanbanSchema (the retired arm) was the only face that:
- declared
columns / cardTitle / swimlaneField / grouping / navigation;
- refused by name
allowCollapse / cardTemplates / columnWidths / titleField / draggable / onColumnAdd / onCardAdd;
- ⭐ judged a lane's
cards, through columns: KanbanColumn[] — which is objectui#6939's actual defect fix.
The surviving ObjectKanbanSchema declares none of them, while ObjectKanban still reads all of them.
⇒ The family went from judging several of 13 read keys to judging 5.
⛔ What this card is NOT
- ⛔ Not option B. It does not declare the missing scalar keys (
cardTitle, swimlaneField, grouping, navigation, or the refusal set). That would widen a published accept set, needs its own ruling, and re-opens the settled question of which keys the object-bound board honours. The maintainer chose C over B deliberately.
- ⛔ Not a claim that anything regressed for authors. No
object-kanban document changes meaning: it was never judged by the kanban arm. What was lost is judging that only ever applied to the retired spelling.
- ⛔ Not a re-opening of objectui#8802's ruling.
The scope: one declaration
Declare on ObjectKanbanSchema — TS face and zod mirror, moving together:
columns?: KanbanColumn[]; // TS
columns: z.array(KanbanColumnSchema)… // zod mirror
⇒ This restores the judging half only: a lane's shape and its cards are checked again. The scalar surface is untouched.
⚠️ Direction check the implementing seat owes. BaseSchema closes with [key: string]: any and .passthrough(). On such a face a declaration cannot widen — it can only narrow, by adding validation where there was none. Verify that this is that case before writing the PR body, and state it in the strict/lenient vocabulary. If it turns out to widen anything, ⛔ STOP and report: that flips the clause-② verdict and this becomes option B, which is not ruled.
What is measurably wrong today, and should be the pin
The dev recorded the concrete consequences of the loss. Each is a candidate assertion:
columns[].items now parses green (it is not a declared member of a lane, and nothing refuses it);
- a card with no
title now parses green;
- three handler keys are read but undeclared.
⇒ The pin should assert the restored refusals, each with a firing control showing the same document was accepted before. ⛔ A pin that only asserts a good document parses would have passed before this card too and would pin nothing.
⚠️ Two facts the implementing seat must not rediscover the hard way
- The two schema-catalog fixtures needed
groupBy and data: [] added during the retirement, because the object-kanban face refuses a purely static board (lanes carrying their own cards, no groupBy, no record source). Their rendered DOM is byte-identical afterwards — the sha256/tag/element pins in kanban-column-cards-6939.test.tsx pass unchanged — because both spellings always resolved to the same renderer. ⇒ if this card's declaration interacts with that refusal, say so; a static board is exactly the shape columns[].cards judging is about.
SchemaRegistry (packages/types/src/registry.ts) has never carried an object-kanban entry, so with 'kanban' retired the kanban family has no entry in that map at all and ComponentType no longer offers any kanban node type. ⛔ Adding one widens ComponentType and is a ruling of its own — carrier objectui#7665. ⛔ Do not fix it here.
Refs: objectui#8802 / PR #8865 (the retirement that created this) · objectui#6939 (the lane/card judging defect whose fix is what was lost) · objectui#7665 (SchemaRegistry coverage) · objectui#7322 · ADR-0049.
Filed by the
domain:spec@ objectui PM seat, sessionsession_01Jmxdo7bmeqCQHLSfmLVX9w, as option C of the ruling recorded on this shift.Maintainer ruling, 2026-09-09: "A now, C as the follow-up card." ⇒ ⛔ this card is not asking whether to do it. It is asking the implementing seat to do exactly C and nothing wider.
What happened
Retiring the bare
kanbannode type (objectui#8802, PR #8865) removed the only schema face that judged several things. The dev surfaced this as an open question during execution rather than after — the right time.KanbanSchema(the retired arm) was the only face that:columns/cardTitle/swimlaneField/grouping/navigation;allowCollapse/cardTemplates/columnWidths/titleField/draggable/onColumnAdd/onCardAdd;cards, throughcolumns: KanbanColumn[]— which is objectui#6939's actual defect fix.The surviving
ObjectKanbanSchemadeclares none of them, whileObjectKanbanstill reads all of them.⇒ The family went from judging several of 13 read keys to judging 5.
⛔ What this card is NOT
cardTitle,swimlaneField,grouping,navigation, or the refusal set). That would widen a published accept set, needs its own ruling, and re-opens the settled question of which keys the object-bound board honours. The maintainer chose C over B deliberately.object-kanbandocument changes meaning: it was never judged by thekanbanarm. What was lost is judging that only ever applied to the retired spelling.The scope: one declaration
Declare on
ObjectKanbanSchema— TS face and zod mirror, moving together:⇒ This restores the judging half only: a lane's shape and its
cardsare checked again. The scalar surface is untouched.BaseSchemacloses with[key: string]: anyand.passthrough(). On such a face a declaration cannot widen — it can only narrow, by adding validation where there was none. Verify that this is that case before writing the PR body, and state it in the strict/lenient vocabulary. If it turns out to widen anything, ⛔ STOP and report: that flips the clause-② verdict and this becomes option B, which is not ruled.What is measurably wrong today, and should be the pin
The dev recorded the concrete consequences of the loss. Each is a candidate assertion:
columns[].itemsnow parses green (it is not a declared member of a lane, and nothing refuses it);titlenow parses green;⇒ The pin should assert the restored refusals, each with a firing control showing the same document was accepted before. ⛔ A pin that only asserts a good document parses would have passed before this card too and would pin nothing.
groupByanddata: []added during the retirement, because theobject-kanbanface refuses a purely static board (lanes carrying their own cards, nogroupBy, no record source). Their rendered DOM is byte-identical afterwards — the sha256/tag/element pins inkanban-column-cards-6939.test.tsxpass unchanged — because both spellings always resolved to the same renderer. ⇒ if this card's declaration interacts with that refusal, say so; a static board is exactly the shapecolumns[].cardsjudging is about.SchemaRegistry(packages/types/src/registry.ts) has never carried anobject-kanbanentry, so with'kanban'retired the kanban family has no entry in that map at all andComponentTypeno longer offers any kanban node type. ⛔ Adding one widensComponentTypeand is a ruling of its own — carrier objectui#7665. ⛔ Do not fix it here.Refs: objectui#8802 / PR #8865 (the retirement that created this) · objectui#6939 (the lane/card judging defect whose fix is what was lost) · objectui#7665 (
SchemaRegistrycoverage) · objectui#7322 · ADR-0049.