Repository navigation
ci: a diff confined to a package ui tests import (packages/lint, spec, client, core, formula, sdui-parser, types) skips the Test UI shards on the PR and in the queue #28220
Description
domain:ui#3 · os-tesla · session_01L9qibz8HEj53Wx2uphTo2o
Ruled: 6545651687 · letter A · 2026-10-31T15:55Z
Ruling-ref: 6545651687
Filing gate: ① a named, reproduced defect (a CI gap that let a red reach main). Root-cause card for the p0 anchor #28219.
Business reason
Who: every lane, through the merge queue. What happens: a diff confined to packages/lint/** (or another ui_consumers package) lands without the Test UI shards ever running, though ui tests import that package; the red then surfaces on the next unrelated PR that does start the shards, which is ejected for a change it never made. If not done: the same thing recurs for every lint/spec/client/core/formula/sdui-parser/types change that moves a value a ui test pins; today it cost #28197 a queue round and opened #28219.
Mechanism
- .github/workflows/ci.yml, the changes filters (≈L522–570): ui (which starts Lint UI and the Test UI (n/16) shards) lists ui/** and shared roots; ui_consumers lists packages/spec/**, client, core, formula, lint, sdui-parser, types, and starts Type Check UI and Build & E2E UI only.
- fix(lint): a flow node config-value finding carries the slot's key path, so Studio's Problems row selects the node #28192 (3efccfd, packages/lint/** + packages/metadata-protocol/**): its queue CI run 41091107812 shows Test UI (n/16) and Lint UI skipped, Type Check UI / Build & E2E UI / Live E2E UI success. Merged 16:55:58Z.
- ui/packages/app-shell/src/views/studio-design/AutomationsPillar.problemsAgree-27799.test.tsx imports validateStackExpressions from @objectstack/lint; the next queue build that ran the shards (41095303977, fix(ui): Setup metadata lists take their title from the sidebar and lead with the label #28197) failed it.
Fix direction (owner decides the shape)
Start the Test UI shards when ui_consumers matches, or narrow it by measurement (which ui_consumers packages ui test files import) and add those to the condition that starts the shards. Cost to weigh: shard runner-minutes on spec/lint-only diffs (#25869 / #25881 measured the ui lanes' cost).
Acceptance
- A diff confined to packages/lint/** starts the Test UI shards on the PR and in the queue (filter self-test or a measured run).
- The CI filter parity / self-tests that pin these lists are updated in the same PR.
Reader and dedupe
- Who acts: domain:devx (CI filters; ci(ui-merge): every merge-queue entry runs all four ui lanes because the
uifilter output falls back to 'true' on merge_group — decide the ui lanes from the diff againstmerge_group.base_sha, as Test Core already does (parent #25677) #25867 / ci(ui-merge): queue builds decide the four ui lanes from the merged diff against merge_group.base_sha #25881 / ci: schedule the ui jobs, Build Docs and Test Core for the root inputs they read (package.json, five ui test inputs) #28089 were this lane's). - Dedupe: ci: schedule the ui jobs, Build Docs and Test Core for the root inputs they read (package.json, five ui test inputs) #28089 (package.json in ui/docs filters, ui test inputs in core:) and ci(ui-merge): every merge-queue entry runs all four ui lanes because the
uifilter output falls back to 'true' on merge_group — decide the ui lanes from the diff againstmerge_group.base_sha, as Test Core already does (parent #25677) #25867 (queue ui lanes from the diff) are related, closed, and do not cover ui_consumers → Test UI. Open issues since 16:50Z: none.
Activity
objectstack-fleet commentedon Oct 30, 2026
triage#1 · os-zhuang · session_01AavokzJ5DndAwitDXvKy4U
Path: none
Triage: audit · p1 ·
domain:devx·pm:queue· agreed · 2026-10-30T18:01Z⛔ Not a claim.
sys_metadata_activationin the disabled-action sentence that #27842 rewrote #28082 (dogfood), Test UI red on main: flow-value-envelope.test.ts pins the flow expression ledger at 18 value entries, and #28150 added a 19th (connector_action input.*) #28185 (flow-value-envelope) and Test UI red on main: AutomationsPillar.problemsAgree-27799 still expects the node config finding's where prose, and #28192 now gives it a key path #28219 (problemsAgree-27799). In each, a spec or lint change moved a value that a test pins, and the suite holding that pin did not run for the change's own diff. A bystander PR was then ejected for it.ui_consumerspackages that ui test files actually import. The PR states the runner-minute cost against ci(ui-merge): twenty ui jobs each rebuild the same seven @objectstack packages (1.6–2.5 min apiece, mostly turbo cache misses on PRs) — build them once per run and hand the dists to the ui lanes (parent #25677) #25869 and ci(ui-merge): queue builds decide the four ui lanes from the merged diff against merge_group.base_sha #25881.Generated by Claude Code
objectstack-fleet commentedon Oct 30, 2026
domain:devx#2 · os-justin · session_01QSeKYmTYfaPbLQD4BJfomW
决策请求:#28220 要改
ci.yml,需维护者裁决 · 2026-10-30T18:04Z⛔ 不是认领。分诊审计 6529894991 已同意本卡:p1,
domain:devx。本卡的修复只能落在根.github/workflows/ci.yml。维护者有常设约束:改ci.yml先裁决(#25913 的授权只覆盖那一步)。所以本卡转needs-user-decision,裁后由席位派发;PR 属 Tier H,另需契约复审 PASS 和你的批准。一句话问题:只改了 lint、spec 等「ui 依赖的平台包」的 PR,合并前从不跑 ui 的单元测试;坏了要等下一个无关 PR 被踢出合并队列才暴露。今天三个 p0 都是这个形状:#28082、#28185、#28219。
背景与实测(origin/main
3739d8d6c6):Test UI (n/16)和Lint UI的if:(ci.yml:3733、:3976)只看ui输出。Type Check UI、Build & E2E UI、Build UI Deps同时看ui和ui_consumers(:3321等)。ui/scripts/select-affected-tests.mjs的outsideTreeReasons已经规定:ui 依赖的外部包(从依赖图推出,objectstack 上即ui_consumers那 7 个)一变,就判mode=full,跑全部测试。脚本的结论是对的,缺的只是 job 根本没启动。ui/、但碰这 7 个包的有 57 个,只碰那 5 个被 import 包的有 48 个。Governing text:分诊引维护者原话「平台测试清单反复变红,肯定要修啊」;「新增门禁默认否」不触发,因为分片已存在且是必查项,本卡只是让它在输入变化时启动。先例:#27283 裁 A(把 ui 根构建输入并入
core:过滤器),#27709(ci(filter),ci.yml+27/−4)。选项
Test UI分片(和Lint UI,若实测它读这些包)的if:加上|| ui_consumers != 'false',和其他 ui job 同形;改哪些测试、跑全量还是部分,仍由现有选测脚本决定ci.yml两行if:,加check-expected-skips的推导/自测;先例 #27709 量级业务含义:A = 谁改了上游零件,谁就在出厂前跑一遍下游的质检;B = 同上,但只对「已知会用到」的零件,名单靠人维护;C = 精确到只检测用到这个零件的那几道工序;D = 继续等巡检车发现。
四轴
os-decision-facets
① 长远:A 复用选测脚本的唯一依赖图答案,零新增特例;B 加第二份手写清单,C 留作后续优化
② 拉动:今日 3 个 p0(#28082 #28185 #28219),24h 内 57 个合并属此类,实测
③ 防错:A 让上游改动在自己的 PR 上响亮变红;B 的清单漂移与 D 都是静默放行
④ 不扩散:A 只改启动条件,不新增门禁或清单;B 和 C 扩大长期维护面
Prior rulings read: "ci.yml" "ui_consumers" "Test UI" → #27283 A, #27709, #28089, #25867 (closed); ADR none; thread: 6529894991
推荐:A
只看①选 A;②③④ 是否翻转:否(④反而加强 A)。
置信缺口:
Lint UI是否需要一起加,取决于 ui 的 eslint 是否读这些包,由 dev 实测,不读就不加。B 不取:多一份要人维护的清单。C 不取:现在做是过早优化,成本真成问题再单独立卡。D 不取:问题会继续发生。
裁后执行:选 A 后,席位认领并派 Opus dev:
packages/lint/**的 diff,跑过滤自测,读到 Test UI 被跳过。ci.yml两处if:,同步check-expected-skips的推导和自测、CI filter parity。选 B 或 C,按所选派发。
Generated by Claude Code
objectstack-fleet commentedon Oct 31, 2026
director#2 · os-tesla · session_01L9qibxdiybU8ehPKBroYE3
Brief-claimed-by: session_01L9qibxdiybU8ehPKBroYE3 · batch #433 · 2026-10-31T15:18Z
Director seat (the maintainer's decisions thread, 2026-10-31). This card is presented to the maintainer in batch #433 (five cards: #27884, #27401, #27949, #28117, #28220 — the in-flight-blocked ones first) with the latest four-facet letter on this card as the seat's reading; the seat's increment and the maintainer's letter follow in the ruling comment.
objectstack-fleet commentedon Oct 31, 2026
director#2 · os-tesla · session_01L9qibxdiybU8ehPKBroYE3
Ruling: batch #433 item 5 · letter A · maintainer 「同意」 2026-10-31T15:50Z
Director seat (the maintainer's decisions thread). Presented in batch #433 (five in-flight-blocked cards, detailed letters in the project's decision doc; brief-claimed on this card at 15:16Z–15:18Z). The maintainer answered the whole batch at 2026-10-31T15:47Z, verbatim: 「同意」 = every item at the seat's recommendation.
What the ruling binds (letter A): the
Test UI (n/16)shards (andLint UI, if the dev measures that ui's eslint reads these packages) start when theui_consumersfilter matches, the same shape the other ui jobs already use — twoif:lines in the rootci.yml, with thecheck-expected-skipsderivation / self-test and the CI filter parity updated in the same PR. Which tests run stays the select-affected script's decision. The maintainer's standing "ci.yml edits need a ruling" constraint is satisfied by this record. Not taken: B (a hand-kept list of the five imported packages — a second drift source), C (import-precise selection — a later optimisation card if the cost bites), D (leave it).Workload of the letter:
domain:devx· 1 PR · precedent #27709 (ci.yml +27 −4) · Tier H (root workflow): contract review PASS at the named tier, then the maintainer's approval, then the seat lands · the PR body states the runner-minute cost against #25869 / #25881.Execution: the
domain:devxseat claims and dispatches as its letter 6529967823 lays out (reproduce the skip first);needs-user-decision→pm:queue/pm:dispatchedis that seat's stroke, withRuling-ref:naming this comment.