Skip to content

chore(objectui): move the console pin to 1f23d5b070fa, carrying objectstack-ai/objectui#12475 and objectstack-ai/objectui#12493 - #23709

Merged
objectstack-fleet[bot] merged 2 commits into
mainfrom
claude/issue-23691-console-pin-hop
Oct 15, 2026
Merged

objectstack-fleet[bot] merged 2 commits into
mainfrom
claude/issue-23691-console-pin-hop

Conversation

@objectstack-fleet

Copy link
Copy Markdown
Contributor

Fixes #23691
Clause-②: no

This PR moves the console pin from b9814b334d8a to 1f23d5b070fa, objectui main at 1f23d5b070fa4d0cee0274902944d247bc4588b7. That commit carries both objectui changes the card owes:

It is one bump, through scripts/bump-objectui.sh, and not a rider on another PR.

Tier: no governed surface. node scripts/pm/check-governed-merges.mjs --branch claude/issue-23691-console-pin-hop reads 0 of 5 paths on the register. Size: 5 files, +141 / −10 (151 changed lines, under the 3000 human-merge line).

The hop: 83 objectui commits, 300 paths, all on objectui main

  • REST compare b9814b334d8a...1f23d5b070fa: ahead_by 83, behind_by 0, 300 files.
  • In the sibling checkout (deepened with git fetch --unshallow first), git merge-base --is-ancestor exits 0 for 720f6d4, for b512428 and for the old pin, each against 1f23d5b070fa. It also exits 0 for 1f23d5b070fa against objectui origin/main. 720f6d4 is 12 commits behind the new pin and b512428 is 2 behind. Control: the objectui tip b5416943ce45 against the old pin exits 1.
  • Why 1f23d5b070fa and not the tip. When the work started, objectui main had moved two commits past the commit the dispatch read, to b5416943ce45, and that tip's push-run CI was still in progress. At 1f23d5b070fa every check-run of objectui's required set (Lint, Type Check, Test (shard N/16), Build & E2E, Build Docs, Changeset Declaration) reads completed: success, 41 of 41 across its merge-queue and push runs, re-read at 2026-10-15T17:43Z. At that reading the tip had one cancelled required run (Lint), and main had moved again, to 518a8e308466. 1f23d5b070fa is the newest main commit read fully green that carries both fixes.

Acceptance readings, at the new pin

(a) The built console's AI build page never sends ?handoffPrompt= on load

Source, at objectui 1f23d5b070fa. packages/app-shell/src/console/ai/AiChatPage.tsx reads the Builder handoff only from navigation state: readBuilderHandoffState(location.state). The prompt is seeded once per history entry, and the entry's state is replaced without handoffPrompt, so a reload does not send it again. git grep for a searchParams read of handoffPrompt (get('handoffPrompt')) finds nothing under packages or apps at the new pin. The same search at the old pin finds the read, at AiChatPage.tsx:882.

