兄弟们,2026年了,如果你还在维护一个包含十几个微服务或前后端项目的巨型仓库,并且每次新建模块都要手动复制一份 tsconfig.json,那你大概率已经尝到了"配置漂移"的苦头。更致命的是,由于TypeScript路径解析的坑,很多团队被迫在开发阶段先全量编译一遍内部包,热更新慢得像蜗牛。今天咱们就来聊聊,如何利用最新的 NodeNext 模块解析和 npm workspaces,打造一个既优雅又极速的 TypeScript Monorepo。
核心痛点:TSConfig继承陷阱与开发体验割裂
在Monorepo中,最常见的错误就是要么在每个包里维护独立的TS配置(改一个基础规则要改十几遍),要么在根目录写一个巨大的 include 数组(这会导致增量编译完全失效)。此外,如果内部共享包没有正确配置 exports,你在本地开发时就无法直接引用源码,必须忍受漫长的构建等待。
实战方案:基线继承与无缝源码直连
1. 建立不可变的 tsconfig.base.json
在根目录下只放置编译器选项,绝不包含任何 include 或 exclude。所有的子包通过 extends 继承它,并仅覆盖自己的 rootDir 和 outDir。
1// 根目录 tsconfig.base.json
2{
3 "compilerOptions": {
4 "target": "ES2022",
5 "module": "NodeNext",
6 "moduleResolution": "NodeNext",
7 "strict": true,
8 "declaration": true,
9 "skipLibCheck": true
10 }
11}
2. 利用 exports 实现开发期源码直连
这是提升开发体验的关键!在内部共享包的 package.json 中,直接将 exports 指向 .ts 源码文件。配合 npm workspaces,应用层在开发时可以直接热加载这些源码,无需任何构建步骤。
1// packages/utils/package.json
2{
3 "name": "@myrepo/utils",
4 "type": "module",
5 "exports": {
6 ".": {
7 "types": "./src/index.ts",
8 "default": "./src/index.ts"
9 }
10 }
11}
总结:优秀的Monorepo不是把代码简单地堆在一起,而是通过严格的工程约束来换取长期的可维护性。拥抱 NodeNext 和 Workspace,让你的大型项目既能享受类型安全的红利,又能保持丝滑的开发体验!