Skip to content

perf(unplugin-dts): optimize watch rebuilds - #487

Merged
qmhc merged 3 commits into
mainfrom
improve-ts-watch
Aug 31, 2026
Merged

perf(unplugin-dts): optimize watch rebuilds#487
qmhc merged 3 commits into
mainfrom
improve-ts-watch

Conversation

@qmhc

@qmhc qmhc commented Aug 28, 2026

Copy link
Copy Markdown
Owner

概述

优化 TypeScript 项目在 watch 模式下的 Program 重建和文件监听生命周期,同时补齐跨 bundler 的新增、删除、重命名与输出目录隔离行为。

该 PR 只包含 TypeScript watch 与通用 watcher 基础设施,不包含后续 Vue/Volar 生命周期调整,也不改变公开 API 或选项。

主要变更

  • 为纯 TypeScript processor 增加按版本失效的 SourceFile cache,并把旧 Program 交给 TypeScript 复用未变化 AST。
  • 将同一构建轮次的多个 watchChange 聚合到下一次 buildStart,只重建一次 Program、执行一次完整 diagnostics。
  • 对创建、删除、重命名、tsconfig、JSON 和自定义 resolver 等不安全场景使用 fresh fallback。
  • 修正 Vite、Webpack、Rspack、Rollup 和 Rolldown 的文件/目录监听、输出目录忽略和 stale declaration 清理边界。
  • 增加可区分 hook 归因、transform 并行重叠与未归因墙钟的性能计时。
  • 补充 watch 模式的布局建议与已知 bundler 边界文档。

性能结果

冻结的 7 组配对 A/B benchmark 中:

  • 普通单文件或公共依赖增量构建耗时降低约 19%–27%。
  • 同一轮多文件修改耗时降低约 35%–46%。
  • 120/480 文件 cold build 中位数约慢 1.5%,因此该 PR 不宣称冷构建收益。

480 文件公共依赖场景中,watchChange 的下降部分确实转移到了 buildStart;但 transform 从 38.9ms 降至 0.6ms,writeBundle 从 306.5ms 降至 203.4ms,关键路径归因合计从 511.7ms 降至 359.6ms。SourceFile identity 观测显示 566/567 个 SourceFile 被复用。

正确性与验证

  • fresh oracle 14/14 场景通过,预期一致的产物文件集合和逐文件 SHA-256 均与独立 fresh build 相同。
  • pnpm --filter unplugin-dts test:PR1 独立状态 11 files / 78 tests passed。
  • TypeScript 类型检查、目标 ESLint、git diff --check 通过。
  • pnpm build 通过。
  • playground/ts-vite 和原有 playground/vue-vite 构建通过。
  • 真实 Vite、Webpack、Rspack watcher 回归测试通过。

已知边界

纯 Rollup/Rolldown 在递归源码目录与输出目录重叠时继续 fail-close,避免生成文件形成无限 rebuild;这种布局下,未被引用的新文件可能需要调整目录布局或重启 watcher。

@qmhc
qmhc merged commit 349e1b4 into main Aug 31, 2026
4 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant