Exploring Node.js Modules: CommonJS vs. ES6 Modules

Jitesh Verma
Globant
Published in
4 min readMay 8, 2023

In this article, we'll look at how to define modules in a Node.js project. You can either use CommonJS modules or ECMAScript modules. Knowing their pros and cons lets you pick the right one for your project. But first, let's understand what a module is.

What is a Module?

A module is a self-contained unit of code that encapsulates related functionality. This allows developers to organize their code into logical, reusable components. Such components can be easily imported and used in other parts of their project.

Node.js supports two module systems for organizing and sharing code. These are

  • CommonJS modules
  • ECMAScript modules

CommonJS modules have been the traditional method for handling dependencies in Node.js, whereas ECMAScript modules are a newer addition and follow the standard format used in modern browsers.

CommonJS Modules

The CommonJS module format specifies a way to define a module using a require()function to load modules and module.exports or exports object to expose functionality. Here is an example to demonstrate how to use require()and module.exports :

This image demonstrates how to use `require()` and `module.exports` to load a module or expose functionality from a module. In this example, we defined a function named `addTwo` in `addTwo.cjs` named file and exported it via `module.exports`. In another file named `index.cjs`, we imported it using `require()` function.
CommonJS Module Example

Different ways to configure CommonJS modules

Following are the ways to configure CommonJS modules in your project:

  • Files with a .js extension when the nearest parent package.json file doesn't contain a top-level field "type" ; refer to image Configuration 1
This example demonstrates how to use CommonJS module when the nearest parent `package.json` file doesn’t contain top-level field “type”.
Configuration 1

Files with a .js extension when the nearest parent package.json file contains a top-level field "type" with a value of "commonjs" ; refer to image Configuration 2

This example demonstrates, how to configure the CommonJS module with the nearest parent `package.json` file containing the field “type” with “commonjs” as a value.
Configuration 2
  • Files with .cjs extension; refer to image Configuration 3
This example demonstrates how to configure the CommonJs module using the `.cjs` extension.
Configuration 3

ECMAScript Modules

In ECMAScript modules exports and require keywords are not used. Instead, modules use the export and import keywords to export and import variables, functions, etc. Here is an example of how to use ECMAScript modules in Node.js:

This image shows two files. The first one is addTwo.js, which exports a function named “addTwo” using the “export” keyword. The second file is index.js, which imports the addTwo.js module using the “import” keyword. In index.js, we call the “addTwo” function with 5 as a parameter inside a console.log function.
ECMAScript Module Example

Different ways to configure ECMAScript modules

Following are the ways to configure ECMAScript modules in your project:

  • Files with .js extension when the nearest parent package.json file contains a top-level field "type" with a value of "module". Refer to image ECMAScript Module Configuration 1
This figure represents a `package.json` file with “type” attribute with value of “module”.
ECMAScript Module Configuration 1
  • Files with .mjs extension. Refer to image ECMAScript Module Configuration 2
This example demonstrate how to use ECMAScript Module using `.mjs` extension
ECMAScript Module Configuration 2

Pros and Cons of CommonJS and ES Modules

Following are the pros and cons of CommonJS modules:

  • Module loading in CommonJS is synchronous. Because module loading is synchronous, it can block the main thread of execution and cause delays if the modules being loaded are large. It can pose rigorous performance issues for large-scale applications that can load hundreds of modules.
  • In the case of legacy code or code written in the old version of NodeJS, CommonJS has full and stable support since it is the default standard. Versions preceding v8.5.0 have to be using this only.

Following are the pros and cons of ES modules:

  • Module loading in ES Module is asynchronous by default. The asynchronous loading of ES modules can improve the performance of your code by allowing other code to continue executing while the module is being loaded.
  • A file extension must be provided when using the import keyword. Directory indexes (e.g. ./directory/index.js ) must also be fully specified.
  • We can import CommonJS modules from ES modules since, in this case, module.exports simply become the default export which we might import as such.

Conclusion

In conclusion, ECMAScript and CommonJS modules are different approaches to defining and organizing code in Node.js applications.

ECMAScript modules provide a more modern and standardized way of defining modules, allowing for more flexibility and cleaner code. They use the import and export statements to define and export module code and allow for named exports, default exports, and re-exports.

CommonJS modules, on the other hand, are the older and more widely used approach to defining modules in Node.js. They use the require() function to load modules and the module.exports object to define and export module code.

ECMAScript modules have some advantages over CommonJS modules and are supported from Node.js 13.2.0 onwards. In general, the choice between the two module systems depends on the specific needs and requirements of the project.

Thanks for reading, and happy coding!

--

--