Skip to content

feat: migrate build from Rollup + SWC to esbuild#8473

Draft
kpal81xd wants to merge 4 commits intomainfrom
build
Draft

feat: migrate build from Rollup + SWC to esbuild#8473
kpal81xd wants to merge 4 commits intomainfrom
build

Conversation

@kpal81xd
Copy link
Contributor

Summary

  • Migrates the PlayCanvas engine JS build pipeline from Rollup + SWC to esbuild
  • Replaces sequential Rollup builds with parallel esbuild builds (Promise.all)
  • Replaces @rollup/plugin-strip + @rollup/plugin-swc with unplugin-strip for function call stripping
  • Adds custom esbuild plugins for shader chunks, JSCC preprocessing, dynamic imports, and import validation
  • TypeScript definitions still built via Rollup (rollup-plugin-dts) — unchanged
  • Removes unused Rollup plugins (rollup-dynamic, rollup-import-validation, rollup-shader-chunks, rollup-spaces-to-tabs, rollup-swc-options)

Build Comparison Report

Benchmarked on the same machine, 3 runs each, median reported.

Build Times

Builder Median Runs
esbuild 15.4s 15458ms, 15380ms, 15709ms
Rollup + SWC 40.6s 40657ms, 43917ms, 37274ms
Speedup 2.63x

Bundled File Sizes

File                   |    esbuild |     Rollup |    Δ% |     esb gz |    roll gz | Δ gz%
-----------------------+------------+------------+-------+------------+------------+------
playcanvas.js          |       3.5M |       3.4M |  1.6% |     716.7K |     690.1K |  3.8%
playcanvas.mjs         |       3.5M |       3.3M |  5.2% |     716.6K |     683.5K |  4.8%
playcanvas.dbg.js      |      17.1M |      20.7M |-17.1% |       3.7M |       4.7M |-21.3%
playcanvas.dbg.mjs     |      17.1M |      20.0M |-14.3% |       3.7M |       3.9M | -6.4%
playcanvas.prf.js      |       3.5M |       3.4M |  1.6% |     718.0K |     691.4K |  3.8%
playcanvas.prf.mjs     |       3.5M |       3.3M |  5.2% |     717.9K |     684.8K |  4.8%
playcanvas.min.js      |       2.1M |       2.0M |  1.5% |     552.6K |     533.3K |  3.6%
playcanvas.min.mjs     |       2.1M |       2.0M |  1.1% |     552.5K |     536.0K |  3.0%
playcanvas.d.ts        |       2.0M |       2.0M |    0% |     402.6K |     402.6K |    0%

Unbundled Directories

Directory              |  esb # | roll # |   esb size |  roll size |    Δ%
-----------------------+--------+--------+------------+------------+------
playcanvas/            |   2240 |   2254 |       7.5M |       6.5M | 14.0%
playcanvas.dbg/        |   1133 |   1130 |       6.4M |       6.3M |  1.7%
playcanvas.prf/        |   1110 |   1124 |       4.5M |       3.6M | 25.4%

Correctness

  • TypeScript definitions: IDENTICAL
  • Export surface area: IDENTICAL (1251 exports)
  • Unbundled file lists: Minor differences in code-splitting (14–32 files differ per directory)

Known Differences

  • UMD wrapper: esbuild uses self fallback; Rollup uses globalThis
  • Export block: esbuild emits individual export statements; Rollup emits a single export {} block
  • Debug builds are ~14–17% smaller with esbuild (no SWC runtime helpers)
  • Release/min builds are ~1–5% larger with esbuild (different tree-shaking heuristics)

Test plan

  • Run node build.mjs — all 12 JS targets + types build successfully
  • Run node build.mjs target:esm:release:bundled — single target works
  • Verify build/playcanvas.d.ts is identical to main
  • Verify export surface matches main (playcanvas.mjs)
  • Spot-check a built example in the browser

🤖 Generated with Claude Code

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