Filed unassigned by the domain:spec@objectui PM seat, session session_01Jmxdo7bmeqCQHLSfmLVX9w, carving group E out of objectui#7759 so it can be implemented. objectui#7759's own charter is measurement-and-proposal — "this card changes no source file and opens no PR" — so the implementation lane needs its own card. ⛔ objectui#7759 stays open and unclaimed.
⭐ A ruling already exists and this is the part its sweep missed. Director batch #112 delegated exactly this to the seat: 「E 组由席位按 #6124 直接派」 — dispatch group E against objectui#6124 directly, ⛔ without spending a maintainer letter.
The ruling
objectui#6124, maintainer ruling 2026-08-30 (Q2 → A with C): replace z.function() handler mirrors with a named refusal arm. The machinery is in-tree — handlerKeyRefusal(key, disposition, label?) at packages/types/src/zod/tombstone.zod.ts:109, with HandlerKeyDisposition at :69.
Premise re-derived on origin/main before filing
| reading |
value |
handlerKeyRefusal defined |
tombstone.zod.ts:109 |
surviving z.function( in data-display.zod.ts (907 lines) |
3 |
surviving z.function( in form.zod.ts (861 lines) |
2 |
⭐ The control that makes this a residue and not an unswept file: handlerKeyRefusal( already appears 8× in data-display.zod.ts and 20× in form.zod.ts. ⇒ the objectui#6124 sweep demonstrably did reach these exact files; these five are what it left behind. A file the ruling never touched would show 0.
Sites located (⛔ re-derive every address — this seat has had line numbers rot twice tonight):
data-display.zod.ts:157 — cell: z.function().optional().describe('Custom cell renderer')
data-display.zod.ts:314 — renderCellEditor: z.function().optional().describe(…)
form.zod.ts:175 — validate: z.function().optional().describe('Custom validation function')
form.zod.ts:186 — custom: z.function().optional().describe('Custom condition function')
⚠️ objectui#7759's proposal F moves FormFieldSchema::validation into this group: measured member-by-member it is not structural — FieldConstraintsSchema and FieldValidationRules agree on all seven members except validate, which is the z.function() above. On main, form.zod.ts:618 is validation: FieldConstraintsSchema.optional() and :619 is condition: FieldConditionSchema.optional() — both structural references whose referenced schema carries the function. ⭐ Decide explicitly whether fixing FieldConstraintsSchema::validate and FieldConditionSchema::custom discharges them, and say which.
⚠️ data-display.zod.ts:250 is NOT one of these
cell: retirementTombstone('RETIRED (objectui#5474) — never read by the static table; use data-table') — already retired by a different ruling, a different mechanism. ⛔ Do not touch it, and ⛔ do not confuse it with :157, which is a live z.function() on a different schema.
What is owed
- Re-derive the surviving
z.function() population yourself, with the handlerKeyRefusal count as your firing control, and report it. ⛔ Do not trust the figures above.
- Convert each to a named refusal arm using the existing
handlerKeyRefusal machinery. ⛔ Do not invent a second mechanism — 20 call sites in one file are the house pattern.
- ⭐ Each key's
HandlerKeyDisposition is a judgement about what the TypeScript twin does. Read the twin per key and say what you read; ⛔ do not pick a disposition by analogy with a neighbour.
- A firing control per key: the refusal must be shown refusing by name, and a control key that still parses green.
- ⚠️
renderCellEditor's docblock says "z.function() encodes no parameter shape, so the member on DataTableSchema is the authority for it". ⛔ Check whether the refusal preserves that pointer, or whether it strips the only place the parameter shape is documented.
Clause-②: yes — this narrows the accept set on a published authoring face, which is exactly why director batch #112 put every mirror-narrowing proposal at yes. ⛔ Declared yes on that ground and on the charter tie-break, ⛔ not because a widening tell fired.
⛔ The maintainer's ordering rule governs this card
Verbatim, from the director's batch #112 note: 「我们的项目以 objectstack 协议为准,文档应该以实际实现为准。协议不正确的应该先修改协议。」 and its ordering gloss: 凡「实现或立 spec 卡退役」处,先判协议对不对;判协议不对的,spec 卡先行、本卡阻塞其上。
⇒ ⛔ Never narrow or widen a spec-declared shape locally in objectui. ⛔ Never add an author-writable key the spec does not declare. If you judge the protocol itself wrong, the deliverable is stop and say so — a spec card goes first and this card blocks on it.
Standing rules — read every line, they are not boilerplate
Identity. The card is assigned and the Claim: on it is yours; it names your branch. ⛔ Never write the assignee field. ⛔ Never post a second Claim:. If the newest Claim: names another branch, stop and report.
Container hazards.
/home/user/objectui is SHALLOW with a STALE origin/main. ⛔ Never git fetch, git checkout, or cut a worktree there. Clone fresh into your own scratchpad subdirectory.
/home/user/objectstack is a shared primary checkout — read-only.
- ⛔ Never
git stash. ⛔ Never kill a process by name. ⛔ Never mutate node_modules. ⛔ Never touch content/docs/releases/.
- ⛔ These do NOT exist in objectui and are never a red you can wait for:
scripts/pm/os-regen-merge.sh, scripts/pm/check-widening-tells.mjs, scripts/pm/check-clause2-carriers.mjs.
Measurement discipline.
- ⛔ Never write "(no output above = clean)" or any unconditional false-clean echo. Print the command and the exit code.
- ⭐ A control is only a control if it is known to fire in the region being tested. ⚠️ Two true negatives are not a reading.
- ⛔ A bad probe value is not a reading — a multi-line
grep -F pattern is split into OR'd patterns and is one. ⛔ An empty gate section is a FAILED RUN.
- ⛔ Never quote a bare
grep -c without its exact command.
- ⛔ A claim written in the tree is a claim, not a reading — a docblock, a card body, a triage comment. Three devs refuted this seat tonight by measuring something I had quoted from in-tree prose. Refute me the same way if the measurement says so.
- Read the stored body back after every GitHub write and report what came back.
Deliverable. Worktree → code → tests → changeset → push → draft PR carrying needs:contract-review. ⛔ Do not flip ready, ⛔ do not enqueue, ⛔ no auto-merge — landing is the seat's. Report structured JSON: PR number and head sha, every premise confirmed or refuted with exact commands, your firing controls, and CI as total / success / skipped / non-green plus whether the reported total_count equals the returned array length.
Generated by Claude Code
Filed unassigned by the
domain:spec@objectuiPM seat, sessionsession_01Jmxdo7bmeqCQHLSfmLVX9w, carving group E out of objectui#7759 so it can be implemented. objectui#7759's own charter is measurement-and-proposal — "this card changes no source file and opens no PR" — so the implementation lane needs its own card. ⛔ objectui#7759 stays open and unclaimed.⭐ A ruling already exists and this is the part its sweep missed. Director batch #112 delegated exactly this to the seat: 「E 组由席位按 #6124 直接派」 — dispatch group E against objectui#6124 directly, ⛔ without spending a maintainer letter.
The ruling
objectui#6124, maintainer ruling 2026-08-30 (Q2 → A with C): replace
z.function()handler mirrors with a named refusal arm. The machinery is in-tree —handlerKeyRefusal(key, disposition, label?)atpackages/types/src/zod/tombstone.zod.ts:109, withHandlerKeyDispositionat:69.Premise re-derived on
origin/mainbefore filinghandlerKeyRefusaldefinedtombstone.zod.ts:109z.function(indata-display.zod.ts(907 lines)z.function(inform.zod.ts(861 lines)⭐ The control that makes this a residue and not an unswept file:
handlerKeyRefusal(already appears 8× indata-display.zod.tsand 20× inform.zod.ts. ⇒ the objectui#6124 sweep demonstrably did reach these exact files; these five are what it left behind. A file the ruling never touched would show 0.Sites located (⛔ re-derive every address — this seat has had line numbers rot twice tonight):
data-display.zod.ts:157—cell: z.function().optional().describe('Custom cell renderer')data-display.zod.ts:314—renderCellEditor: z.function().optional().describe(…)form.zod.ts:175—validate: z.function().optional().describe('Custom validation function')form.zod.ts:186—custom: z.function().optional().describe('Custom condition function')FormFieldSchema::validationinto this group: measured member-by-member it is not structural —FieldConstraintsSchemaandFieldValidationRulesagree on all seven members exceptvalidate, which is thez.function()above. Onmain,form.zod.ts:618isvalidation: FieldConstraintsSchema.optional()and:619iscondition: FieldConditionSchema.optional()— both structural references whose referenced schema carries the function. ⭐ Decide explicitly whether fixingFieldConstraintsSchema::validateandFieldConditionSchema::customdischarges them, and say which.data-display.zod.ts:250is NOT one of thesecell: retirementTombstone('RETIRED (objectui#5474) — never read by the static table; use data-table')— already retired by a different ruling, a different mechanism. ⛔ Do not touch it, and ⛔ do not confuse it with:157, which is a livez.function()on a different schema.What is owed
z.function()population yourself, with thehandlerKeyRefusalcount as your firing control, and report it. ⛔ Do not trust the figures above.handlerKeyRefusalmachinery. ⛔ Do not invent a second mechanism — 20 call sites in one file are the house pattern.HandlerKeyDispositionis a judgement about what the TypeScript twin does. Read the twin per key and say what you read; ⛔ do not pick a disposition by analogy with a neighbour.renderCellEditor's docblock says "z.function()encodes no parameter shape, so the member onDataTableSchemais the authority for it". ⛔ Check whether the refusal preserves that pointer, or whether it strips the only place the parameter shape is documented.Clause-②: yes— this narrows the accept set on a published authoring face, which is exactly why director batch #112 put every mirror-narrowing proposal atyes. ⛔ Declaredyeson that ground and on the charter tie-break, ⛔ not because a widening tell fired.⛔ The maintainer's ordering rule governs this card
Verbatim, from the director's batch #112 note: 「我们的项目以 objectstack 协议为准,文档应该以实际实现为准。协议不正确的应该先修改协议。」 and its ordering gloss: 凡「实现或立 spec 卡退役」处,先判协议对不对;判协议不对的,spec 卡先行、本卡阻塞其上。
⇒ ⛔ Never narrow or widen a spec-declared shape locally in objectui. ⛔ Never add an author-writable key the spec does not declare. If you judge the protocol itself wrong, the deliverable is stop and say so — a spec card goes first and this card blocks on it.
Standing rules — read every line, they are not boilerplate
Identity. The card is assigned and the
Claim:on it is yours; it names your branch. ⛔ Never write the assignee field. ⛔ Never post a secondClaim:. If the newestClaim:names another branch, stop and report.Container hazards.
/home/user/objectuiis SHALLOW with a STALEorigin/main. ⛔ Nevergit fetch,git checkout, or cut a worktree there. Clone fresh into your own scratchpad subdirectory./home/user/objectstackis a shared primary checkout — read-only.git stash. ⛔ Never kill a process by name. ⛔ Never mutatenode_modules. ⛔ Never touchcontent/docs/releases/.scripts/pm/os-regen-merge.sh,scripts/pm/check-widening-tells.mjs,scripts/pm/check-clause2-carriers.mjs.Measurement discipline.
grep -Fpattern is split into OR'd patterns and is one. ⛔ An empty gate section is a FAILED RUN.grep -cwithout its exact command.Deliverable. Worktree → code → tests → changeset → push → draft PR carrying
needs:contract-review. ⛔ Do not flip ready, ⛔ do not enqueue, ⛔ no auto-merge — landing is the seat's. Report structured JSON: PR number and head sha, every premise confirmed or refuted with exact commands, your firing controls, and CI as total / success / skipped / non-green plus whether the reportedtotal_countequals the returned array length.Generated by Claude Code