Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Bug?]: ERR_MODULE_NOT_FOUND with Yarn 4.6.0 #6646

Closed
1 task done
Methuselah96 opened this issue Jan 6, 2025 · 3 comments
Closed
1 task done

[Bug?]: ERR_MODULE_NOT_FOUND with Yarn 4.6.0 #6646

Methuselah96 opened this issue Jan 6, 2025 · 3 comments
Labels
bug Something isn't working

Comments

@Methuselah96
Copy link

Methuselah96 commented Jan 6, 2025

Self-service

  • I'd be willing to implement a fix

Describe the bug

Module resolution fails for some combination of CJS and ESM as of Yarn 4.6.0. It works when using Yarn 4.5.3 or npm (with both Node 22.12.0 and Node 22.11.0).

To reproduce

  1. Clone https://github.com/Methuselah96/test-jest
  2. Run yarn install
  3. Run yarn test
  4. Observe error:
Error [ERR_MODULE_NOT_FOUND]: Cannot find package 'babel-jest' imported from C:\Users\nbier\Documents\test-jest\jestTransformer.js
Did you mean to import "babel-jest/build/index.js"?
    at packageResolve (node:internal/modules/esm/resolve:857:9)
    at moduleResolve (node:internal/modules/esm/resolve:926:18)
    at defaultResolve (node:internal/modules/esm/resolve:1056:11)
    at ModuleLoader.defaultResolve (node:internal/modules/esm/loader:654:12)
    at #cachedDefaultResolve (node:internal/modules/esm/loader:603:25)
    at ModuleLoader.getModuleJobForRequire (node:internal/modules/esm/loader:353:53)
    at new ModuleJobSync (node:internal/modules/esm/module_job:341:34)
    at ModuleLoader.importSyncForRequire (node:internal/modules/esm/loader:326:11)
    at loadESMFromCJS (node:internal/modules/cjs/loader:1414:24)
    at Module._compile (node:internal/modules/cjs/loader:1547:5)

Environment

System:
    OS: Windows 11 10.0.26100
    CPU: (20) x64 13th Gen Intel(R) Core(TM) i5-13500
  Binaries:
    Node: 22.12.0 - ~\AppData\Local\Temp\xfs-d16ac07e\node.CMD
    Yarn: 4.6.0 - ~\AppData\Local\Temp\xfs-d16ac07e\yarn.CMD
    npm: 10.9.0 - C:\Program Files\nodejs\npm.CMD
    bun: 1.1.0 - ~\.bun\bin\bun.EXE

Additional context

No response

@Methuselah96 Methuselah96 added the bug Something isn't working label Jan 6, 2025
@flex-jonghyen
Copy link

@clemyan Could you let me know there is any progress?

@clemyan
Copy link
Member

clemyan commented Feb 13, 2025

I have dug into this and determined this happens when all of the following is true

  • PnP is enabled
  • require(esm) is enabled (default for Node 22.12.0+)
  • module.registerHooks() is not available (as of this writing, Node <23.5.0)
  • require(esm) is used
  • the required esm has a static import to something that needs PnP to resolve (e.g. a dependency)

If all the the above is true, then the require(esm) call throws.

The PnP runtime injects itself into the Node process by monkey-patching the CJS module loader (e.g. Module._resolveFilename). As far as I can tell, the implementation of require(esm) bypasses this monkey-patch: static imports of the required ESM to go through neither the CJS loader pipeline nor the ESM loader pipeline (--loader/module.register()), making it so that no third-party code can inject itself into the resolution process. Fortunately, seems like the implementation of module.registerHooks() has "fixed" that and those imports go through the CJS loader once again. See nodejs/node#52697 (comment).

The reason this issue does not happen for Yarn 4.5.3 is due to how Jest loads the transformer — it attempts require-ing it first, then fallback to a dynamic import if an ERR_REQUIRE_ESM is thrown. The underlying assumption is that requiring an ESM would throw such an error, which fails to take into account new features in node like require(esm) or stripping types. See jestjs/jest#14013.

Support for require(esm) in PnP was added in Yarn 4.6.0 (via #6639). Before that, the PnP runtime itself would throw an ERR_REQUIRE_ESM. In Yarn 4.6.0, if require(esm) is enabled, instead we just fallback to Node's default behavior, which in the situation described, throws an ERR_MODULE_NOT_FOUND instead of an ERR_REQUIRE_ESM.

This can be fixed/worked around by:

  • jest fixing its loading logic
  • using a node version where --experimental-require-module is not default (at the time of this writing, <22.12.0)
  • running node with --no-experimental-require-module (setting it via NODE_OPTIONS if necessary)
  • using a node version where module.registerHooks() is available (as of this writing, >=23.5.0)
  • using a dynamic import instead: export default import('babel-jest').then((module) => module.default.createTransformer())

As far as I can tell, the only way to fix this issue on our side is to revert our support for require(esm), which breaks many other projects. As such, I'm closing this issue as a wontfix for now. If anyone has addition insight into the issue or can find a feasible solution on Yarn's side, we can re-open it.

@clemyan clemyan closed this as not planned Won't fix, can't repro, duplicate, stale Feb 13, 2025
@Methuselah96
Copy link
Author

Methuselah96 commented Feb 13, 2025

Thanks for the update. I was already wary of Yarn PnP needing to patch Node and TypeScript in order for it to function. I have a workaround to get my Jest example working, but this issue also causes my Storybook build to fail, and I haven't found a trivial workaround for that. It's probably time for me to move off of Yarn PnP, despite it's faster installation times.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

3 participants