Skip to content
PirefactorCLI & tooling19 files · +1133 −224

Reorganize a pnpm project into a proper monorepo

Session from pi-web on Hugging Face by woxQAQ · MIT · condensed by Coders Talk

32msession
4interventions
GOAL

Convert a single Node/TypeScript project that only looked like a monorepo into an actual pnpm workspace monorepo with separate bridge, bin and web packages, keeping the build, type-check and tests working.

  1. Prompt · +0
    Reorganize the @packages/ project to actually be a pnpm monorepo instead of just looking like one.
  2. Agent did · +0m
    Explored the existing package structure, then added pnpm-workspace.yaml, per-package package.json/tsconfig files for bridge/bin/web, updated the root package.json and vitest config, ran install, type-check, tests and build to confirm it worked.
  3. Intervention · +8m
    Developer said the scripts folder shouldn't be its own workspace package.
    Why: scripts 不需要作为一个 package — it's just build helpers, not a publishable unit.
  4. Intervention · +11m
    Developer questioned the manually written exports map in bridge/package.json, then said stop using relative imports between packages altogether — use the package name.
    Why: 手动写 exports 没必要,包之间也不要用相对路径导入,应该用包名。
  5. Fail · +12m
    Agent tried to add esbuild to bundle the bin package for the package-name-import switch; the install timed out and was aborted.
  6. Agent did · +13m
    Dropped esbuild in favor of Vite's built-in bundler, added vite.config for the bin package, wired tsconfig paths for @pi-web/bridge imports, rebuilt and retested everything, then committed.
  7. Intervention · +19m
    Developer said drop the shared-types.ts re-export file in web and import @pi-web/bridge/types directly; several sed/perl passes were needed after an '@' got stripped, plus exports/paths fixes before check passed.
    Why: 不需要 @packages/web/src/shared-types.ts ,直接引用 @pi-web/bridge/types。
  8. Fail · +27m
    TypeScript error: exit-input.ts not under bin's rootDir, surfaced after the earlier import changes; fixed by dropping rootDir from bin's tsconfig.
  9. Intervention · +31m
    Developer noticed packages/web/tsconfig.json still had relative paths and asked to fix it; agent made it inherit paths from the root tsconfig instead.
    Why: @packages/web/tsconfig.json 还是保留了相对路径,请你改掉。
  10. Break · 2h 05m away, not counted
  11. Outcome · +32m
    Confirmed final publish shape: only the root @woxqaq/pi-web package would be published (bridge, bin, web are all private), bundling dist/bin, dist/bridge and web-dist via the files field.
VERDICT

Next time I'd specify upfront that packages should use package-name imports (not relative paths) and that internal packages must stay private, since that's exactly what I ended up correcting twice. The intervention that mattered most was pushing back on esbuild — pointing out Vite already bundles with rolldown saved us an unnecessary dependency and got the packages resolving correctly through Vite's own config.

I tried this · 0

Discussion · 0

How Builds work