From 036081e9e7dee8905ead544144f39d4aa624cd2f Mon Sep 17 00:00:00 2001 From: Brandon Schoch <15143995+theoryeffects@users.noreply.github.com> Date: Fri, 10 Jul 2026 16:22:29 -0400 Subject: [PATCH] fix: resolve named CommonJS imports in dev-server bundling The node_modules bundler skips JavaScriptTransformer for non-linker files when advancedOptimizations is false (i.e. during `ng serve`). That transform provides the CommonJS->ESM interop that synthesizes named exports, so skipping it makes `import def, { named } from ''` fail with "No matching export" in dev, while `ng build` (advancedOptimizations=true, transforms every file) works. Keep the dev fast-path for genuine ESM vendor files but not for CommonJS ones, so CJS interop no longer depends on the optimization level. Co-Authored-By: Claude Opus 4.8 (1M context) --- src/tools/esbuild/node-modules-bundler.ts | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/src/tools/esbuild/node-modules-bundler.ts b/src/tools/esbuild/node-modules-bundler.ts index e680df9..1db093e 100644 --- a/src/tools/esbuild/node-modules-bundler.ts +++ b/src/tools/esbuild/node-modules-bundler.ts @@ -45,7 +45,16 @@ function createAngularLinkerPlugin( const needsLinking = requiresLinking(args.path, contents); - if (!needsLinking && !advancedOptimizations) { + // Genuine ESM vendor files may skip the transform in dev (advancedOptimizations=false) + // to keep the dev server fast. CommonJS files may not: esbuild resolves their named + // exports via the CJS->ESM interop that `jsTransformer.transformData` performs, so + // skipping it makes `import { named } from ''` fail with "No matching export" + // during `ng serve` (while `ng build`, where advancedOptimizations=true, transforms every + // file and works). Only skip the transform for non-CommonJS files, so CJS interop no + // longer depends on the optimization level. + const maybeCommonjs = /\bmodule\.exports\b|\bexports\.[A-Za-z_$]/.test(contents); + + if (!needsLinking && !advancedOptimizations && !maybeCommonjs) { return null; }