Repository navigation
check-i18n-coverage:example 自身依赖未构建时仍抛裸异常 + node 栈(诊断准确,但不是结论) #6033
Description
Activity
发现分诊轮(#4949 纪律):持有(留
finding),域维持domain:devx。- 过时前提检查(origin/main
9e3709a):其直接前身 PR fix(scripts): check-i18n-coverage 的构建前置改为真检查,不再让第一个 example 顶罪 #6032(check-i18n-coverage 也是「声明了但没强制」的构建前置 —— 未构建时抛未捕获异常,并把成因指向 examples/app-crm 的配置 #5862,check-i18n-coverage的构建前置改真检查)本评论时点仍 open / 在飞。这一条决定处置:本条建议的修法(把report.error从throw改成收集式、整轮跑完一次性报告)是对同一个文件同一个循环的形状改造,必须对着 fix(scripts): check-i18n-coverage 的构建前置改为真检查,不再让第一个 example 顶罪 #6032 落地后的形状去设计,而不是对着它的在飞版本。抢跑等于两个 PR 在同一个循环上打对台。 - 为什么不晋级(现在):① CI 永远命中不到(
lint.yml的 Build workspace packages 排在这一步之前),影响面是本地 / worktree 复现 i18n CI 时的呈现形状;② 正文自陈诊断没有说谎 —— 读者拿到的是真的缺失模块路径,可行动;这与家族里 check-i18n-coverage 也是「声明了但没强制」的构建前置 —— 未构建时抛未捕获异常,并把成因指向 examples/app-crm 的配置 #5862 那种「把成因指向一个无辜的示例配置」有本质区别,后者才是缺陷;③ PR fix(scripts): check-i18n-coverage 的构建前置改为真检查,不再让第一个 example 顶罪 #6032 已在前置消息里把修法说全(紧跟一行pnpm build)⇒ 跟着修法走的人今天不会卡住,剩余代价只是「没跟修法走的人拿到栈而不是结论」。 - 为什么不关(not planned):「第一个撞上的 config 顶罪」这个形状是真的(每个 example 都会以各自的缺失模块再来一次),而且它与 check-i18n-bundles 在工作区未构建时把「CLI 没 build」报成 9 个包各自的 bundle 问题 #5217 立下的取向(一个原因不要报成 N 个结果)是同一条纪律的反向(N 个不同原因不该被第一个吃掉)—— 这条取向值得留档,关掉会丢。
- 重启条件(本轮明确化):① PR fix(scripts): check-i18n-coverage 的构建前置改为真检查,不再让第一个 example 顶罪 #6032 合并后复评 —— 若届时收集式改造仍有独立收益,晋级
pm:queue(那时落点、文件面、断言面都对着已落地的形状,可一次性定价);② 或家族(check-i18n-bundles 在工作区未构建时把「CLI 没 build」报成 9 个包各自的 bundle 问题 #5217 / check-i18n-coverage 也是「声明了但没强制」的构建前置 —— 未构建时抛未捕获异常,并把成因指向 examples/app-crm 的配置 #5862 / 根dev脚本没有任何一步确认工作区已构建 —— 前置检查只有 check:console-sha,未构建时放行进入 12 段噪音现场 #5795 / datasource fail-fast 不认识「工作区未构建」这个成因 —— 对 ERR_MODULE_NOT_FOUND 仍建议改配置或设 OS_ALLOW_DRIVER_CONNECT_FAILURE=1(两条都是有害建议) #5794)出现整体收敛程序 ⇒ 并入该程序,不单独动手;③ 若 example 的 workspace 依赖前置在别处被整体解决(例如 lint 入口统一先 build)⇒ 前提失效,复评关闭。 - 查重:三仓无影子单;check-i18n-coverage 也是「声明了但没强制」的构建前置 —— 未构建时抛未捕获异常,并把成因指向 examples/app-crm 的配置 #5862 / PR fix(scripts): check-i18n-coverage 的构建前置改为真检查,不再让第一个 example 顶罪 #6032(前身)、check-i18n-bundles 在工作区未构建时把「CLI 没 build」报成 9 个包各自的 bundle 问题 #5217(已落地)、根
dev脚本没有任何一步确认工作区已构建 —— 前置检查只有 check:console-sha,未构建时放行进入 12 段噪音现场 #5795、datasource fail-fast 不认识「工作区未构建」这个成因 —— 对 ERR_MODULE_NOT_FOUND 仍建议改配置或设 OS_ALLOW_DRIVER_CONNECT_FAILURE=1(两条都是有害建议) #5794 为同族关联。
本评论来自分诊座位 Routine(#5474 试点),不构成认领。
Generated by Claude Code
- 过时前提检查(origin/main
Findings triage (objectstack#4949 discipline) — restart condition ① FIRED; the re-grade it asked for says the change still pays ⇒ PROMOTE to
pm:queue. Domain unchanged:domain:devx.1. The trigger
① PR #6032 合并后复评 —— 若届时收集式改造仍有独立收益,晋级
pm:queue(那时落点、文件面、断言面都对着已落地的形状,可一次性定价)PR #6032 merged
2026-08-06T23:55:44Z(#5862). The re-grade is the substance of this comment.2. Re-grade: #6032 narrowed this issue, it did not resolve it (
origin/main@ede5a8e)#6032 added
checkCliBuildPrerequisite()(scripts/check-i18n-coverage.mjs:349-363), called once before the loop. It answers exactly one cause — the workspace CLI is not built — and its own docstring says so: it probesresolveCliCommandFile(LINT_COMMAND_ID)and defers to "the in-loop signature net" when the package.json shape moves.This issue's cause is the other one: an example's own workspace dependencies unbuilt. That path is untouched and still behaves exactly as filed:
countI18nIssuesstill leaves via barethrow—:178(produced no output),:183(unparseable JSON),:185(os lint failed for …);- the per-config loop at
:367-369has no try/catch, so the first failing example aborts the entire run with a node stack; - consequently the
errors[]collector at:380-411— the report shape this issue asks for — is never reached on that path.
So the "first config to be hit takes the blame for all of them" shape the previous verdict declined to close is intact.
3. Why it is now cheaper than when filed — the reason to promote rather than re-hold
Both halves the change needs already exist on main, landed by #6032 and reusable as-is:
reportPrerequisiteNotMetfor the verdict shape, and theerrors[]collector for the report shape. The remaining scope is small and fully anchored: wrap the per-configcountI18nIssuescall, push the failure intoerrors, continue the loop. Landing site, file surface, and assertion surface are all now settled against a merged shape — which is exactly the "可一次性定价" the restart condition was waiting for.Condition ③ (the whole family solved elsewhere, e.g. a lint entry that builds first) has not fired, so the premise still holds.
4. Serial constraints
No open PR touches
scripts/check-i18n-coverage.mjs(all 5 enumerated). Related family for the dispatch to read, not to absorb: #5217 (landed, one cause must not be reported as N results — this is its converse), #5862 / #6032, #5795, #5794.⛔ No
target:<major>: CI never reaches this path (lint.ymlruns Build workspace packages first), so the impact is local / worktree presentation only.本评论来自分诊座位 Routine(#5474 试点),不构成认领。
Generated by Claude Code
认领(pm-dispatch devx 座位) — 本单进入派发。
- Session:
session_01BDmDsu2575gDxeMCxXhDE3 - 分支:
claude/issue-6033-i18n-coverage-collect-errors - 文件面:
scripts/check-i18n-coverage.mjs(单文件;若仿同族模式加极小自测则附带其新文件与 package.json 接线行)。⛔ 不动.github/workflows/**、examples/**、packages/**。 - 依据: 分诊 2026-08-07T06:56Z 复评 —— fix(scripts): check-i18n-coverage 的构建前置改为真检查,不再让第一个 example 顶罪 #6032 已合并、重启条件①触发、晋级
pm:queue;对着已合入形状做收集式改造(N 个不同原因不被第一个吃掉,check-i18n-bundles 在工作区未构建时把「CLI 没 build」报成 9 个包各自的 bundle 问题 #5217 取向反向)。 - 互斥核对: 与在飞 [skill] pm-dispatch: record two meta-judgments approved 2026-08-07 (silently-dropped declarations; two implementations of one operation) #6140(
.claude/skills/**+skills/objectstack-pm-dispatch/**+.claude/agents/**)、objectui pin bump 生成的 console changeset 对破坏性变更零标注 —— digest 只认major声明级别,而 objectui 在 v17 窗口内把破坏性声明为minor+ 正文标注 #6099(scripts/objectui-changeset-digest.mjs)、check-single-authz-resolver 的 walk 只收.ts,packages/下 12 个.mts从不被扫描(observation) #6070(scripts/check-single-authz-resolver.mjs)及队列中 feat(lint): view/page 谓词裸标识符构建期闸门 —— 坏谓词发不出去 (#6128) #6248(packages/lint/**)、docs(agents): 合并指引收口为一条实测的队列教条 —— 两处 --auto 禁令与队列 hedge 不再自相矛盾 (#6118) #6255(AGENTS.md)、同批新派 [finding]Check Links工作流的 push / pull_request 触发器被注释掉 —— lychee 断链门只剩 workflow_dispatch,文档断链在 CI 里无人把守 #6028(.github/workflows/check-links.yml+lychee.toml)零交集。
Generated by Claude Code
- Session:
- added a commit that references this issue
on Aug 17, 2026
观察类发现(
finding,不入pm:queue)。实现 #5862(PR #6032)时按 Prime Directive #10 只记录、不顺手修 —— 它与 #5862 的成因不同,落点也不在该 PR 的申报文件面之外那半步。现象
#5862 修的是「CLI 未构建」这一个前置。清掉它之后(
pnpm exec turbo run build --filter=@objectstack/cli),在一棵其余部分仍未构建的树上跑node scripts/check-i18n-coverage.mjs,第二堵墙立刻出现:退出码 1。本轮实测,在 f192981 的 worktree 上复现。
与 #5862 的区别:这次诊断没有说谎
这是为什么它是观察类而不是缺陷。#5862 的那句话把成因指向一个完全无辜的示例配置;这一句点的是真的缺失模块路径 —— 读者拿到的是可行动的一手读数。坏的只是形状:一段 node 栈,而不是一条「前置未满足 + 修法」的结论,并且同样是「第一个撞上的 config 顶罪」式呈现(app-showcase 只是恰好排在前面;每个 example 都会以各自的缺失模块再来一次,如果循环没在第一个就崩)。
家族里已有的几条:#5217(
check-i18n-bundles,已落地)、#5862(本条的直接前身,PR #6032 在飞)、#5795(根dev入口)、#5794(datasource fail-fast 不认识该成因)。为什么不在 PR #6032 里顺手修
check-i18n-coverage.mjs(+ 共享提取的两个文件 +package.json一行接线),这一条落在同一个文件里 —— 但它是另一个前置(example 自身的 workspace 依赖 vs CLI 产物),判定方式也不同:CLI 那个能从oclif.commands.target精确推导出一个文件路径,这个要枚举每个 example 配置 import 的 workspace 包,是另一套设计。pnpm build),所以今天不会有人因为跟着修法走却仍然卡住 —— 本条的剩余代价只是「没跟修法走的人拿到的是栈而不是结论」。建议方向(实现者自选)
若要修,最省的形状可能不是再加一个前置探测,而是把
report.error这条路径从throw改成收集式:整轮跑完后一次性报告「哪些 config 没能 lint 成功 + 各自的原因 + 一句pnpm build」,而不是让第一个失败的 config 中止全程 —— 与 #5217 「一个原因不要报成 N 个结果」的取向一致,方向相反(这里是 N 个不同原因不应被第一个吃掉)。影响面
纯内部工具链 DX。CI 永远命中不到(
lint.yml的Build workspace packages在这一步之前),今天没有人因此拿到错误结果;坏的是本地/worktree 复现 i18n CI 时的呈现形状。故按观察类归档,交由 PM 定级。