CodePark/ questions / Modules
START PRACTICINGPRACTICE
Frontend question · JavaScript › Modules

What are the differences between ES modules and CommonJS?

CommonJS (CJS) is Node's original module system. ES modules (ESM) are the official JavaScript standard. The main difference: CommonJS loads at runtime and can be anywhere, while ES module imports are static and can be analyzed before the code runs.

CommonJS:

  • It uses require() and module.exports.
  • Loading is synchronous and happens at runtime. So require can appear anywhere, even inside an if.
  • You get a copy of the exported value at the moment of the call. For objects, the copy is a reference to the same object.

ES modules:

  • They use import and export.
  • Static import declarations must be at the top level. So tools can read the dependency graph before running the code. This enables tree shaking (removing unused code).
  • Loading is asynchronous in browsers.
  • Imports are live read-only bindings. "Live" means you always see the exporter's current value. "Read-only" means the importer cannot assign to it.
  • Modules are always strict, top-level this is undefined, and top-level await is allowed.
  • import() loads a module dynamically and returns a promise.

In Node: a file is ESM if it ends in .mjs, or if package.json has "type": "module". ESM can import CommonJS. Recent Node versions can also require() ES modules that do not use top-level await.

  • CommonJS uses require and module.exports. It loads synchronously at runtime and can be dynamic.
  • ESM uses static import and export. Tools can analyze them, which enables tree shaking.
  • ESM imports are live bindings. CommonJS gives the value at the time of require.
  • ESM is strict, supports top-level await, and uses import() for dynamic loading.
  • Node chooses the system by the .mjs or .cjs extension, or the type field in package.json.