Skip to content

fix: preserve runtime createRequire in ESM builds#1334

Merged
styfle merged 1 commit into
vercel:mainfrom
Jaksenc:fix/create-require-runtime
Jun 29, 2026
Merged

fix: preserve runtime createRequire in ESM builds#1334
styfle merged 1 commit into
vercel:mainfrom
Jaksenc:fix/create-require-runtime

Conversation

@Jaksenc

@Jaksenc Jaksenc commented Jun 14, 2026

Copy link
Copy Markdown
Contributor

Problem

Since 0.38.2, an ESM build can replace a runtime
createRequire(...) binding with undefined, causing the later runtime
require(...) call to throw.

Change

  • Disable Webpack's createRequire parser handling in ncc so Node evaluates
    the call at runtime.
  • Add a normal integration fixture with an .mjs entry that imports the
    TypeScript runtime payload and loads a runtime-selected JSON module.

This keeps the fix at ncc's Webpack configuration boundary and covers the
reported runtime behavior without changing dependency tracing.

Validation

  • node scripts/build.js --no-cache
  • node --expose-gc --max_old_space_size=4096 node_modules/jest/bin/jest.js test/integration.test.js --runInBand --testNamePattern create-require-runtime
    • 1 passed
  • pnpm test -- test/unit.test.js
    • 28 passed
  • node --expose-gc --max_old_space_size=4096 node_modules/jest/bin/jest.js --runInBand test/integration.test.js --testNamePattern='^(?!should execute "ncc run (?:axios\.js|canvas\.js|isomorphic-unfetch\.js|request-ts\.ts|request\.js|sharp\.js|socket\.io\.js)"$).*'
    • 62 passed; 7 local environment-dependent cases skipped
  • Negative control with Webpack's createRequire parsing restored reproduced
    TypeError: input_require is not a function.

Risk

The parser option applies to all JavaScript handled by ncc. It intentionally
preserves createRequire for Node to evaluate at runtime, so modules selected
only at runtime must still be deployed with the bundle.

The cross-platform Node 22/24/26 matrix remains for CI. A local CLI watch test
failed with Watchpack EMFILE errors and reproduced identically on
origin/main, so it is not attributed to this change.

Out of scope

  • Changing how ncc traces or deploys runtime-selected modules.
  • Dependency or lockfile updates.

Issue linkage

Fixes #1312

Comment thread test/integration.test.js Outdated
try {
const { code, assets } = await ncc(input, {
cache: false,
esm: true,

@styfle styfle Jun 25, 2026

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Did you add the programatic api here instead of cli because you want to set esm: true?

If thats the only reason, its probably best to rename the .ts file to .mts or set type:module in package.json instead.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ohh yeah, that's exactly why I used the programmatic API there. I wanted to force esm: true, but you're right that it made the test more custom than it needed to be.

I moved it back into the normal integration path with a .mjs entry, and kept the actual createRequire bit in a tiny TS file that it imports.

I tried .mts too, but it still goes through the CJS path here, and typed .mts input doesn't seem to hit the TS loader. So .mjs felt like the smallest way to exercise the ESM path without adding .mts support in this PR.

Does that work better?

@Jaksenc
Jaksenc force-pushed the fix/create-require-runtime branch from f24f444 to e26fc50 Compare June 27, 2026 19:23

@styfle styfle left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Great work, thanks!

@styfle
styfle merged commit 8f0aefd into vercel:main Jun 29, 2026
13 checks passed
@github-actions

Copy link
Copy Markdown

🎉 This PR is included in version 0.44.1 🎉

The release is available on:

Your semantic-release bot 📦🚀

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Regression: dynamic runtime require works in 0.38.1 but breaks in 0.38.2

2 participants