fix(scripts): test type-check 覆盖率改由解析后的 tsconfig 程序判定,schema-catalog 的测试接上编译 - #4004
Merged
Merged
Conversation
…fig program, not from text
`check-type-check-coverage.mjs` reported green while the four test files in
`examples/schema-catalog` were read by no `tsc` invocation, for two independent
reasons that overlapped on that one package:
- `countTestFiles` recursed `src/` only, and those tests live in `test/`, so
the count was 0 and section 5 skipped the package entirely;
- `buildExcludesTests` probed the tsconfig TEXT for a `*.test.` glob, and the
package keeps its tests out of the build by naming the DIRECTORY in
`exclude`, so the probe found nothing and reported "already covered".
Both text heuristics are gone. Test files are enumerated from the package root
(skipping `node_modules`/`dist`/`coverage`/dot-dirs), and coverage is decided by
resolving each tsconfig's `files`/`include`/`exclude` through `extends` and
asking whether the program really reads each file. Directory-form excludes then
fall out of documented semantics instead of needing a second special case, and so
does the shape one step over that no glob probe could catch: an `include` of
`src/**/*` with no `exclude` at all. Section 5b tightens with it — a chained
`tsconfig.test.json` now has to read the files the build skips, not merely
mention a test glob somewhere.
`examples/schema-catalog` is wired up accordingly: a `tsconfig.test.json`
chained from `type-check`. Compiling those tests for the first time exposed one
real defect — `@object-ui/fields` was imported by `fields-form-hosted.test.tsx`
and declared nowhere, a phantom dependency that only resolved through vitest's
aliases — now a devDependency. With it declared, the four files compile at zero
errors, so no TEST_DEBT entry is needed.
`scripts/__tests__/check-type-check-coverage.test.ts` pins all of it against
throwaway package trees, including the exact shape of this bug and the two
retired predicates reproduced as executable statements, so neither blind spot can
return as a simplification.
Fixes #3968
|
The latest updates on your projects. Learn more about Vercel for GitHub. |
Contributor
✅ Console Performance Budget
📦 Bundle Size Report
Size Limits
|
Collaborator
Author
|
PM 验收(session_01GTRjn8xBqp75dk7kFupVRt):通过,转 ready 并挂 auto-merge。#3968 落地 —— type-check 覆盖门两个盲区(src-only 计数、glob-only 排除探测)收口,门读数 23/38 → 24/39。 核验记录(head
Generated by Claude Code |
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 #3968
结论先说
门的两个盲区都不是"少认一种写法",而是用文本猜程序内容。这个 PR 把判据换成"解析后的 tsconfig 程序到底读了哪些文件",两个盲区就一起消失了;
examples/schema-catalog的 4 个测试文件同时接上 tsc 编译。基 sha
0cbdca888。修前门是绿的(23/38 packages compile their tests,本包不在分母里);修后是24/39。一、门修(
scripts/check-type-check-coverage.mjs)盲区 1 —— 只递归
src/(原:180):countTestFiles(resolve(root, dir, "src"))改为从包根枚举(listTestFiles,跳过node_modules/dist/coverage/ 点目录)。本包测试住在test/,原先数到 0,于是:299的if (!pkg.hasScript || pkg.testFiles === 0) continue;把整个 5c 跳过了 —— 最该说话的检查根本没跑。盲区 2 —— 只认 glob 形式的排除(原
:182):buildExcludesTests = /\*\.test\./.test(tsconfig)改为解析每个 tsconfig 的files/include/exclude(并沿extends继承,按声明它的那个 config 的目录解析),逐个测试文件问"这个程序读不读它"。第二处特意不是"再加一条识别目录形式排除的规则"。因为按目录排除只是这一族里的一种写法,还有一种任何 glob 探测都抓不到的:
include: ["src/**/*"]且根本没有 exclude,测试在test/—— 程序同样一个字节都没读。改成按解析后的程序判定,目录形式排除是 TS 文档语义的自然结果(无扩展名、无通配符的 pattern 就是目录,递归匹配),上面那种也一并抓到。pin 测试里两种形态各有一条。顺带收紧 5b(如实披露,这是第三处改动):原判据是"testConfig 里出现过
*.test.这样的 glob",现在要求这个 project 真的读到 build 程序漏掉的那些文件。这不是顺手加严 —— 我自己写本包的tsconfig.test.json时第一版就踩了:exclude是沿 extends 继承的,父配置排除了整个test目录,于是这个 project 编译了 0 个文件。tsc恰好会喊 TS18003("No inputs were found"),但只覆盖一部分测试的 project 是静默的 —— 那正是原判据放过去的形状。另加一条 5·0:tsconfig 解析不了时不再猜覆盖率,而是单独报错(一个解析失败的 tsconfig 会退化成包含整个仓库,本身就是缺陷;
tsconfig.scripts.json的头注释记过一次块注释里的**/把配置弄坏的事故)。注释剥离是字符串感知的:本仓每个 include/exclude pattern 里都有/*,粗暴剥离会把它要保护的 glob 吃掉。脚本结构按仓内既有门的形态改(
check-skills-paths.mjs/check-changeset-presence.mjs):纯函数export,main()收尾,invokedDirectly守卫 —— 否则 pin 测试一 import 就会扫全仓并process.exit。DEBT / NOT_COMPILED / CHECKED_BY_OWN_BUILD / TEST_DEBT 四张表和其余各节的判据、文案一字未动,auditPackages(packages, tables)允许 fixture 传空表。二、补覆盖(
examples/schema-catalog)形态取仓内既有形态(先读了
packages/types、packages/sdui-parser、packages/layout、packages/plugin-report四个包):新增tsconfig.test.json+type-check串起来。与既有 23 个包的差异只在必要处,每处都写了原因:
include指向test/而不是src/;exclude必须显式重写(见上);rootDir放宽到包根(测试在src旁边而不是里面);补jsx: react-jsx(测试是.tsx,build 配置没有 jsx 因为src/只有 JSON 和.ts);noEmit/declaration/composite归零。没有折进tsconfig.json—— 那是 build 配置(tsc到dist、rootDir: ./src),测试会被 emit 进发布产物。首次编译暴露的问题(1 条,如实披露):
fields-form-hosted.test.tsx里import '@object-ui/fields',而package.json从未声明它 —— 幻影依赖,只靠 vitest 的 alias 解析(packages/sdui-parser/tsconfig.test.json的注释记着同一类发现)。已补为 devDependency,pnpm-lock 相应更新。补上之后 4 个文件零错误,所以不需要 TEST_DEBT 条目。⛔ 未动这 4 个测试文件的任何内容,也未动
src/schemas/**与div.tsx(#3965 的面)。三、反向钉
scripts/__tests__/check-type-check-coverage.test.ts(21 条,全部对着 tmpdir 里的一次性包树,仓内不留刻意失效的 fixture)。除了正常判据,两条被替换掉的旧谓词按原样重现在测试里当断言用:本 bug 的原形态既被断言"新门必须报 1 条 5c",也被断言"旧的 src-only 计数 = 0、旧的 glob 探测 = false" —— 两个盲区变成可执行语句。实际反向验证(先定方向后跑,都是"红"方向):
listTestFiles(packageDir)改回listTestFiles(resolve(packageDir, "src"))→ 21 条里 12 条红(含"全仓只有本包测试在 src 外"那条)。fields/plugin-charts/plugin-editor/console的include: ["src"]不再展开)—— 两个方向都证明这行是承重的。tsconfig.test.json与type-check串接临时撤掉 → 门 exit 1,正是 5c 那条,点名 4 个文件(这就是"修后对现状必须红"的证据)。test/smoke.test.tsx临时塞一个类型错误 →turbo run type-check红(error TS2322),已还原、工作树干净。顺手核了 turbo 的type-check任务 inputs 是$TURBO_DEFAULT$,所以test/**在缓存键里,改测试文件不会命中旧缓存。最后一组断言是对真仓库的(不是 fixture):本包测试存在、全在
src/外、build 程序不读它们、test project 读全了。撤销任一半都会红。四、孤例复核
重验了一遍(
git ls-files独立于门自己的 walker):*.test.ts(x)共 1129 个 —— packages 1070、apps 28、scripts 27(我这条之后 28)、examples 4;按包切分,测试在src/外的只有examples/schema-catalog(outside_src=4 / in_src=0)。scripts/那 27 个由tsconfig.scripts.json覆盖(pnpm type-check:scripts已跑绿)。dev 报告的结论成立,只是文件数是 4 而不是 5(分诊评论已记录这个漂移)。验证
pnpm exec vitest run examples/schema-catalog --maxWorkers=2→Test Files 4 passed (4) / Tests 1090 passedpnpm exec vitest run scripts/__tests__/check-type-check-coverage.test.ts→21 passedpnpm exec turbo run type-check --concurrency=2→78 successful, 78 total(本包实跑tsc --noEmit && tsc -p tsconfig.test.json)pnpm type-check:scripts→ exit 0node scripts/check-type-check-coverage.mjs→ 绿,24/39node scripts/check-control-bytes.mjs→ OK(另按grep -naP自查过改动文件,无匹配)changeset
不需要 —— 以 presence 门的实测判定为据:
node scripts/check-changeset-presence.mjs输出5 file(s) changed, 0 of them under the src/ of a package the release covers→No source of a released package changed in this range, so no changeset is owed.(改动面是 CI 脚本 + 一个 private example 包的清单/配置。)Generated by Claude Code