Skip to content

chore(rest): @objectstack/rest 从 #4311 的 DEBT 台账毕业 —— 接进 turbo typecheck (#6905) - #6937

Merged
os-project-manager merged 1 commit into
mainfrom
claude/issue-6905-rest-typecheck-graduation
Aug 9, 2026
Merged

chore(rest): @objectstack/rest 从 #4311 的 DEBT 台账毕业 —— 接进 turbo typecheck (#6905)#6937
os-project-manager merged 1 commit into
mainfrom
claude/issue-6905-rest-typecheck-graduation

Conversation

@os-project-manager

Copy link
Copy Markdown
Collaborator

Fixes #6905

前置条件:自查通过

PR #6895(#6307)已合入 main:293476148 fix(rest): refuse a repeated ?version= on GET/DELETE /packages/:id (#6307) (#6895)

自己复测的读数(全闭包 turbo run build 72/72 之后跑 pnpm check:type-check-debt,不采信卡里的数字):

ℹ @objectstack/rest: DEBT records 2, and tsc now reports 0 -- graduation candidate.
  Onboard it (add "typecheck": "tsc --noEmit", or drop the test exclusion, and delete
  the ledger entry in the same PR). `--lower` deliberately leaves this one alone: 0 is
  not a lower ceiling, it is a graduation…

实测 0,与卡一致。

两条路为什么选"加脚本"

门禁的提示把两条路并列,但它们属于两本不同的账,scripts/check-type-check-coverage.mjs 的头注写得很清楚:

  • DEBT(src 没被检查)的毕业方式是 —— "add "typecheck": "tsc --noEmit" to its package.json, and delete its entry here in the same PR";
  • TEST_DEBT(src 检查了、测试被藏起来)的毕业方式才是 —— "drop the exclusion from tsconfig.json and delete the entry here in the same PR"

本卡是 DEBT 卡,所以走加脚本这条。三条佐证:

  1. 仓库惯例:packages/* 里 16 个 typecheck 脚本,12 个逐字就是 tsc --noEmit;放在 test 之后也是多数写法(lint / verify / formula / mcp / objectql)。
  2. 同族先例:lintmcpobjectqlruntimeformulaverify 六个包同时持有 TEST_DEBT 条目、且用的就是朴素的 tsc --noEmit —— 直接证明这条路不会扰动另一本账。
  3. 去掉 test exclusion 会撞别的门禁:ci.yml 有一条"测试文件不得进入发布产物"的闸门,头注也点名 build config 保留该 exclusion 是有理由的;真要修 TEST_DEBT,支持的做法是 @ts-expect-error 退役 pin 在 packages/spec 里是幽灵检查:tsconfig 把 **/*.test.ts 排除出唯一的 tsc --noEmit #5286 的 sibling tsconfig.test.json,那是另一张卡的事。

