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 }}
Repository navigation
ci(ui-merge): Test UI runs the whole suite on every pull_request and merge_group run — wire objectui's ui/scripts/select-affected-tests.mjs into the merged ci.yml now that the repo-root migration it waited on has landed (parent #25677) #25868
Filing gate ③ (maintainer-directed) + ④: aftercare of the ui/ merge (#25752), part of #25677. Touches .github/workflows/ci.yml = Tier H: GOVERNED_APPROVERS review, the PR stops at draft.
Maintainer, 2026-10-26 01:45Z, in the project thread that measured post-merge CI speed: 「创建issue」 (asked after reading the ranked fix list; this is item 2).
谁付代价(业务筛): ui developers. In the objectui repo, a small ui PR ran only the tests its change could reach and finished CI in 3–8 min. In the merged repo, every ui PR runs all 16 Test UI shards (7–14 min each, ~190 runner-min), so a one-file fix waits ~14 min.
Measured
objectui CI, last 50 PR runs before the freeze: median 12.0 min, p90 14.8 min (n=36 successful). Affected-only runs: 2.8–8.1 min (e.g. 40154823798 2.8, 40159908661 4.2, 40161091709 7.2).
objectstack post-merge: Test UI full on every event. In run 40251065567 (ci.yml-only change) the 16 shards took 6.6–12.0 min each, 184 runner-min in total. In run 40248884869 they took 8.5–14.3 min.
Vitest in shard 6/16 (run 40248884869): Duration 590 s, of which tests 210 s; import 1148 s and setup 235 s (summed across workers).
Port objectui's wiring into the root ci.ymltest-ui job: pull_request uses the PR base, merge_group uses merge_group.base_sha, and mode=full / mode=affected behave as in objectui. Fail open: a selector error means a full run.
push / schedule keep the full battery (maintainer ruling 2026-10-25 Q6-b).
The wiring test follows the root workflow, not the retired ui one. The gate rosters follow; each --self-test exits 0.
Acceptance
On a one-package ui PR, Test UI runs only the selected files. On the card: shard wall times before and after.
A change to ui/package.json or ui/vitest.config.* still selects mode=full.
Expected saving: small ui PRs back to ~3–8 min CI; up to ~190 runner-min per run. Size: M. Clause-②: no. Metadata-protocol: none.
Acceptance note (optional, measure only): Test UI time is mostly module import, not tests (import 1148 s vs tests 210 s above). If the seat sees a cheap vitest setting that moves this, report the reading. It is not part of this card.
Dedupe
search_issues 2026-10-26 01:50Z 「wire ui select-affected-tests.mjs Test UI affected selection git root relative paths」: 13 hits. Related ones are closed prerequisites (#25728, #25723, #25733, #25763) or the wiring parent #25697, which carries the comment and no task for this. New.
Claim: epic #25677 round 8 (post-cutover CI speed cards; Tesla 2026-10-26 01:45Z 「创建issue」) 2026-10-26T01:56Z
Session: session_01RSDL3SFtJaKzcymvCD8RsU
Account: os-tesla
Branch: claude/project-thread-n0iri6 (the card thread's designated branch in objectstack-ai/objectstack — the thread can push only this branch, a measured platform exception to claude/issue-<n>-<slug>)
Worktree: objectstack-issue-25868
Domain: domain:devx
Seat: epic:#25677
Scope: the whole card — port objectui's selector wiring into the root ci.ymltest-ui job (pull_request base / merge_group.base_sha, mode=full / mode=affected, fail-open to full), make ui/scripts/select-affected-tests.mjs read git paths relative to ui/ (nestedPrefix(), #25728) and its turbo ls --affected parity test pass nested; push/schedule keep the full battery (Q6-b); the wiring test follows the root workflow; the gate rosters follow with --self-test 0; Tier H (draft, os-zhuang + hotlong), skip-changeset
Why now: every ui PR runs all 16 Test UI shards (~190 runner-min, ~14 min wall) where objectui ran 3–8 min affected-only; the prerequisites (#25723, #25728, #25733) are closed
Container & model: M, mode:thread (thread session session_015oJuSyTy7Y3cm91KJMEW2m; order: this card's body, FRAME.md applies), model: opus, effort: xhigh
Clause-②: no
Metadata-protocol: none
Responsibility: n/a — epic step
Thread-read: none
Serial constraints cleared: #25867 edits only the filter job of the same file (branch claude/project-thread-8dceid); the #25853 seat's Type Check UI row PR edits scripts/check-required-contexts.mjs and the two statesTheSet surfaces, not ci.yml; #25869 is held until this and #25868 land. Rebase over whichever lands first; ⛔ do not change the test-ui job's if: or shard count; a selector error means a full run, never a skipped one
{
"issue": 25868,
"status": "done",
"branch": "claude/project-thread-n0iri6",
"pr": "https://github.com/objectstack-ai/objectstack/pull/25882",
"session": "session_015oJuSyTy7Y3cm91KJMEW2m",
"premise_still_valid": true,
"summary": "Root ci.yml test-ui now has objectui's select step (id select) and a run step that reads its mode output: pull_request diffs from merge-base(origin/BASE_REF, HEAD), merge_group from base_sha, every other event and every selector failure is a full run; checkout takes fetch-depth 0. The selector already read ui-relative git paths (#25728), but its diff dropped every changed file outside ui/, so a lockfile, root tsconfig or packages/spec change selected only the always-on set; new changedOutsideTree/outsideTreeReasons turn a non-doc workspace-root file, patches/, or one of the seven ui_consumers packages (derived from the dependency graph, not listed) into a full run. Wiring test and the selector's ci.yml block now read the root workflow; new nested-layout fixture cases.",
"tests": "ui: vitest run scripts/__tests__/select-affected-tests.test.ts + select-affected-tests-wiring.test.ts -> 2 files, 49/49 pass (head bc79c8aa). Whole ui scripts/__tests__ -> 190 files, 5608 pass, 2 skipped, 1 fail: check-pre-install-import-graph.test.ts (unresolved scripts/objectstack-pin.mjs), reproduced on c475b45b with this diff's four files restored (37 tests, 1 fail) = pre-existing on main. Selector probes: no ui change 686/5810 files (8.8% of dataset weight), plugin-gantt leaf 1036 (20.2%), plugin-kanban 2647 (54.2%), lockfile+packages/spec before = affected 686 (the hole), after = full.",
"gates": "dispatch-gates --ran: 63 derived, 59 exit 0, 4 NOT MEASURED exit 3 (no built dists): check:dts-closure, check:dual-build-cjs-loads, check:lean-entry-closure, check:sourcemap-no-sources-content -> Build Core runs them on the PR. CI on the PR: in_progress at report time.",
"dogfood_battery": "n/a — no ! in the PR title and no (narrowing) arm",
"mcp_calls": "0",
"api_writes": "2 relay writes: pr_create (fleet-write run 40260290346, #25882, body read back identical; relay's governed follow-up requested hotlong + os-zhuang) and this report comment; plus git push of the thread branch",
"open_questions": [],
"out_of_scope_findings": [
"class: a · reach: Test UI on main/PR runs ui/scripts/__tests__/check-pre-install-import-graph.test.ts and it fails 'finds no pre-install gate reaching a package' with unresolved: scripts/objectstack-pin.mjs (deleted at cutover, still named by ui/.github/workflows/*) · evidence: fails on c475b45b alone · dedupe words: check-pre-install-import-graph objectstack-pin.mjs unresolved Test UI red"
]
}
Evidence for the card's acceptance, read 2026-10-26T05:18Z from the first pull_request CI runs after #25882 merged (03:27:04Z, cb0a2fcf). Times are job wall clock from the Actions jobs API, started_at to completed_at.
Before (Test UI ran the full suite on every event): run 40248884869, 16 shards at 8.5–14.3 min; run 40251065567 (a ci.yml-only change), 16 shards at 6.6–12.0 min, 184 runner-min.
16 shards at 2.5–3.5 min, 46.7 runner-min; the test step itself 1.1–1.8 min per shard
The first two runs ran the full suite, as designed: a change to packages/lint or packages/spec reaches every ui test through the built output, and the selector says so.
In that run, Test UI (14/16) is red on ui/scripts/__tests__/check-pre-install-import-graph.test.ts (unresolved: scripts/objectstack-pin.mjs). This is the same failure as on main, not the selector's; the dispatcher has it.
Not read yet: a one-package ui PR (ui/packages/X only). Predicted from ui/scripts/test-shard-timings.json: plugin-gantt 20.2% of the full suite's file time, plugin-kanban 54.2%.
Activity
objectstack-fleet commentedon Oct 26, 2026
Claim: epic #25677 round 8 (post-cutover CI speed cards; Tesla 2026-10-26 01:45Z 「创建issue」) 2026-10-26T01:56Z
Session:
session_01RSDL3SFtJaKzcymvCD8RsUAccount:
os-teslaBranch:
claude/project-thread-n0iri6(the card thread's designated branch in objectstack-ai/objectstack — the thread can push only this branch, a measured platform exception toclaude/issue-<n>-<slug>)Worktree:
objectstack-issue-25868Domain:
domain:devxSeat:
epic:#25677Scope: the whole card — port objectui's selector wiring into the root
ci.ymltest-uijob (pull_requestbase /merge_group.base_sha,mode=full/mode=affected, fail-open to full), makeui/scripts/select-affected-tests.mjsread git paths relative toui/(nestedPrefix(), #25728) and itsturbo ls --affectedparity test pass nested; push/schedule keep the full battery (Q6-b); the wiring test follows the root workflow; the gate rosters follow with--self-test0; Tier H (draft, os-zhuang + hotlong),skip-changesetWhy now: every ui PR runs all 16 Test UI shards (~190 runner-min, ~14 min wall) where objectui ran 3–8 min affected-only; the prerequisites (#25723, #25728, #25733) are closed
Container & model: M,
mode:thread(thread sessionsession_015oJuSyTy7Y3cm91KJMEW2m; order: this card's body, FRAME.md applies),model: opus,effort: xhighClause-②: no
Metadata-protocol: none
Responsibility: n/a — epic step
Thread-read: none
Serial constraints cleared: #25867 edits only the
filterjob of the same file (branchclaude/project-thread-8dceid); the #25853 seat's Type Check UI row PR editsscripts/check-required-contexts.mjsand the two statesTheSet surfaces, notci.yml; #25869 is held until this and #25868 land. Rebase over whichever lands first; ⛔ do not change thetest-uijob'sif:or shard count; a selector error means a full run, never a skipped oneobjectstack-fleet commentedon Oct 26, 2026
os-dev-report
{ "issue": 25868, "status": "done", "branch": "claude/project-thread-n0iri6", "pr": "https://github.com/objectstack-ai/objectstack/pull/25882", "session": "session_015oJuSyTy7Y3cm91KJMEW2m", "premise_still_valid": true, "summary": "Root ci.yml test-ui now has objectui's select step (id select) and a run step that reads its mode output: pull_request diffs from merge-base(origin/BASE_REF, HEAD), merge_group from base_sha, every other event and every selector failure is a full run; checkout takes fetch-depth 0. The selector already read ui-relative git paths (#25728), but its diff dropped every changed file outside ui/, so a lockfile, root tsconfig or packages/spec change selected only the always-on set; new changedOutsideTree/outsideTreeReasons turn a non-doc workspace-root file, patches/, or one of the seven ui_consumers packages (derived from the dependency graph, not listed) into a full run. Wiring test and the selector's ci.yml block now read the root workflow; new nested-layout fixture cases.", "tests": "ui: vitest run scripts/__tests__/select-affected-tests.test.ts + select-affected-tests-wiring.test.ts -> 2 files, 49/49 pass (head bc79c8aa). Whole ui scripts/__tests__ -> 190 files, 5608 pass, 2 skipped, 1 fail: check-pre-install-import-graph.test.ts (unresolved scripts/objectstack-pin.mjs), reproduced on c475b45b with this diff's four files restored (37 tests, 1 fail) = pre-existing on main. Selector probes: no ui change 686/5810 files (8.8% of dataset weight), plugin-gantt leaf 1036 (20.2%), plugin-kanban 2647 (54.2%), lockfile+packages/spec before = affected 686 (the hole), after = full.", "gates": "dispatch-gates --ran: 63 derived, 59 exit 0, 4 NOT MEASURED exit 3 (no built dists): check:dts-closure, check:dual-build-cjs-loads, check:lean-entry-closure, check:sourcemap-no-sources-content -> Build Core runs them on the PR. CI on the PR: in_progress at report time.", "dogfood_battery": "n/a — no ! in the PR title and no (narrowing) arm", "mcp_calls": "0", "api_writes": "2 relay writes: pr_create (fleet-write run 40260290346, #25882, body read back identical; relay's governed follow-up requested hotlong + os-zhuang) and this report comment; plus git push of the thread branch", "open_questions": [], "out_of_scope_findings": [ "class: a · reach: Test UI on main/PR runs ui/scripts/__tests__/check-pre-install-import-graph.test.ts and it fails 'finds no pre-install gate reaching a package' with unresolved: scripts/objectstack-pin.mjs (deleted at cutover, still named by ui/.github/workflows/*) · evidence: fails on c475b45b alone · dedupe words: check-pre-install-import-graph objectstack-pin.mjs unresolved Test UI red" ] }Generated by Claude Code
objectstack-fleet commentedon Oct 26, 2026
Evidence for the card's acceptance, read 2026-10-26T05:18Z from the first
pull_requestCI runs after #25882 merged (03:27:04Z,cb0a2fcf). Times are job wall clock from the Actions jobs API,started_attocompleted_at.Before (Test UI ran the full suite on every event): run 40248884869, 16 shards at 8.5–14.3 min; run 40251065567 (a ci.yml-only change), 16 shards at 6.6–12.0 min, 184 runner-min.
After:
ui/packages/app-shell+packages/lint(one of the sevenui_consumers)ui/packages/app-shell,ui/packages/i18n+packages/lint,packages/specuifilter (unchanged)ui/scripts/(no ui package)packages/lintorpackages/specreaches every ui test through the built output, and the selector says so.ui/scripts/__tests__/check-pre-install-import-graph.test.ts(unresolved: scripts/objectstack-pin.mjs). This is the same failure as onmain, not the selector's; the dispatcher has it.ui/packages/Xonly). Predicted fromui/scripts/test-shard-timings.json: plugin-gantt 20.2% of the full suite's file time, plugin-kanban 54.2%.Generated by Claude Code