Repository navigation
fix(app-shell): a report's or dataset's Name keeps every underscore typed (objectui#12746) - #12788
Merged
objectstack-fleet[bot] merged 2 commits intoOct 16, 2026
Merged
Conversation
…yped (objectui#12746) The report and dataset designers committed Name with the strict toFieldName on every keystroke, which trims a trailing underscore before the next key arrives, so qavrf_rev typed key by key read qavrfrev and a namespaced report or dataset could not be named by typing. Both now commit with toFieldNameLoose, as the object designer does; the Label derivation and the nameFollowsLabel comparison keep the strict form. Claude-Session: https://claude.ai/code/session_01Vk15bz8xHtKGUfXfCm16h4 Co-authored-by: Claude <noreply@anthropic.com>
…rscore (objectui#12746) One file beside each inspector, with a host double that merges each patch back: qavrf_rev typed key by key stays qavrf_rev, a cleared Name stays empty, the Label derivation keeps the strict form, and a trailing underscore typed onto a derived Name keeps it from following the Label. The objectui#12680 host-level cases now type the same namespaced name into all three designers; their comment said the report and dataset Name could not carry a separator. Claude-Session: https://claude.ai/code/session_01Vk15bz8xHtKGUfXfCm16h4 Co-authored-by: Claude <noreply@anthropic.com>
Contributor
✅ Console Performance Budget
The eager closure is every chunk the entry reaches through static imports — what the browser fetches and parses before the app renders. The entry chunk on its own is a small fraction of it. 📦 Bundle Size Report
Size Limits
|
This was referenced Oct 16, 2026
Contributor
Author
席位核对 — ACCEPT ·
|
| designer | qavrf_rev typed, before (3e2c763) |
after (a5cbab9) |
Label-only control |
|---|---|---|---|
| report | qavrfrev |
qavrf_rev, kept through a later Label edit |
revenue_board mid-edit, revenue_board_q final, unchanged |
| dataset | qavrfrev |
qavrf_rev, kept through a later Label edit |
the same, unchanged |
| object (control) | qavrf_rev |
qavrf_rev |
the same, unchanged |
- A dataset named
qavrf_revsaved through the designer:PUT /api/v1/meta/dataset/qavrf_rev?mode=draft&package=com.qa.vrfanswered 200.
3. Gates (check-runs pinned to this head).
- 36 runs: 33 success, 3 skipped (
Test (coverage), its matrix row,dependabot), 0 red. - Among the successes:
Lint,Type Check,Repo Gates,Test,Test (shard 1/16)…(16/16),Test (dist pins),Build & E2E,Build Docs,Bundle Analysis(PASS,6224333879: eager closure 3127.2 KB of 3744.1 KB),Live E2E (informational), the changeset checks,Line Citation GateandGoverned Surface Queue Guard. - The dev's local subset:
- 14 files / 125 tests, every report, dataset and object inspector suite plus the objectui#12680 host test;
- the closure build and the app-shell type-check;
- eslint, 0 errors;
- changeset presence and new-line citations.
- On unchanged
main's inspectors, the 3 touched test files read 10 failed / 14 passed. The pins receivedqavrfrevandfield, and the objectui#12680 cases receivedqavrfhandtyped. The restore was proven. - Ablations: A3, a loose Label derivation, turns the strict-derivation pin red (
revenue_). A4, comparing the strict form of the Name, turns the trailing-underscore pin red (qavrf_board). Each was restored and proven.
4. Accepted deviations.
ResourceEditPage.nameSurvivesLabel-12680.test.tsxis outside the claim's two inspectors.- It is this seat's objectui#12680 host test. Its report and dataset cases typed
qavrfrevenueunder a comment that said those Name fields "carry no separator". - This change makes that comment false. The cases now type
qavrf_hand_typed, as the object case does, and they are red onmain. - It is test-only and keeps the pin truthful, so the seat accepts it without a claim re-statement.
- It is this seat's objectui#12680 host test. Its report and dataset cases typed
- A cleared Name now stays empty instead of reading
field, and the Name follows the Label again. That is pinned, and it matches the object designer. - A trailing
_typed onto a derived Name stops it following the Label. That is pinned, and it matches the object designer. The spec's identifier rule accepts a trailing_, measured by the dev's probe. - Prose checked against the diff:
- the changeset's "A cleared box stays empty, and the Name then follows the Label again";
- "A Name derived from the Label still uses the strict form";
- "An existing report's or dataset's name is unchanged and still not editable".
5. Out of scope (where each went).
- A Label in a non-Latin script, or a cleared Label, derives the report or dataset Name
field, where the object designer leaves it empty. Measured in Chromium. → filed objectui#12789. - The dev's shell left a stray 6-byte
/build.pid(a PID) at the container's filesystem root. It is outside every repository and is not part of this PR. The dev's ownrmwas refused by the session's safety check, so the seat has reported it to the maintainer rather than removing it.
6. Landing.
- Not governed:
check-governed-queue-guard.mjs --testover the 6 paths reads NOT GOVERNED. - 236 lines changed, under the 3000-line threshold.
Clause-②: no. Every check is green or an expected skip.- ⇒ The seat lands it: relay
pr_ready+automerge_enable, through the merge queue. - On MERGED,
Fixescloses objectui#12746.
Generated by Claude Code
objectstack-fleet
Bot
deleted the
claude/issue-12746-name-keeps-underscore
branch
October 16, 2026 21:09
This was referenced Oct 16, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Fixes #12746
Clause-②: no (designer only; no export, prop or type changes)
What changes
The report and dataset designers' Name box (create mode) committed every keystroke through the strict
toFieldName. That rule trims a trailing_, so the underscore was gone before the next key arrived:qavrf_revtyped key by key readqavrfrev, and a report or dataset in a namespaced package could not get itsqavrf_prefix by typing. Clearing the box also wrotefieldback into it.Both boxes now commit through
toFieldNameLoose, imported from where it already lives besidetoFieldName(previews/object-fields-io.ts), which is what the object designer's Name does. Nothing else moves, so the strict form stays exactly where the object designer keeps its own:toFieldName, so a Label typed with a trailing space or punctuation never leaves a trailing_in the Name;nameFollowsLabelstill compares the stored Name with the strict form of the Label. A Name the author extends with_therefore stops following the Label, and a later Label edit leaves it alone;An existing item's name is untouched: the Name box renders only in create mode, as before.
Files:
ReportDefaultInspector.tsxandDatasetDefaultInspector.tsx(the Name commit and its import in each, plus a comment), one test beside each, the objectui#12680 host-level test (its report and dataset cases typedqavrfrevenuewith a comment saying those Name fields could not carry a separator; they now typeqavrf_hand_typedlike the object case), and.changeset/12746-report-dataset-name-keeps-underscore.md(@object-ui/app-shellpatch).Browser readings (Chromium, real keystrokes)
Backend: objectstack
66d456d01examples/app-crm,objectstack dev --seed-admin --freshon a private port. Console: this branch's worktree on Vite, proxied to it. A writable package created withPOST /api/v1/packages{"manifest":{"id":"com.qa.vrf",…,"namespace":"qavrf"}}→ 201. Pages:/apps/crm_app/metadata/{report,dataset,object}/new?package=com.qa.vrf. Name typedqavrf_revkey by key, then Label typedRevenue Boardand tabbed out of. Control: a fresh form, Label only, typedRevenue BoardthenQ.3e2c763)a5cbab9)qavrfrevqavrf_revqavrf_revrevenue_board/revenue_board_q(unchanged)qavrfrevqavrf_revqavrf_revrevenue_board/revenue_board_q(unchanged)qavrf_revqavrf_revqavrf_revrevenue_board/revenue_board_q(unchanged)After the fix, a dataset named by typing
qavrf_rev(LabelRevenue, base objectopportunity) saved through the designer's Save button:PUT /api/v1/meta/dataset/qavrf_rev?mode=draft&package=com.qa.vrf→ 200,Saved dataset 'qavrf_rev' (env-wide, package=com.qa.vrf, state=draft).Tests
New, one beside each inspector, each rendering the inspector with a host double that merges every patch back into the draft (real user-event keystrokes):
ReportDefaultInspector.nameKeepsUnderscore-12746.test.tsxDatasetDefaultInspector.nameKeepsUnderscore-12746.test.tsxEach file pins four things: (1)
qavrf_revtyped key by key staysqavrf_revin the box and in the draft; (2) a cleared Name stays empty and can be typed again; (3) the Label → Name derivation keeps the strict form (Revenue -- Boardderivesrevenue_board, thenQderivesrevenue_board_q); (4) a_typed onto a derived Name (qavrf→qavrf_) makes the Name the author's, so a later Label edit (Qavrf Board) leavesqavrf_.Final run at
a5cbab9, after the closure build:pnpm exec vitest runover the report, dataset and object inspector suites (every file whose name starts withReportDefaultInspector,DatasetDefaultInspectororObjectDefaultInspector) plusResourceEditPage.nameSurvivesLabel-12680.test.tsx→Test Files 14 passed (14),Tests 125 passed (125).Red on unchanged main, and one ablation per pin
Each leg ran the three touched test files (24 tests). Every mutation was proven on disk (anchor count and blob hash), and every restore was proven by blob hash equal to
HEADand an emptygit diff HEAD.3e2c763blobs (toFieldNameLoosecount 0 in each)10 failed, 14 passedqavrfrevforqavrf_rev), pin 2 (fieldfor an empty box), pin 4 (qavrfforqavrf_); objectui#12680 report and dataset typed-Name cases (qavrfhandtypedforqavrf_hand_typed)toFieldName(v)replaced bytoFieldNameLoose(v)in both inspectors2 failed, 22 passedrevenue_(the loose derivation leavesrevenue_, which no longer equals the strict form of the Label, so the Name stops following)nameFollowsLabelcompares the strict form of the Name (toFieldName(nameValue)) in both inspectors2 failed, 22 passedqavrf_withqavrf_boardPin 3 is green on unchanged main by construction (main applies the strict form everywhere); A3 is the leg that shows it can fail. All tests here import the inspectors through relative source paths, so no
dist/build sits between a mutation and its run.Local gates (all at
a5cbab9)pnpm --workspace-concurrency=2 --filter '@object-ui/app-shell^...' run build→ exit 0 (28 packages built).pnpm --filter @object-ui/app-shell run type-check(tsc --noEmit && tsc -p tsconfig.test.json; the test project's include glob covers the new*.test.tsxfiles) → exit 0.pnpm exec eslinton the five changed source and test files → exit 0, 0 errors; 7 warnings, all on lines this diff does not touch (react-refresh/only-export-components,@typescript-eslint/no-explicit-any).node scripts/check-changeset-presence.mjs→ exit 0, "5 source file(s) of 1 released package(s) changed, and this change declares 1 changeset(s)".pnpm check:new-line-citations→ exit 0,VERDICT new-cross-file-line-citations: 0 new citation(s).Everything else is CI's.
Acceptance notes
fieldwhen the Label holds no Latin letters or is cleared. In Chromium, on this branch (the derivation lines are byte-identical to3e2c763): Label收入derives Namefieldin both designers, and clearing the Label leaves Namefield. The object designer derives an empty Name in both cases, which asks the author for one. The cause is the stricttoFieldNamefallback ('field'for an empty result) in the derivation, which this card keeps as it is. Reported to the seat, not filed from here.Generated by Claude Code