Skip to content
nkNilay Kabariya

Entry No.005·Fixes··1 min read

Fix: ERR_REQUIRE_ESM require() of ES Module not supported

Why require() of an ES module fails, why it mostly stopped failing on Node 22.12+, and the new errors you hit instead. All reproduced on Node 24.

by Nilay#node#esm#commonjsFIXED

The error, verbatim

Jump to the fix ↓
Error [ERR_REQUIRE_ESM]: require() of ES Module ...\node_modules\chalk\source\index.js
from ...\app.js not supported.
Instead change the require of index.js in ...\app.js to a dynamic import()
which is available in all CommonJS modules.
code: 'ERR_REQUIRE_ESM'

Tested on

Node
24.14.0
Package
chalk 5.6.2 (ESM-only)
Old behaviour
node --no-experimental-require-module
OS
Windows 11 Pro
Contents
  1. The fix01
  2. Upgraded Node and now see “is not a function”?02
  3. The other new error: ERR_REQUIRE_ASYNC_MODULE03
  4. Why it happens04
  5. How this was reproduced05

The fix

Option 1: upgrade Node. Since Node 22.12, require() can load ES modules by default. On Node 24 the exact code that throws ERR_REQUIRE_ESM just runs. If you’re on Node 20 or 22.11 or older, upgrading is the least-effort fix.

Option 2: use a dynamic import() from CommonJS. It works on every Node version, old or new:

(async () => {
  const { default: chalk } = await import("chalk");
  console.log(chalk.green("works"));
})();

Option 3: pin the last CommonJS version of the package, if one exists (for chalk that’s chalk@4). Or convert your own project to ESM with "type": "module" and use import everywhere.

Upgraded Node and now see “is not a function”?

This is the trap after the upgrade. require() of an ES module now returns the module namespace, so the package’s default export sits under .default:

TypeError: chalk.green is not a function

Add .default:

const chalk = require("chalk").default;
console.log(chalk.green("works"));

The other new error: ERR_REQUIRE_ASYNC_MODULE

require() still can’t load an ES module that uses top-level await:

Error [ERR_REQUIRE_ASYNC_MODULE]: require() cannot be used on an ESM graph with
top-level await. Use import() instead.

The fix is the same import() as Option 2:

import("./tla/index.js").then((m) => console.log(m.default));

Why it happens

Node has two module systems: CommonJS (require) and ES modules (import). Many popular packages, like chalk, node-fetch, got and nanoid, went ESM-only in their newer major versions. Older Node refused to require() them at all. Newer Node allows it, as long as the module graph has no top-level await.

How this was reproduced

Only Node 24 was installed, so the old error was reproduced by running Node 24 with --no-experimental-require-module. That flag turns off require(esm) and gives the exact error older Node versions produce.

— N.K., end of entry No.005

Useful? Pass it on:Post on X

Related entries

  1. No.002

    Fix: __dirname is not defined in ES module scope (Node 24)

    ES modules don't have __dirname or __filename. The one-line modern fix (import.meta.dirname) and the fallback for older Node, both run on Node 24.

    > console.log(path.join(__dirname, "data.json"));

    FIXED1 min
  2. No.001

    Fix: “Cannot use import statement outside a module”

    The fix for Node and the browser. On Node 24 a plain .js file now often just works, so here's exactly when the error still happens. Reproduced in both.

    > SyntaxError: Cannot use import statement outside a module

    FIXED1 min
  3. No.004

    Fix: ERR_OSSL_EVP_UNSUPPORTED digital envelope routines (webpack 4)

    Old webpack 4 builds crash on Node 17+ with 0308010C. Upgrading webpack 4 to 4.47.0 fixes it without the legacy OpenSSL flag. Reproduced on Node 24.

    > Error: error:0308010C:digital envelope routines::unsupported

    FIXED1 min

Post card · Newsletter

Get the next fix in your inbox.

One short email when a new entry is published. No spam, never shared, and you can leave any time.

— Nilay

or follow by RSS

By subscribing you agree to the privacy note. One click to leave.

tip: paste the exact error text