The pin test, packages/app-shell/src/console/ai/__tests__/AiChatPage.handoffNeverFromUrl-12493.test.tsx (objectui PR objectstack-ai/objectui#12536), asserts four things:

  • a page loaded with ?handoffPrompt= sends nothing (sent stays []);
  • the in-app "Open in Builder" handoff lands its text once, by navigation state, and the URL never carries it;
  • a reload of the handoff history entry does not send it again;
  • control: a user-typed first message sends.

Built bundle. scripts/build-console.sh built objectui at the pin into .cache/objectui-1f23d5b070fa/. The AI build page lands in apps/console/dist/assets/ObjectView-CPn8lYVn.js (198569 bytes), the only asset that names handoffPrompt. The minifier writes string literals as template literals, so the pattern accepts all three quote characters. The results:

  • a .get(…handoffPrompt…) call: 0 hits in that asset and 0 in all 3434 assets;
  • positive control, .get(…package…): 1 hit in the same asset. It is the same component's ?package= read, the line just before the old handoffPrompt read. Here it is followed by the navigation-state reader: h=d.get(`package`)?.trim()||void 0,g=o(),_=(0,$.useMemo)(()=>Uc(g.state),[g.state]).

The copy in packages/console/dist/assets/ is byte-identical (cmp exit 0). On a smoke boot (below), the served /_console/assets/ObjectView-CPn8lYVn.js is byte-identical to it and gives the same 0 and 1.

(b) History and Audit are hidden for a setup.access-only caller

Source, at objectui 1f23d5b070fa.

  • packages/app-shell/src/hooks/useCanAuthorMetadata.ts declares AUTHORING_TRAIL_CAPABILITIES = ['studio.access', 'manage_metadata']. useCanReadAuthoringTrail() answers whether the caller holds any of them, and fails open when no capability set was reported.
  • ResourceEditPage.tsx calls it once (const canReadTrail = useCanReadAuthoringTrail(), line 1210). It gates the History and Audit entries (!createMode && canReadTrail, lines 2322, 2334, 3251 and 3286), and a ?tab=history / ?tab=audit deep link (line 1228).
  • PermissionMatrixEditor.tsx calls it at line 476. It gates the History button and the embedded History sheet (lines 1560, 1624 and 1787). That editor offers no Audit entry.

The pin test, packages/app-shell/src/views/metadata-admin/trailDoorsGate-12475.test.tsx, asserts:

  • a setup.access-only caller sees neither history-button nor audit-button on ResourceEditPage, and no History on PermissionMatrixEditor, routed or embedded;
  • a studio.access or a manage_metadata holder sees them;
  • an unreported capability set fails open;
  • control: create mode shows no trail entries at all.

Built bundle. useCanAuthorMetadata-B_1yXw8l.js carries the gate: var r=[`studio.access`,t];function i(){let{hasCapabilities:t}=e();return r.some(e=>t([e]))}, exported as n. metadata-admin-GnoOznL8.js imports that n as ht and calls Sn=ht(). Both "data-testid":`audit-button` and "data-testid":`history-button` sit behind !n&&Sn&&.

No live browser run. This is a source and bundle reading only. A setup.access-only organization admin is not a seeded identity, so a browser pass would first have to provision one.

Artefacts that travel with the pin

Console Pin Gate steps, run locally (each exited 0)

  1. Client closure: turbo run build --filter=@objectstack/client --filter=@objectstack/sdui-parser (34 tasks).

  2. scripts/build-console.sh at the new pin. It reported:

    • bundle canary import/jobs present;
    • exactly one zod version literal ({major:4,minor:6,patch:5});
    • "Console bundle carries THIS tree's @objectstack/spec, and only it";
    • dist ready, 64460 KB, from objectui@1f23d5b070fa.

    That run came before the manifest regeneration, so its dist ships the previous tracked manifest. The dist is gitignored, and CI and the release build their own.

  3. pnpm check:console-sha and pnpm check:console-injection: both exit 0, inside the gate run below.

Smoke boot. pnpm dev -- --fresh -p 43198 from this worktree:

  • GET /api/v1/health answered 200 (status: ok, version 18.0.0-next.1).
  • GET /_console/ answered 200 (18552 bytes), and its entry assets/index-zcLuSSpu.js answered 200.
  • The served /_console/.objectui-sha reads 1f23d5b070fa4d0cee0274902944d247bc4588b7.

I stopped the server by its listening PID and the recorded pnpm PID, and the port was free afterwards.

Verification, at 7ab227d26

  • Tests that read the changed artefacts.
    • pnpm --filter @objectstack/sdui-parser exec vitest run: 14 files, 225 passed.
    • pnpm --filter @objectstack/lint exec vitest run src/validate-jsx-pages.production-witness.test.ts: 5 passed. It feeds the real repo-root sdui.manifest.json to the validator.
    • The packages/cli tests that read a console dist manifest are left to CI. This diff changes no package source.
  • Derived gates. node scripts/pm/dispatch-gates.mjs --commands --repo objectstack-ai/objectstack (no paths, from the merge base) derived 69 commands. Each was run with its exit code recorded. --ran reports "69 derived, 69 run, 0 NOT-MEASURED, 0 UNRUN".
    • Two first exited 3 (prerequisite not met) and were re-run green at the same head. check-plugin-teardown-shape --self-test needed its fixture commit 621a48760788, fetched at depth 1 (48 cases). check:dual-build-cjs-loads needed a full turbo run build --filter=!@objectstack/docs (75 tasks); it then read 110 entry points across 68 packages.
    • Named here: check-sdui-manifest (sha256 370153544e9b…, 107 components, recorded at the live pin), its self-test (13 cases), check:sdui-lockstep, check:objectui-changeset, check-adr-0087-registration --base origin/main, check-changeset-no-major --base origin/main (pre mode) and check-empty-changeset --base origin/main.
  • NOT MEASURED: repo-wide pnpm lint and the Type Check lanes. Reason: both are CI-owned runs, and this diff adds no TypeScript.

Acceptance notes


Generated by Claude Code

fix(app-shell): the bell's and Home's activity feed reads the app objects only (#12530) (#12542)

objectui@1f23d5b070fa4d0cee0274902944d247bc4588b7

Claude-Session: https://claude.ai/code/session_016PVjjuVPte5XEJvaQx1E4t
Co-authored-by: Claude <noreply@anthropic.com>
…parser lockstep at 1f23d5b070fa

node scripts/gen-sdui-manifest-node.mjs over .cache/objectui-1f23d5b070fa/apps/console
(107 components, sha256 370153544e9b); pnpm gen:sdui-lockstep with OBJECTUI_ROOT at the
pin's build worktree (grammar blob 0131f27cf86d and predicate blob 76c18fb95d1f unchanged).

Claude-Session: https://claude.ai/code/session_016PVjjuVPte5XEJvaQx1E4t
Co-authored-by: Claude <noreply@anthropic.com>
@github-actions github-actions Bot added size/m documentation Improvements or additions to documentation tooling labels Oct 15, 2026
@github-actions

Copy link
Copy Markdown
Contributor

📓 Docs Drift Check

⚠️ 1 changed file(s) yielded no anchor (packages/sdui-parser/objectui-lockstep.json), so the pages documenting them are NOT COVERED by this run — this is not a clean bill of health for those files. Nothing else in this diff resolved to a documentable surface (no symbol, route or SDK anchor derived from 1 changed package(s)).

What this run could not see
  • 1 changed file(s) yielded no anchor (packages/sdui-parser/objectui-lockstep.json) — pages documenting those are invisible to this run
  • a page that states a rule by its inputs shares no identifier with the emitter that implements the rule, so an emitter-only diff cannot list it — not on this run and not on any run. Measured on fix(driver-sql): emit varchar(maxLength) for a text field a declared index keys on #11430: content/docs/protocol/objectql/types.mdx documents the text-family column mapping by the ObjectQL type names it maps FROM (text / textarea / html) while the diff changed createColumn; it went unlisted, and it was the page that diff falsified, in four places. No shared token exists to detect this on, so a rule your change carries has to be re-read by hand in the pages that restate it.
  • a key NAME is not a key, so the hand re-read the line above prescribes can land on the wrong schema. The same spelling is authorable on one governed type and a [REMOVED] tombstone on another for each of active, aria, joins, objects, template, tools and version (censused on [finding] tools is a key on BOTH AgentSchema (tombstoned, dead) and SkillSchema (live, cloud-attested), so a name-based search attributes skill examples to the agent key — it produced a false stop-the-line alarm on PR #19059 #19093 over the liveness ledger's governed types, top-level keys); nothing in a search result distinguishes the two, so a grep hit on a LIVE example reads as evidence about the DEAD key. Measured on fix(spec): the agent.tools liveness row says dead — it claimed live on a key the schema tombstoned #19059: content/docs/ai/agents.mdx was reported as contradicting the agent.tools tombstone over its tools: example at :161, which is inside the defineSkill({ block opened at :155 — the page was already correct. Settle ownership by PARSING the value against both schemas, never by the name: that literal PASSES SkillSchema, and as an AgentSchema it FAILS at tools with the tombstone prescription. ⛔ These names are not the whole class — a key retired through a .strict() guidance map leaves no tombstone in the walked shape and none of them here (tool.category, live as AIToolDefinition.category).

Coarse fallback — 3 page(s) merely mention a changed package (the pre-#9192 predicate, kept for the deliberately-wide backstop): node scripts/docs-audit/affected-docs.mjs --json 69351e985a76972227abae61250d5815e66f5776 → packageMentionDocs.

@objectstack-fleet

Copy link
Copy Markdown
Contributor Author

席位核对 · ACCEPT · PR #23709 (draft, head 7ab227d26, Fixes #23691) · domain:devx seat 2 · session_016PVjjuVPte5XEJvaQx1E4t · 2026-10-15T17:52Z

Checked on GitHub and against the sources, not on the report's say-so.

  • Shape:
    • 5 files, +141 / −10, inside the claim's surface (6197566516): .objectui-sha, the derived console changeset, sdui.manifest.json with its record, and packages/sdui-parser/objectui-lockstep.json.
    • No packages/spec/src/**, no objectui source, no hand edit to packages/console/dist/.
    • Not governed: check-governed-merges.mjs --pr 23709 read 0 of 5 paths, 151 lines.
    • The body's only closing keyword is Fixes #23691. Clause-②: no is at line start.
  • Target: objectui 1f23d5b070fa. By REST compare, it is 83 ahead of / 0 behind the old pin b9814b334d8a, 12 ahead of 720f6d4 and 2 ahead of b512428, so it carries both fixes. Its objectui required set was green per the dev's reading (41/41 at 17:43Z); the newer main tip was still running. The pin moves only to that commit.
  • The two security readings, re-read by the seat in objectui at 1f23d5b070fa:
    • (a) get('handoffPrompt') under packages/apps: 0 hits at the new pin, 1 at the old pin (control). The pin test AiChatPage.handoffNeverFromUrl-12493.test.tsx is present. The dev's built-bundle reading is 0 hits for the URL read and 1 for the .get('package') control in the same chunk.
    • (b) useCanReadAuthoringTrail is declared at hooks/useCanAuthorMetadata.ts:72 over AUTHORING_TRAIL_CAPABILITIES = ['studio.access', 'manage_metadata'] (:58). It is called at ResourceEditPage.tsx:1210 and PermissionMatrixEditor.tsx:476, and the pin test trailDoorsGate-12475.test.tsx is present. No live browser run (source plus bundle reading only); accepted as dispatched.
  • Generated artefacts:
    • sdui.manifest.json and its record are regenerated from the built tree at the pin: 107 components, sha256 370153544e9b…. They are not hand-edited.
    • The manifest drops the retired provider: "api" wording and adds record:related_list.parentDataSource, matching objectui at the pin.
    • The lockstep record is re-recorded with no grammar move.
  • Changeset prose, checked sentence by sentence by this seat:
    • The frontmatter is major, from objectui#12334's declared sync major, with .changeset/pre.json in pre mode on next. The "83 non-merge commits" equals the compare count. The closing range line b9814b334d8a...1f23d5b070fa equals the .objectui-sha diff.
    • The two security entries (b51242899: "no longer reads ?handoffPrompt= from the URL"; 720f6d475: "show History and Audit only to a caller the authoring-trail doors admit") match the source read above.
    • Each of the ADR-0087 not-required block's five answers was re-read on origin/main:
      • page.zod.ts:989 refuses page kind: 'jsx';
      • view.zod.ts:198 refuses view.data.provider: 'api';
      • topbar.switchObject has 0 readers;
      • no package or example depends on @object-ui/* (0 manifests).
    • The form equals the last landed hop's changeset (325a92e26).
  • Gates:
    • Local: the dev's 69 derived commands at 7ab227d26 (--ran: 0 NOT-MEASURED). check:objectui-pin-citations no longer exists (retired 1418de4c7), so the PM's assumption there was falsified, and correctly reported.
    • CI on 7ab227d26, read at this act: 24 success, 6 skipped (the expected-skip roster names), 8 in progress (Test Core 1–6/6 and two Type Check lanes), 0 failed. The landing waits for every check to be green.
  • Out of scope:
  • Landing: once every check on the current head is green, the seat readies this PR and arms auto-merge through the relay, then confirms MERGED on origin/main.

Generated by Claude Code

@objectstack-fleet
objectstack-fleet Bot marked this pull request as ready for review October 15, 2026 18:15
@objectstack-fleet
objectstack-fleet Bot enabled auto-merge October 15, 2026 18:15
@objectstack-fleet
objectstack-fleet Bot added this pull request to the merge queue Oct 15, 2026
Merged via the queue into main with commit 53e3638 Oct 15, 2026
41 checks passed
@objectstack-fleet
objectstack-fleet Bot deleted the claude/issue-23691-console-pin-hop branch October 15, 2026 18:44
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

documentation Improvements or additions to documentation size/m tooling

Projects

None yet

2 participants