My App

Monorepo 架构说明

Monorepo 架构说明

Monorepo 架构说明

本文档说明本仓库的目录结构、Workspaces 配置及日常使用方式。


一、架构概览

本仓库采用 npm Workspaces 的 Monorepo 结构:

  • 根目录:只负责声明 workspaces、统一安装依赖,不发布到 npm(private: true)。
  • packages/:可复用的库包,可被应用或其他包依赖,可单独发布。
  • dev/应用或开发用项目,通常不发布,依赖 packages 中的包。

依赖安装只在根目录执行一次 npm install,各子包通过 workspace 链接互相引用。


二、目录结构

code-gen-monorepo/
├── package.json              # 根 package,声明 workspaces,private: true
├── package-lock.json          # 根锁文件,统一管理所有 workspace 依赖
├── .gitignore
├── docs/                      # 文档
│   └── MONOREPO.md           # 本说明文档

├── packages/                  # 库包(可复用、可发布)
│   └── cg/                    # 示例库包
│       ├── package.json       # name: "cg"
│       ├── src/
│       │   └── index.ts
│       ├── dist/              # 构建产物(需先 build)
│       ├── tests/
│       ├── tsconfig.json
│       └── tsdown.config.ts

└── dev/                       # 应用 / 开发项目
    └── nest-admin-app/        # NestJS 应用
        ├── package.json       # name: "nest-admin-app", 依赖 "cg": "*"
        ├── src/
        │   ├── main.ts
        │   ├── app.module.ts
        │   └── ...
        ├── test/
        ├── tsconfig.json
        └── nest-cli.json

说明

路径用途
根目录 package.json定义 workspaces: ["packages/*", "dev/*"],根包不发布
packages/*各子包为独立 npm 包,可被其他 workspace 或外部项目依赖
dev/*各子目录为应用或工具项目,通常依赖 packages/* 中的包
根目录 node_modules安装后大部分依赖会提升到此,子包多为链接

三、Workspaces 说明

3.1 根 package.json 中的配置

{
  "private": true,
  "workspaces": ["packages/*", "dev/*"]
}
  • private: true
    根包禁止被 npm publish 发布,避免误操作。

  • workspaces

    • packages/*:将 packages/ 下每个子目录视为一个 workspace(如 packages/cg)。
    • dev/*:将 dev/ 下每个子目录视为一个 workspace(如 dev/nest-admin-app)。

3.2 依赖安装与提升(Hoisting)

  • 安装位置:在根目录执行一次 npm install 即可。
  • 行为
    • npm 会为所有 workspace 安装其 dependencies / devDependencies
    • 能兼容的依赖会提升到根目录的 node_modules
    • 子包目录下通常没有或只有少量 node_modules(链接或版本冲突时单独安装)。
  • 结论:不需要在 packages/cgdev/nest-admin-app 里再执行 npm install

3.3 子包引用方式(依赖 workspace 包)

应用要使用本仓库里的库包时,在应用自己的 package.json 里写依赖名和版本,不要用 npm install 包名 从 npm 安装同名包。

例如 dev/nest-admin-app 依赖本仓库的 packages/cg

{
  "dependencies": {
    "cg": "*"
  }
}
  • "cg": "*" 表示「使用当前仓库里名为 cg 的 workspace 包」。
  • 安装后,根目录或应用下的 node_modules/cg链接packages/cg,而不是从 npm 拉取。
  • 若写 npm install cg 且未在 package.json 里声明 "cg": "*",则会从 npm 安装外部包,而不是本仓库的 packages/cg

注意workspace:* 为 pnpm/Yarn Berry 协议,npm 不支持;使用 npm 时用 "*" 即可,npm 会解析为本地 workspace。

3.4 小结

概念说明
Workspaces 定义package.jsonworkspaces: ["packages/*", "dev/*"]
安装命令仅在根目录执行 npm install
依赖位置主要安装在根目录 node_modules,子包多为链接
子包互依赖在子包 package.json 中写 "包名": "*",指向本仓库同名 workspace

四、常用操作

4.1 安装依赖

# 在仓库根目录执行
npm install

4.2 构建库包(如 cg)

# 进入库包目录构建
cd packages/cg && npm run build

# 或从根目录(若根 package.json 有对应 script)
npm run build --workspace=cg

应用依赖 cg 时,需先保证 packages/cg 已构建(存在 dist/),否则运行/构建应用可能报错。

4.3 运行应用(如 nest-admin-app)

# 进入应用目录
cd dev/nest-admin-app
npm run start:dev

# 或从根目录(若根 package.json 有对应 script)
npm run start:dev --workspace=nest-admin-app

4.4 添加新的 workspace 包

  1. packages/dev/ 下新建目录,并包含合法的 package.json(含 name 等)。
  2. 在根目录执行 npm install,npm 会自动识别新 workspace。

4.5 应用依赖库包

  1. 在应用的 package.jsondependencies 中增加:"包名": "*"(如 "cg": "*")。
  2. 在根目录执行 npm install
  3. 确保被依赖的库包已构建(若有构建步骤)。

五、注意事项

  1. 根目录不要发布:根 package.json 保持 "private": true
  2. 只用根目录安装:不要在子包目录执行 npm install,以免破坏 workspace 结构。
  3. npm 与 workspace 协议:使用 npm 时用 "cg": "*",不要用 workspace:*(pnpm/Yarn 才支持)。
  4. 类型与构建:应用引用 workspace 包时,若出现「找不到模块/类型」:
    • 确保该库包已执行过 build(如 packages/cgdist/ 存在)。
    • 库包 package.jsonexports 中建议包含 types 条件,便于 TypeScript 解析。
    • 若仍无法解析,可在应用内增加本地类型声明(如 cg.d.ts)。

六、相关文件索引

文件作用
根目录 package.jsonworkspaces 定义、根脚本、private
packages/cg/package.json库包 cg 的入口、exports、构建脚本
dev/nest-admin-app/package.json应用依赖(含 "cg": "*")、应用脚本
docs/MONOREPO.md本说明文档

On this page