机制上也确认了不会污染:新脚本只点名 tsconfig.json,而它仍然 exclude**/*.test.ts,所以 testsInvoked 依旧为空,TESTS_COVERED 依旧要求 TEST_DEBT['@objectstack/rest'] 存在 —— 该条目原封不动。

改了什么

  • packages/rest/package.json:加 "typecheck": "tsc --noEmit";
  • scripts/check-type-check-coverage.mjs:删掉 DEBT 里的 @objectstack/rest 条目。

两者必须在同一个 PR:只删条目会挂 COVERED,只加脚本会挂 RECONCILED。

实测数字(全部自测,非引用)

before after
门禁总账 62/77 workspace packages type-checked,15 in DEBT(457 frozen) 63/77,14 in DEBT(455 frozen)
声明了 typecheck 脚本的 turbo 任务 62 63
turbo run typecheck 实际执行的任务总数(含 ^build 依赖) 125 126
rest 的 typecheck 命令 < NONEXISTENT > tsc --noEmit
TEST_DEBT 19 包 / 1615 frozen 19 包 / 1615 frozen(未动)

卡里预估 120→121;我实测的基线是 125→126(turbo run typecheck 执行的任务数),另一种数法"声明了脚本的包数"是 62→63。两个数都列在这里,以免下一个人对不上。

pnpm --filter @objectstack/rest typecheck 干净退出 0。

双向实证:门禁真的开始看着这个包了

预测先写、再跑(记录在案)。注入的不是随手造的类型错,而是把 PR #6895 删掉的那条肢体原样装回去 —— packages/rest/src/package-routes.ts 的 GET / DELETE 两处,还原成 const version = req.query?.version || 'latest'const version = req.query?.versionreq.query?.versionstring | string[] | undefined,而 packageService.get/deleteversion?: string。这正是被删掉的台账条目所记的那笔债。

预测 A —— 复现台账记的组成(errors: 2, note: 'code-tier 2 (TS2345).'),数量和错误码都对得上。实测:

src/package-routes.ts(271,55): error TS2345: Argument of type 'string | string[]' is not assignable to parameter of type 'string | undefined'.
src/package-routes.ts(346,61): error TS2345: Argument of type 'string | string[]' is not assignable to parameter of type 'string | undefined'.
      2 error TS2345

命中。(另有 2 条 TS6133 —— 我的还原手法把 readSingleQueryValue / repeatedQueryParamMessage 两个辅助函数留在原地成了未引用;那是注入手法的副产物,不属于原缺陷,如实记在这里。code-tier 那一档是精确的 2×TS2345。)

预测 B —— turbo run typecheck 变红。实测红,退出码 2:

@objectstack/rest:typecheck: src/package-routes.ts(346,61): error TS2345: ...
 Tasks:    17 successful, 18 total
Failed:    @objectstack/rest#typecheck
 ERROR  run failed: command  exited (2)

这条红是有效力的:lint.yml 的 "Type check workspace packages" 步跑的正是 turbo run typecheck --filter='./packages/*' …,packages/rest 在其中。

预测 C(与卡里的括号相反,先写下来的) —— pnpm check:type-check-coverage 不会变红,实测确实保持绿(退出 0)。它是门禁的结构那一半(头注自称 "structural, sub-second"),COVERED / REAL / RECONCILED / TESTS_COVERED / PINS_CHECKED / RUNNABLE 读的全是 package.json、tsconfig 与 workflow 文本,从不启动编译器,所以任何类型错都推不动它。跑编译器的是 check:type-check-debt(--re-measure),而它只编译有台账条目的包 —— 本 PR 删掉 rest 的 DEBT 条目后,它也不再编译 rest 的 src。

这恰好是"加脚本"不可省的理由,也是本卡最该说清的一句话: 毕业前,看着 rest/src 的是台账条目(记 2,实测 4 就会超顶变红);毕业后,看着它的唯一东西就是 turbo run typecheck。所以只删条目、不加脚本,才真的会把这个包从"记录在案的欠债"挪成"没人检查"——而加了脚本之后,上面那条退出码 2 的红就是接管完成的证据。

预测 D —— 撤掉注入后恢复绿。实测 turbo run typecheck --force 18/18,退出 0,工作区 git status 干净;注入自始至终只在工作区,从未提交。

⚠️ 全程没有碰 packages/rest/src/rest-server.ts(#6601 的同事正在那里)。注入落在 package-routes.ts

合并后复跑(main 当时又前进了 6 个提交)

merge → 重建全闭包(72/72)→ 复测,一趟连续做完:

check-type-check-coverage: OK — 63/77 workspace packages type-checked (plus the root), 14 in the DEBT ledger (455 frozen raw errors), 1 exempt.
check-type-check-coverage --re-measure: OK — 33 ledger entr(ies) re-measured in 274.9s, 1764 raw tsc error(s) total, none above its recorded number.

台账条目 34 → 33,rest 的 DEBT graduation-candidate 提示行消失;rest 的 TEST_DEBT 行仍在、数字未动。

changeset:不加,走 skip-changeset

纯构建/工具改动:没有任何运行时行为变化,scripts/ 不发布,package.json 里新增的 typecheck 脚本对使用者没有语义。

先例是 #4311 同族里最贴近的一次 —— PR #5045@objectstack/runtime 做同样的毕业,它的 changeset 是为 @objectstack/spec 的真实类型契约变更而写的,并在正文里明说毕业这半件事不发布:

@objectstack/runtime itself is not released by this change — it gains a typecheck script and loses its check-type-check-coverage DEBT entry

本 PR 只有那"半件事",没有随附的 spec/源码改动(rest 已零错,无债可修),所以按同一句话的口径,没有可发布的东西。另一条先例 #6376 / PR #6510(纯改这个门禁脚本)同样没有 changeset。

#5471 / #4898,空 frontmatter 的 changeset 是禁止的,所以这里用 skip-changeset 标签而不是空文件。


Generated by Claude Code

PR #6895(#6307)修掉重复 `?version=` 把 `string[]` 喂进 `version?: string`
的缺陷后,`@objectstack/rest` 已零错编译,而 DEBT 台账仍记 2。门禁自己把这
个状态标成 graduation candidate 并明说 `--lower` 不会处理它 —— 0 不是更低的
天花板,而是毕业。

- `packages/rest/package.json` 增加 `"typecheck": "tsc --noEmit"`;
- 删掉 `scripts/check-type-check-coverage.mjs` 里 DEBT 的 `@objectstack/rest` 条目。

两者必须同一个 PR:只删条目不加脚本会挂 COVERED,只加脚本不删条目会挂
RECONCILED。TEST_DEBT 是另一本账,本 PR 不动。

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017uFVNMmTxLpmfQYiuKM1Yx
@vercel

vercel Bot commented Aug 9, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

1 Skipped Deployment
Project Deployment Actions Updated (UTC)
objectstack Ignored Ignored Aug 9, 2026 5:03am

Request Review

@github-actions

github-actions Bot commented Aug 9, 2026

Copy link
Copy Markdown
Contributor

📓 Docs Drift Check

This PR changes 1 package(s): @objectstack/rest.

12 hand-written doc(s) reference the affected code and may need an implementation-accuracy re-verification:

  • content/docs/ai/connect-mcp.mdx (via @objectstack/rest)
  • content/docs/api/error-handling-server.mdx (via @objectstack/rest)
  • content/docs/api/index.mdx (via @objectstack/rest)
  • content/docs/permissions/authentication.mdx (via @objectstack/rest)
  • content/docs/permissions/system-context.mdx (via packages/rest)
  • content/docs/plugins/index.mdx (via @objectstack/rest)
  • content/docs/plugins/packages.mdx (via @objectstack/rest)
  • content/docs/protocol/kernel/http-protocol.mdx (via @objectstack/rest)
  • content/docs/protocol/kernel/i18n-standard.mdx (via packages/rest)
  • content/docs/releases/implementation-status.mdx (via @objectstack/rest)
  • content/docs/releases/v12.mdx (via @objectstack/rest)
  • content/docs/releases/v17.mdx (via @objectstack/rest)

Advisory only. To re-verify, run the docs-accuracy-audit workflow scoped to these files:
node scripts/docs-audit/affected-docs.mjs origin/main → pass the list as args.docs.

@os-project-manager os-project-manager added skip-changeset PR has no user-facing published change; bypasses the changeset gate and removed size/xs labels Aug 9, 2026 — with Claude
@github-actions github-actions Bot added the dependencies Pull requests that update a dependency file label Aug 9, 2026
@os-project-manager
os-project-manager marked this pull request as ready for review August 9, 2026 05:28
@os-project-manager
os-project-manager added this pull request to the merge queue Aug 9, 2026
Merged via the queue into main with commit df0605b Aug 9, 2026
33 checks passed
@os-project-manager
os-project-manager deleted the claude/issue-6905-rest-typecheck-graduation branch August 9, 2026 05:44
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

dependencies Pull requests that update a dependency file skip-changeset PR has no user-facing published change; bypasses the changeset gate

Projects

None yet

Development

Successfully merging this pull request may close these issues.

@objectstack/rest 已可零错编译,应从 #4311 的 DEBT 台账毕业 —— 加 typecheck 脚本 + 删台账条目(阻塞于 PR #6895)

2 participants