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 }}
This repository was archived by the owner on Nov 4, 2026. It is now read-only.
Repository navigation
This repository was archived by the owner on Nov 4, 2026. It is now read-only.
fields: a formula cell with no declared result type prints the raw number in monospace, and the datetime cell's date and time have no separator in the copied text #11683
Path: ② the capabilities an end user meets in the app — field rendering | 缺项 | P2
Split by the triage seat (objectstack-wide, seat post objectstack-ai/objectstack#6015) · session_01AavokzJ5DndAwitDXvKy4U from objectui#11672 (the 2026-10-06 console dogfood sweep, showcase, framework ce577ec4), items 10 (formula) and 16 (datetime cell). Re-read on objectui main (848ba0e12f) before filing: still live, with no open duplicate. ⛔ Not a claim, ⛔ not a dispatch.
Triage: lands in packages/fields/src/index.tsx (the formula cell about :2636–:2645; the datetime cell about :1251–:1252) ⇒ domain:ui; rationale: two cell renderers in one file format their text by hand.
What happens
Projects' Budget Remaining (a formula with no declared result type) renders 200000, unformatted and in monospace, next to a formatted currency column. A datetime cell renders "2026/10/6上午1:42": the gap is only an ml-2 margin, not text, so the copied and read value has no separator.
Done when
An untyped formula's numeric result is formatted as a number. The dev reads whether the formula's inputs give a better type, for example currency.
The datetime cell's text carries a real separator.
domain:ui seat 1 · session_01DrKzdPdyLLBW3qpZ4vtk7z · read 2026-10-06T15:46Z. ⛔ Not a claim, ⛔ not a dispatch.
This card was next in the lane's order, but its file surface (packages/fields/src/index.tsx, the formula cell about :2636–:2645 and the datetime cell about :1251–:1252) intersects in-flight area:records work:
objectui#11690 (pm:dispatched, claimed by another seat) edits the percent progress bar in the same file (about :863).
objectui#11689 (pm:dispatched) now also carries BooleanCellRenderer's hard-coded words in the same file (about :933–:947; family comment 6019099345).
The pm-dispatch rule allows at most one in-flight card per area:* axis unless the file surfaces are disjoint, so this card waits for objectui#11690 to land.
Known pits for the claimant: re-read the formula and datetime cell renderers on main after objectui#11690 and objectui#11689 land. Line numbers in this card will have moved, and BooleanCellRenderer's neighbourhood may have gained translated-word plumbing that the datetime separator can reuse.
Claim: PM loop round 1
Session: session_01CGZy1BGCjdN5cXqL9cnvB8
Account: os-support-ai
Branch: claude/issue-11683-formula-datetime-cells
Worktree: objectui-issue-11683
Domain: domain:ui
Seat: domain:ui#3
File surface: packages/fields/src/index.tsx — FormulaCellRenderer (about :2649) and DateTimeCellRenderer (about :1134–:1266, the ml-2 time span) only; the tests beside them; and .changeset/11683-*.md (stop on breach; explain in the report). ⛔ Not packages/core/src/utils/date-display.ts: this seat's PR objectui#11729 (objectui#11693, awaiting the maintainer's decision) holds it.
Container & model: M, mode:subagent, model: opus (dispatch-gates --tier --repo objectstack-ai/objectui: no path-derived mandate; default tier)
Clause-②: no
Thread-read: 6019992174
Serial constraints cleared: none blocking. objectui#11690 (PR objectui#11732, the percent cell in this file) merged as 9fc68aa at 2026-10-06T20:02Z; objectui#11689 (BooleanCellRenderer) landed as 22b503c earlier. Seat 1's deferral 6019992174 named both. No open objectui PR touches packages/fields/src/index.tsx (read 2026-10-06T20:06Z). Fold-or-serial with objectui#11697 (JsonCellRenderer, same file, same axis): serial, not folded. The two cards share a file, but not a defect shape or a fix (number formatting and a text separator here; a structured display of composite values there). objectui#11697 waits for this card (seat post §3). objectui#11733 (in flight, same axis) is on other files.
Why Clause-②: no: two cell renderers change what they draw. No accepted input, export or prop is added. If the separator needs a new locale key, the dev reports it before opening the PR, and the seat amends this line.
{
"issue": 11683,
"status": "done",
"branch": "claude/issue-11683-formula-datetime-cells",
"pr": "https://github.com/objectstack-ai/objectui/pull/11747",
"session": "session_01CGZy1BGCjdN5cXqL9cnvB8 — the parent's id (mode:subagent), as the dispatch names it",
"premise_still_valid": true,
"summary": "FormulaCellRenderer now draws a numeric result through NumberCellRenderer (formatNumberFieldValue: locale grouping, the width resolveFieldScale answers, a declared formula scale honoured, no monospace). A result is numeric when returnType is 'number', or when no returnType is declared and the value is a JS number; a digit string with no returnType and any other declared returnType draw as before. summary shares the renderer, so a numeric roll-up is formatted too. DateTimeCellRenderer's compact face puts a text space between the date and time spans (time keeps text-muted-foreground, margin ml-2 to ml-1), so textContent equals formatDateTime(value, {style:'compact'}): '10/6/2026 1:42 am' (en-US), '2026/10/6 上午1:42' (zh-CN). The card's reading (do the inputs give a better type, e.g. currency): no, not in the renderer. Spec 17.6.0 returnType is number|text|boolean|date (no currency), and the spec's field form says of returnType that consumers read it 'instead of re-parsing the expression'; inferring currency from Budget Remaining's two currency inputs would mean parsing CEL in the renderer, so it renders as a grouped number. Fix landed at the producer named by Zone 2 (packages/fields/src/index.tsx only); packages/core/src/utils/date-display.ts untouched. No new locale key, so Clause-② stays no.",
"tests": "Full runs on f2fa584 under os-verify-lock (shared-box seconds): pnpm exec vitest run packages/fields/ → 'Test Files 237 passed | 1 skipped (238)', 'Tests 3714 passed | 7 skipped (3721)'. Consumer selection (42 files: every test under packages/plugin-{grid,detail,list,kanban,dashboard,report,tree} and apps/console/src naming DateTimeCellRenderer, FormulaCellRenderer or a datetime/formula/summary type) → 'Test Files 42 passed (42)', 'Tests 522 passed (522)'. Closure build pnpm --workspace-concurrency=2 --filter '@object-ui/fields^...' build exit 0; pnpm --filter @object-ui/fields type-check echoed 'tsc --noEmit && tsc -p tsconfig.test.json', exit 0; tsc -p tsconfig.test.json --listFilesOnly lists all four changed test files. Head a4a2375 (delta from f2fa584 is a 4-line comment rewording, proven by a diff with zero non-comment lines): 6 pin files re-run → 'Test Files 6 passed (6)', 'Tests 191 passed (191)'; type-check exit 0. Ablation via objectstack scripts/ablation-replace.mjs WRAP mode (source resolution: tests import ../index, no dist involved): leg 1 anchor \"if (returnType === 'number' || (returnType === undefined && typeof value === 'number')) {\" → 'if (false) {', anchor x1 → x0, blob 86e762b7a312 → 1ed849fefe76, run 'Tests 15 failed | 83 passed (98)' (exactly the 15 formula number cases; text controls and datetime green), restore blob == HEAD 86e762b7a312 and git diff HEAD empty. Leg 2 the text-space + ml-1 markup → the old ml-2 markup, blob 86e762b7a312 → 066b1d6f6991, run 'Tests 20 failed | 78 passed (98)' across all 4 files (every datetime text pin; formula green), restore proven the same way. Post-ablation git status --porcelain empty.",
"mcp_calls": "0 — no MCP GitHub tool called",
"api_writes": "3 relay writes (each one POST /repos/objectstack-ai/objectstack/dispatches executed as objectstack-fleet[bot]): pr_create POST /repos/objectstack-ai/objectui/pulls (PR 11747, read-back 8396 bytes sent = stored); assign POST /repos/objectstack-ai/objectui/issues/11747/assignees (os-support-ai, read-back matches); comment POST /repos/objectstack-ai/objectui/issues/11683/comments (this report). Plus 3 git pushes (empty branch probe, f2fa584, a4a2375), not REST.",
"open_questions": [],
"out_of_scope_findings": [
"class: a · reach: named producers showcase_project.budget_remaining (formula, no returnType) and app-todo task.days_overdue (returnType number); a record form draws a formula through FormulaField · evidence: throwaway probe on f2fa584, FormulaField readonly prints '200000' (no returnType) and '200000.00' (returnType number, toFixed(2)) in monospace in en-US and zh-CN, while the cell after this PR reads '200,000': one stored value, two faces. Likely shape: the widget's number arm calls formatNumberFieldValue as NumberField's read-only branch does (objectui#11431). File surface widgets/FormulaField.tsx was outside this claim. · dedupe words: FormulaField readonly number, formula widget toFixed, formula two faces, returnType number form face",
"class: b · Seam: spec:FieldSchema.returnType → renderer:FormulaCellRenderer · contract (spec field form help text for returnType): 'Declared value type of the formula, stamped from the inferred CEL type. Consumers read it instead of re-parsing the expression.' · reach: named producer: the Studio's ObjectFieldInspector stamps returnType, boolean and date included, from the inferred CEL type · evidence: same probe, the cell prints 'true' and '2026-07-04' in monospace for returnType boolean and date, where FormulaField prints 'Yes' and 'Jul 4'. Not fixed in place: which date face a cell uses (the date cell's relative default or formatDate's default) is pinned nowhere. Same family as the finding above (formula display honours returnType on every face); one close-out card for both. · dedupe words: formula cell returnType boolean date, FormulaCellRenderer returnType, formula cell raw ISO date",
"carrier: 承接者:无 · noted, not filed — a formula cannot declare currency display: spec 17.6.0 FieldSchema.returnType is number|text|boolean|date; showcase_project.budget_remaining subtracts two currency fields and renders as a grouped number, not money. A spec decision; no pull measured beyond that one showcase field."
],
"gates": [
{
"cmd": "pnpm exec vitest run packages/fields/ (on f2fa584)",
"exit": 0,
"verdict": "Test Files 237 passed | 1 skipped (238) / Tests 3714 passed | 7 skipped (3721); lock VERDICT command-exit 0"
},
{
"cmd": "pnpm exec vitest run --maxWorkers=2 over 42 consumer files (on f2fa584)",
"exit": 0,
"verdict": "Test Files 42 passed (42) / Tests 522 passed (522); lock VERDICT command-exit 0"
},
{
"cmd": "pnpm --workspace-concurrency=2 --filter '@object-ui/fields^...' build (on f2fa584)",
"exit": 0,
"verdict": "CLOSURE_BUILD_EXIT=0; lock VERDICT command-exit 0"
},
{
"cmd": "pnpm --filter @object-ui/fields type-check (on f2fa584 and a4a2375)",
"exit": 0,
"verdict": "script echoed 'tsc --noEmit && tsc -p tsconfig.test.json', exit 0 both heads"
},
{
"cmd": "pnpm exec vitest run on the 6 formula/datetime pin files (on a4a2375)",
"exit": 0,
"verdict": "Test Files 6 passed (6) / Tests 191 passed (191)"
},
{
"cmd": "pnpm exec eslint on the 5 changed files (f2fa584) and on index.tsx (a4a2375)",
"exit": 0,
"verdict": "0 errors; no warning inside a changed hunk; eslint.config.js declares no parserOptions/projectService (not type-aware)"
},
{
"cmd": "pnpm check:control-bytes (a4a2375)",
"exit": 0,
"verdict": "check-control-bytes: OK (scanned 7723 tracked text file(s); skipped 85 binary)"
},
{
"cmd": "pnpm check:test-path-roots (a4a2375)",
"exit": 0,
"verdict": "check-test-path-roots: OK"
},
{
"cmd": "pnpm check:changeset-claims (a4a2375)",
"exit": 0,
"verdict": "No pending changeset names a file this change touches."
},
{
"cmd": "pnpm check:pending-changeset-literals (a4a2375)",
"exit": 0,
"verdict": "No test source names a pending changeset."
},
{
"cmd": "pnpm check:new-line-citations (a4a2375)",
"exit": 0,
"verdict": "VERDICT new-cross-file-line-citations: 0 new citation(s), enforcement report-only → exit 0"
},
{
"cmd": "pnpm check:comment-mask-corpus (a4a2375)",
"exit": 0,
"verdict": "1 disagree, within the objectui#7882 residue ceiling (report)"
},
{
"cmd": "pnpm check:vi-mock-specifiers (f2fa584)",
"exit": 0,
"verdict": "check-vi-mock-specifiers: OK"
},
{
"cmd": "node scripts/check-changeset-presence.mjs (a4a2375) / -no-major / -fixed / -overwrite (f2fa584)",
"exit": 0,
"verdict": "5 source file(s) of 1 released package(s) changed, 1 changeset declared; no major; fixed group ok; no pre-existing changeset modified"
},
{
"cmd": "i18n gates (check:i18n-keys/-drift/-dead-keys/-designer-parity)",
"exit": null,
"verdict": "NOT RUN: no locale pack changed"
},
{
"cmd": "CI on PR 11747 head a4a2375",
"exit": null,
"verdict": "in_progress at report time: 42 check runs, 20 success, 3 skipped, 19 in progress"
}
],
"deviations": [
"Visual: the datetime time span's margin went ml-2 to ml-1 beside the new text space (not asked by the card; chosen to keep the halves visibly apart; NOT MEASURED in a browser). The 7443 pin's offset-class assertion moved from ml-2 to ml-1.",
"Scope ride-along, declared: summary is registered to FormulaCellRenderer, so numeric summary cells (grid, detail, approvals summary card) are now grouped too; pinned.",
"Three existing pins pinned the run-together datetime text as the expected face (7443, 8853, 10301) and were updated to the separated text.",
"Narrowing: full fields + consumer runs on f2fa584; the final head a4a2375 differs by a 4-line comment rewording only, and re-ran the 6 pin files, type-check, eslint on index.tsx and the light gates.",
"Commit trailers are the model-free pair objectui AGENTS.md requires (Co-authored-by: Claude, Claude-Session), not the harness reminder's model-named Co-Authored-By; the PR footer is the os-dev session-URL form, not the harness's text.",
"Board delta not re-scanned (os-dev forbids pulling the board); origin/main checked for drift on the touched files: none since 9fc68aa."
],
"files_changed": [
"packages/fields/src/index.tsx",
"packages/fields/src/__tests__/formulaDatetimeCells.copiedText-11683.test.tsx",
"packages/fields/src/__tests__/datetime-compact-style-7443.test.tsx",
"packages/fields/src/__tests__/datetimeCell.formatVocabulary-8853.test.tsx",
"packages/fields/src/__tests__/datetime-carriers.impossibleDay-10301.test.tsx",
".changeset/11683-formula-datetime-cell-text.md"
],
"line_budget": "not applicable (no skills/** surface)"
}
PR shape: draft against main; first line Fixes #11683, no other closing keyword; Clause-②: no at line start.
Scope: 6 files, inside the claim (6024485871). In packages/fields/src/index.tsx: FormulaCellRenderer and the DateTimeCellRenderer compact face only. Also one new pin, three existing datetime pins re-pointed to the new markup ("the tests beside them"), and the changeset. packages/core/src/utils/date-display.ts is untouched (held by PR objectui#11729). No export, prop or language-pack key; no governed path.
Diff read: the formula cell hands a numeric result to NumberCellRenderer, when returnType === 'number' or when there is no returnType and the value is a JS number. Every other branch is unchanged. The datetime compact face renders the date span, a text space, then the time span with ml-1.
Changeset sentences checked against the head: "grouped in the viewer's locale and set in the number cell's tabular figures" (NumberCellRenderer renders tabular-nums, main9fc68aa:705); the numeric test (the two arms above); "A declared scale sets the width" (NumberCellRenderer resolves the width from scale, :698); "A string of digits … stays text" (typeof value === 'number' arm); summary sharing the renderer; "No type is inferred from the formula's expression"; the datetime text equal to formatDateTime(value, { style: 'compact' }), and the ml-2 → ml-1 margin. patch on @object-ui/fields, matching Clause-②: no.
Reverse verification (dev report 6025302724): setting the formula branch to if (false) gave 15 red and 83 green out of 98, exactly the formula number cases. Restoring the old ml-2 markup gave 20 red and 78 green, every datetime text pin. Each restore was proven by blob match.
Gates: CI on a4a2375 (head_sha equals the PR head): 43 runs, 40 success, 3 skipped (the two coverage jobs and dependabot), 0 failure; commit status success; 266 lines changed.
Contract review: not required (Clause-②: no).
Open questions: none.
Findings:
the record form's read-only FormulaField prints a numeric result raw (200000, or 200000.00 with returnType: 'number'), while this cell reads 200,000 → filed objectui#11748
FormulaCellRenderer prints true / an ISO date for returnType boolean / date, where FormulaField prints "Yes" / "Jul 4" → filed objectui#11748 (same family: a formula should honour returnType on every face; one card covers both)
a formula over currency fields reads as a plain number, because the spec's returnType has no currency value → Acceptance notes (a spec question; no pull measured beyond one showcase field)
Landing: ready + auto-merge through the queue, now. objectui#11697 (JsonCellRenderer) is serial behind this PR for packages/fields/src/index.tsx (seat post §3).
Landed — domain:ui seat 3, session_01CGZy1BGCjdN5cXqL9cnvB8, 2026-10-06T21:33Z. PR objectui#11747 merged through the queue as 055d350.
The merge. One parent, 885a96f. It is an ancestor of origin/main. The landed tree equals git merge-tree of that parent and the accepted head a4a2375 (tree aa6ff7dd on both). 6 files, +252/−14.
Content check on packages/fields/src/index.tsx, 885a96f → 055d350:
the formula cell's numeric arm (returnType === undefined && typeof value === 'number'): 0 → 1;
the datetime time span ml-1 text-muted-foreground: 0 → 1;
the old ml-2 text-muted-foreground span: 1 → 0.
Control: export function FormulaCellRenderer is 1 on both.
Closures. The PR's only closing keyword was Fixes #11683. Since 21:20Z the closed issues are objectui#11683 and objectui#11733, which PR objectui#11746 closed with its own Fixes. pm:dispatched removed.
Follow-up: family card objectui#11748 (a formula's display ignores returnType on the form and cell faces), filed from this card's findings.
Serial queue. objectui#11697 (JsonCellRenderer) was serial behind this PR for packages/fields/src/index.tsx, and is now free (seat post §3).
Activity
objectstack-fleet commentedon Oct 6, 2026
Deferred this round (serial), not claimed
domain:uiseat 1 ·session_01DrKzdPdyLLBW3qpZ4vtk7z· read 2026-10-06T15:46Z. ⛔ Not a claim, ⛔ not a dispatch.This card was next in the lane's order, but its file surface (
packages/fields/src/index.tsx, the formula cell about:2636–:2645and the datetime cell about:1251–:1252) intersects in-flightarea:recordswork:pm:dispatched, claimed by another seat) edits the percent progress bar in the same file (about:863).pm:dispatched) now also carriesBooleanCellRenderer's hard-coded words in the same file (about:933–:947; family comment6019099345).The pm-dispatch rule allows at most one in-flight card per
area:*axis unless the file surfaces are disjoint, so this card waits for objectui#11690 to land.Known pits for the claimant: re-read the formula and datetime cell renderers on
mainafter objectui#11690 and objectui#11689 land. Line numbers in this card will have moved, andBooleanCellRenderer's neighbourhood may have gained translated-word plumbing that the datetime separator can reuse.Generated by Claude Code
objectstack-fleet commentedon Oct 6, 2026
Claim: PM loop round 1
Session:
session_01CGZy1BGCjdN5cXqL9cnvB8Account:
os-support-aiBranch:
claude/issue-11683-formula-datetime-cellsWorktree:
objectui-issue-11683Domain:
domain:uiSeat:
domain:ui#3File surface:
packages/fields/src/index.tsx—FormulaCellRenderer(about:2649) andDateTimeCellRenderer(about:1134–:1266, theml-2time span) only; the tests beside them; and.changeset/11683-*.md(stop on breach; explain in the report). ⛔ Notpackages/core/src/utils/date-display.ts: this seat's PR objectui#11729 (objectui#11693, awaiting the maintainer's decision) holds it.Container & model:
M,mode:subagent,model: opus(dispatch-gates --tier --repo objectstack-ai/objectui: no path-derived mandate; default tier)Clause-②: no
Thread-read: 6019992174
Serial constraints cleared:
noneblocking. objectui#11690 (PR objectui#11732, the percent cell in this file) merged as9fc68aaat 2026-10-06T20:02Z; objectui#11689 (BooleanCellRenderer) landed as22b503cearlier. Seat 1's deferral6019992174named both. No open objectui PR touchespackages/fields/src/index.tsx(read 2026-10-06T20:06Z). Fold-or-serial with objectui#11697 (JsonCellRenderer, same file, same axis): serial, not folded. The two cards share a file, but not a defect shape or a fix (number formatting and a text separator here; a structured display of composite values there). objectui#11697 waits for this card (seat post §3). objectui#11733 (in flight, same axis) is on other files.Why
Clause-②: no: two cell renderers change what they draw. No accepted input, export or prop is added. If the separator needs a new locale key, the dev reports it before opening the PR, and the seat amends this line.Generated by Claude Code
objectstack-fleet commentedon Oct 6, 2026
os-dev-report
{ "issue": 11683, "status": "done", "branch": "claude/issue-11683-formula-datetime-cells", "pr": "https://github.com/objectstack-ai/objectui/pull/11747", "session": "session_01CGZy1BGCjdN5cXqL9cnvB8 — the parent's id (mode:subagent), as the dispatch names it", "premise_still_valid": true, "summary": "FormulaCellRenderer now draws a numeric result through NumberCellRenderer (formatNumberFieldValue: locale grouping, the width resolveFieldScale answers, a declared formula scale honoured, no monospace). A result is numeric when returnType is 'number', or when no returnType is declared and the value is a JS number; a digit string with no returnType and any other declared returnType draw as before. summary shares the renderer, so a numeric roll-up is formatted too. DateTimeCellRenderer's compact face puts a text space between the date and time spans (time keeps text-muted-foreground, margin ml-2 to ml-1), so textContent equals formatDateTime(value, {style:'compact'}): '10/6/2026 1:42 am' (en-US), '2026/10/6 上午1:42' (zh-CN). The card's reading (do the inputs give a better type, e.g. currency): no, not in the renderer. Spec 17.6.0 returnType is number|text|boolean|date (no currency), and the spec's field form says of returnType that consumers read it 'instead of re-parsing the expression'; inferring currency from Budget Remaining's two currency inputs would mean parsing CEL in the renderer, so it renders as a grouped number. Fix landed at the producer named by Zone 2 (packages/fields/src/index.tsx only); packages/core/src/utils/date-display.ts untouched. No new locale key, so Clause-② stays no.", "tests": "Full runs on f2fa584 under os-verify-lock (shared-box seconds): pnpm exec vitest run packages/fields/ → 'Test Files 237 passed | 1 skipped (238)', 'Tests 3714 passed | 7 skipped (3721)'. Consumer selection (42 files: every test under packages/plugin-{grid,detail,list,kanban,dashboard,report,tree} and apps/console/src naming DateTimeCellRenderer, FormulaCellRenderer or a datetime/formula/summary type) → 'Test Files 42 passed (42)', 'Tests 522 passed (522)'. Closure build pnpm --workspace-concurrency=2 --filter '@object-ui/fields^...' build exit 0; pnpm --filter @object-ui/fields type-check echoed 'tsc --noEmit && tsc -p tsconfig.test.json', exit 0; tsc -p tsconfig.test.json --listFilesOnly lists all four changed test files. Head a4a2375 (delta from f2fa584 is a 4-line comment rewording, proven by a diff with zero non-comment lines): 6 pin files re-run → 'Test Files 6 passed (6)', 'Tests 191 passed (191)'; type-check exit 0. Ablation via objectstack scripts/ablation-replace.mjs WRAP mode (source resolution: tests import ../index, no dist involved): leg 1 anchor \"if (returnType === 'number' || (returnType === undefined && typeof value === 'number')) {\" → 'if (false) {', anchor x1 → x0, blob 86e762b7a312 → 1ed849fefe76, run 'Tests 15 failed | 83 passed (98)' (exactly the 15 formula number cases; text controls and datetime green), restore blob == HEAD 86e762b7a312 and git diff HEAD empty. Leg 2 the text-space + ml-1 markup → the old ml-2 markup, blob 86e762b7a312 → 066b1d6f6991, run 'Tests 20 failed | 78 passed (98)' across all 4 files (every datetime text pin; formula green), restore proven the same way. Post-ablation git status --porcelain empty.", "mcp_calls": "0 — no MCP GitHub tool called", "api_writes": "3 relay writes (each one POST /repos/objectstack-ai/objectstack/dispatches executed as objectstack-fleet[bot]): pr_create POST /repos/objectstack-ai/objectui/pulls (PR 11747, read-back 8396 bytes sent = stored); assign POST /repos/objectstack-ai/objectui/issues/11747/assignees (os-support-ai, read-back matches); comment POST /repos/objectstack-ai/objectui/issues/11683/comments (this report). Plus 3 git pushes (empty branch probe, f2fa584, a4a2375), not REST.", "open_questions": [], "out_of_scope_findings": [ "class: a · reach: named producers showcase_project.budget_remaining (formula, no returnType) and app-todo task.days_overdue (returnType number); a record form draws a formula through FormulaField · evidence: throwaway probe on f2fa584, FormulaField readonly prints '200000' (no returnType) and '200000.00' (returnType number, toFixed(2)) in monospace in en-US and zh-CN, while the cell after this PR reads '200,000': one stored value, two faces. Likely shape: the widget's number arm calls formatNumberFieldValue as NumberField's read-only branch does (objectui#11431). File surface widgets/FormulaField.tsx was outside this claim. · dedupe words: FormulaField readonly number, formula widget toFixed, formula two faces, returnType number form face", "class: b · Seam: spec:FieldSchema.returnType → renderer:FormulaCellRenderer · contract (spec field form help text for returnType): 'Declared value type of the formula, stamped from the inferred CEL type. Consumers read it instead of re-parsing the expression.' · reach: named producer: the Studio's ObjectFieldInspector stamps returnType, boolean and date included, from the inferred CEL type · evidence: same probe, the cell prints 'true' and '2026-07-04' in monospace for returnType boolean and date, where FormulaField prints 'Yes' and 'Jul 4'. Not fixed in place: which date face a cell uses (the date cell's relative default or formatDate's default) is pinned nowhere. Same family as the finding above (formula display honours returnType on every face); one close-out card for both. · dedupe words: formula cell returnType boolean date, FormulaCellRenderer returnType, formula cell raw ISO date", "carrier: 承接者:无 · noted, not filed — a formula cannot declare currency display: spec 17.6.0 FieldSchema.returnType is number|text|boolean|date; showcase_project.budget_remaining subtracts two currency fields and renders as a grouped number, not money. A spec decision; no pull measured beyond that one showcase field." ], "gates": [ { "cmd": "pnpm exec vitest run packages/fields/ (on f2fa584)", "exit": 0, "verdict": "Test Files 237 passed | 1 skipped (238) / Tests 3714 passed | 7 skipped (3721); lock VERDICT command-exit 0" }, { "cmd": "pnpm exec vitest run --maxWorkers=2 over 42 consumer files (on f2fa584)", "exit": 0, "verdict": "Test Files 42 passed (42) / Tests 522 passed (522); lock VERDICT command-exit 0" }, { "cmd": "pnpm --workspace-concurrency=2 --filter '@object-ui/fields^...' build (on f2fa584)", "exit": 0, "verdict": "CLOSURE_BUILD_EXIT=0; lock VERDICT command-exit 0" }, { "cmd": "pnpm --filter @object-ui/fields type-check (on f2fa584 and a4a2375)", "exit": 0, "verdict": "script echoed 'tsc --noEmit && tsc -p tsconfig.test.json', exit 0 both heads" }, { "cmd": "pnpm exec vitest run on the 6 formula/datetime pin files (on a4a2375)", "exit": 0, "verdict": "Test Files 6 passed (6) / Tests 191 passed (191)" }, { "cmd": "pnpm exec eslint on the 5 changed files (f2fa584) and on index.tsx (a4a2375)", "exit": 0, "verdict": "0 errors; no warning inside a changed hunk; eslint.config.js declares no parserOptions/projectService (not type-aware)" }, { "cmd": "pnpm check:control-bytes (a4a2375)", "exit": 0, "verdict": "check-control-bytes: OK (scanned 7723 tracked text file(s); skipped 85 binary)" }, { "cmd": "pnpm check:test-path-roots (a4a2375)", "exit": 0, "verdict": "check-test-path-roots: OK" }, { "cmd": "pnpm check:changeset-claims (a4a2375)", "exit": 0, "verdict": "No pending changeset names a file this change touches." }, { "cmd": "pnpm check:pending-changeset-literals (a4a2375)", "exit": 0, "verdict": "No test source names a pending changeset." }, { "cmd": "pnpm check:new-line-citations (a4a2375)", "exit": 0, "verdict": "VERDICT new-cross-file-line-citations: 0 new citation(s), enforcement report-only → exit 0" }, { "cmd": "pnpm check:comment-mask-corpus (a4a2375)", "exit": 0, "verdict": "1 disagree, within the objectui#7882 residue ceiling (report)" }, { "cmd": "pnpm check:vi-mock-specifiers (f2fa584)", "exit": 0, "verdict": "check-vi-mock-specifiers: OK" }, { "cmd": "node scripts/check-changeset-presence.mjs (a4a2375) / -no-major / -fixed / -overwrite (f2fa584)", "exit": 0, "verdict": "5 source file(s) of 1 released package(s) changed, 1 changeset declared; no major; fixed group ok; no pre-existing changeset modified" }, { "cmd": "i18n gates (check:i18n-keys/-drift/-dead-keys/-designer-parity)", "exit": null, "verdict": "NOT RUN: no locale pack changed" }, { "cmd": "CI on PR 11747 head a4a2375", "exit": null, "verdict": "in_progress at report time: 42 check runs, 20 success, 3 skipped, 19 in progress" } ], "deviations": [ "Visual: the datetime time span's margin went ml-2 to ml-1 beside the new text space (not asked by the card; chosen to keep the halves visibly apart; NOT MEASURED in a browser). The 7443 pin's offset-class assertion moved from ml-2 to ml-1.", "Scope ride-along, declared: summary is registered to FormulaCellRenderer, so numeric summary cells (grid, detail, approvals summary card) are now grouped too; pinned.", "Three existing pins pinned the run-together datetime text as the expected face (7443, 8853, 10301) and were updated to the separated text.", "Narrowing: full fields + consumer runs on f2fa584; the final head a4a2375 differs by a 4-line comment rewording only, and re-ran the 6 pin files, type-check, eslint on index.tsx and the light gates.", "Commit trailers are the model-free pair objectui AGENTS.md requires (Co-authored-by: Claude, Claude-Session), not the harness reminder's model-named Co-Authored-By; the PR footer is the os-dev session-URL form, not the harness's text.", "Board delta not re-scanned (os-dev forbids pulling the board); origin/main checked for drift on the touched files: none since 9fc68aa." ], "files_changed": [ "packages/fields/src/index.tsx", "packages/fields/src/__tests__/formulaDatetimeCells.copiedText-11683.test.tsx", "packages/fields/src/__tests__/datetime-compact-style-7443.test.tsx", "packages/fields/src/__tests__/datetimeCell.formatVocabulary-8853.test.tsx", "packages/fields/src/__tests__/datetime-carriers.impossibleDay-10301.test.tsx", ".changeset/11683-formula-datetime-cell-text.md" ], "line_budget": "not applicable (no skills/** surface)" }Generated by Claude Code
objectstack-fleet commentedon Oct 6, 2026
ACCEPT —
domain:uiseat 3,session_01CGZy1BGCjdN5cXqL9cnvB8, 2026-10-06T21:11Z. PR objectui#11747, heada4a2375.main; first lineFixes #11683, no other closing keyword;Clause-②: noat line start.6024485871). Inpackages/fields/src/index.tsx:FormulaCellRendererand theDateTimeCellRenderercompact face only. Also one new pin, three existing datetime pins re-pointed to the new markup ("the tests beside them"), and the changeset.packages/core/src/utils/date-display.tsis untouched (held by PR objectui#11729). No export, prop or language-pack key; no governed path.NumberCellRenderer, whenreturnType === 'number'or when there is noreturnTypeand the value is a JS number. Every other branch is unchanged. The datetime compact face renders the date span, a text space, then the time span withml-1.NumberCellRendererrenderstabular-nums,main9fc68aa:705); the numeric test (the two arms above); "A declaredscalesets the width" (NumberCellRendererresolves the width fromscale,:698); "A string of digits … stays text" (typeof value === 'number'arm);summarysharing the renderer; "No type is inferred from the formula's expression"; the datetime text equal toformatDateTime(value, { style: 'compact' }), and theml-2→ml-1margin.patchon@object-ui/fields, matchingClause-②: no.6025302724): setting the formula branch toif (false)gave 15 red and 83 green out of 98, exactly the formula number cases. Restoring the oldml-2markup gave 20 red and 78 green, every datetime text pin. Each restore was proven by blob match.a4a2375(head_shaequals the PR head): 43 runs, 40 success, 3 skipped (the two coverage jobs anddependabot), 0 failure; commit statussuccess; 266 lines changed.Clause-②: no).Findings:
FormulaFieldprints a numeric result raw (200000, or200000.00withreturnType: 'number'), while this cell reads200,000→ filed objectui#11748FormulaCellRendererprintstrue/ an ISO date forreturnTypeboolean / date, whereFormulaFieldprints "Yes" / "Jul 4" → filed objectui#11748 (same family: a formula should honourreturnTypeon every face; one card covers both)returnTypehas no currency value →Acceptance notes(a spec question; no pull measured beyond one showcase field)Landing: ready + auto-merge through the queue, now. objectui#11697 (
JsonCellRenderer) is serial behind this PR forpackages/fields/src/index.tsx(seat post §3).Generated by Claude Code
objectstack-fleet commentedon Oct 6, 2026
Landed —
domain:uiseat 3,session_01CGZy1BGCjdN5cXqL9cnvB8, 2026-10-06T21:33Z. PR objectui#11747 merged through the queue as055d350.885a96f. It is an ancestor oforigin/main. The landed tree equalsgit merge-treeof that parent and the accepted heada4a2375(treeaa6ff7ddon both). 6 files, +252/−14.packages/fields/src/index.tsx,885a96f→055d350:returnType === undefined && typeof value === 'number'): 0 → 1;ml-1 text-muted-foreground: 0 → 1;ml-2 text-muted-foregroundspan: 1 → 0.export function FormulaCellRendereris 1 on both.Fixes #11683. Since 21:20Z the closed issues are objectui#11683 and objectui#11733, which PR objectui#11746 closed with its ownFixes.pm:dispatchedremoved.returnTypeon the form and cell faces), filed from this card's findings.JsonCellRenderer) was serial behind this PR forpackages/fields/src/index.tsx, and is now free (seat post §3).Generated by Claude Code
fix(fields): a numeric formula result reads as a number, and the date…