chore: upgrade TypeScript to 6.0.3 across the monorepo (unify 5.7/5.9 drift) - #1193
Conversation
tsdown loads a .ts config via an optional peer (unrun/tsx); absent on a clean --frozen-lockfile install (CI), the artifact-canvas build failed with 'Failed to import module unrun'. A plain ESM .mjs config is imported natively by Node, removing the loader dependency. Verified building with tsx hidden.
tsdown's auto config-loader falls back to 'unrun' (an optional peer pnpm doesn't install) on Node without native TS support, so the artifact-canvas build failed on CI's clean install regardless of .ts/.mjs extension. Forcing --config-loader native imports the plain-ESM .mjs config directly on every Node version. Verified against the reproduced CI path (--config-loader unrun).
Architect Integration ReviewClean, well-scoped dependency-upgrade PR. Verified against the actual diff, not just the artifacts: Version unification is structurally correct. A single The two genuine TS 6 breaks are minimally fixed. The tsup → tsdown migration in artifact-canvas is sound. Root cause of the CI failure is real (tsdown's No erosion. No behavioral code changes smuggled in, no deleted or loosened tests, no Consults + CI: 2-way consult (claude, codex) both APPROVE with no blocking issues (gemini CLI unavailable); the post-consult delta is build-config-only. CI 6/6 green including the reproduced-CI-path verification of the tsdown fix. One cosmetic nit, no action needed: the review artifact's Files Changed list says Approved for merge pending the pr gate. Architect integration review |
PIR Review: Upgrade TypeScript to 6.0.3 across the monorepo
Fixes #1187
Summary
Unified the monorepo's TypeScript compiler on a single version (6.0.3), resolving the prior 5.7/5.9 drift across the six packages that carry a
typescriptdevDependency. The version is now pinned once in a pnpmcatalog:entry (every manifest references"typescript": "catalog:"), so future bumps — including the anticipated TS 7 move — are a one-line change and drift is structurally impossible. Fixed the two genuine TypeScript 6 breaking changes (the newtypes: []compiler default, andbaseUrl-deprecation-as-hard-error), the latter by migratingpackages/artifact-canvasoff the unmaintained tsup onto tsdown.Files Changed
Source changes (excludes the 715/-269
pnpm-lock.yamlrefresh and porch's ownstatus.yaml):pnpm-workspace.yaml(+2 / -0) — newcatalog: { typescript: ^6.0.3 }apps/web/package.json(+1 / -1) —typescript→catalog:apps/vscode/package.json(+1 / -1) —typescript→catalog:packages/types/package.json(+1 / -1) —typescript→catalog:packages/core/package.json(+1 / -1) —typescript→catalog:packages/codev/package.json(+1 / -1) —typescript→catalog:packages/artifact-canvas/package.json(+13 / -8) —typescript→catalog:; tsup → tsdown;exports/main/module/typesretargeted to tsdown filenamespackages/core/tsconfig.json(+2 / -1) — add"types": ["node"]packages/codev/tsconfig.json(+2 / -1) — add"types": ["node"]apps/web/src/vite-env.d.ts(+1 / -0) — new;/// <reference types="vite/client" />packages/artifact-canvas/tsdown.config.ts(+20 / -0) — new build configpackages/artifact-canvas/tsup.config.ts(+0 / -24) — deletedpackages/artifact-canvas/scripts/smoke.mjs(+2 / -2) — retarget dist filenames to tsdown'spackages/codev/src/commands/porch/__tests__/e2e/fixtures/todo-app/package.json(+3 / -3) — bump the last remaining TS 5 pin (dead e2e fixture) to TS 6codev/resources/arch.md,codev/resources/lessons-learned.md— governance updates (see below)codev/plans/1187-*.md,codev/reviews/1187-*.md,codev/state/pir-1187_thread.md— protocol artifactsCommits
(plus thread/review commits and porch's phase-transition commits)
Test Results
Full suite re-run under the final catalog + tsdown state:
pnpm --recursive build: ✓ pass (every package, incl. apps/web vite, codev dashboard bundle, artifact-canvas tsdown dual-format)pnpm --recursive check-types: ✓ pass (types, artifact-canvas, core, apps/vscode host + webview)pnpm --filter codev-vscode run vscode:prepublish: ✓ pass (topological workspace-dep build + check-types + lint + production esbuild)packages/artifact-canvaspnpm build:smoke: ✓ pass (CJS + ESM entries load,ArtifactCanvasexported, dist assets present)build,tests): ✓ passdev-approvalgate): reviewer approved the running worktree.No
engines.nodechange was needed — TS 6.0.3 declaresengines.node: ">=14.17", below the repo's existing>=20.0.0.Architecture Updates
Routed to the COLD tier (
codev/resources/arch.md) — reference-level toolchain facts, not decision-gating invariants, and the HOTarch-critical.mdis at its cap (adding would require displacing a stronger invariant, which none of these warrant):pnpm-workspace.yamlcatalog:and referenced as"typescript": "catalog:"everywhere (bump the catalog, never a single package), plus the TS 6types: []default and its["node"]/vite-env.d.tsimplications.packages/artifact-canvasbuilds via tsdown (Rolldown, the maintained tsup successor) and why itsexportsmap uses nested per-formatimport/requireconditions.(These live in our project's own evolved docs, not framework files, so no
codev-skeleton/mirror is required.)Lessons Learned Updates
Routed to the COLD tier (
codev/resources/lessons-learned.md→ Debugging and Root Cause Analysis) — a spec-narrow-but-durable recipe, not a new always-on invariant (HOTlessons-critical.mdalready covers the adjacent "captured raw data beats speculation" / "grep the whole repo after a framework change" rules):check-typestally is meaningless until every workspace dependency is built — ~100 phantomTS2307/TS7006errors in downstream packages all vanished once the upstreamdist/*.d.tsexisted. Build the dep graph (or check-types topologically) before trusting a monorepo error count. Corollary: discover a major dependency upgrade's real fallout empirically at plan time (install + run the full suite), not by predicting it from release notes.Things to Look At During PR Review
exportsmap change inpackages/artifact-canvas/package.jsonis the highest-signal diff. tsup emittedindex.js(ESM) + a singleindex.d.ts; tsdown emits per-formatindex.mjs/index.d.mts(ESM) andindex.cjs/index.d.cts(CJS). The map was restructured from a flat{types, import, require}to nestedimport/requireconditions each pointing at their matching declaration file — the correct dual-package layout (avoids CJS/ESM type masquerading). Downstream resolution was verified: apps/web build, vscode webview check-types, and thebuild:smokeall pass against the new names.types: ["node"]on core/codev only — deliberately not added topackages/config/tsconfig.base.json(the shared base), becausepackages/types(no@types/nodedep) and the browser-contexttsconfig.webview.jsonwould then error. Per-package is the correct scope.todo-appfixture bump — this fixture is vestigial (no src, not referenced by any test; e2esetup.tsbuilds its own inlinepackage.json) and is not a pnpm workspace member, so it can't usecatalog:(direct^6.0.3pin) and its bump produced zero lockfile change. Bumped per architect request to leave no TS 5 pin anywhere;@types/nodeandvitestwere aligned to the workspace's versions for internal consistency.0.22.8) — the maintained Rolldown-based tsup successor. If pre-1.0 tooling is a concern, the fallback is tsup +"ignoreDeprecations": "6.0", but that silence stops working in TS 7.How to Test Locally
pir-1187→ View Diffafx dev pir-1187pnpm installrefreshes the lockfile totypescript@6.0.3cleanly (catalog resolves; zero tsup refs remain)pnpm --recursive buildthenpnpm --recursive check-types— both clean (build first so downstream.d.tsexist)pnpm --filter codev-vscode run vscode:prepublish— production extension build succeedsvitest run(notepackages/codev'stestscript is watch-modevitest— usevitest run) + artifact-canvaspnpm build:smoke