How to import and export in CommonJS and ES Modules
Tags: javascript, beginners
Published: 2023-01-13 09:41:25

> How to import and export in CommonJS and ES Modules

- CommonJS:  [modules are the original way to package JavaScript code for Node.js.](https://nodejs.org/api/modules.html)

- ES Modules: [ES modules bring an official, standardized module system to JavaScript.](https://hacks.mozilla.org/2018/03/es-modules-a-cartoon-deep-dive/)

There are good articles out there to understand what they are and their differences. Here are the links that I read.
Before diving into code right away, I recommend you read these articles.

- [commonjs-vs-es-modules](https://www.knowledgehut.com/blog/web-development/commonjs-vs-es-modules)
- [CommonJS vs. ES Modules: Modules and Imports in NodeJS](https://reflectoring.io/nodejs-modules-imports/)
- [Modules in JavaScript – CommonJS and ESmodules Explained](https://www.freecodecamp.org/news/modules-in-javascript/)

---

## CommonJS

### Basic Usage

[aboutme.js]
```javascript
const person = {
  name: "Lico",
  role: "Frontend Engineer",
};

function printName() {
  console.log(person.name);
}

function printRole() {
  console.log(person.role);
}

module.exports = {
  person,
  printName,
  printRole,
};
```

[main.js]
```javascript
const aboutme = require("./aboutme");

aboutme.printName();
aboutme.person.name = "lico!";
aboutme.printName();
```

![result](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/1mzj5xlud4qpjks3xg6p.png)

You can change the variables that imported from other modules, but do not encourage to do.

---

### Named Import

```javascript
const { printName, printRole } = require("./aboutme");

printName();
printRole();
```

You can import it with [Destructuring assignment](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Destructuring_assignment).

![result](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/7ify3axq64gwt4ahb736.png)

Of course, if you do not export functions, you can't import the functions.

*+ You can export anything instead of object*

[aboutme.js]
```javascript
const person = {
  name: "Lico",
  role: "Frontend Engineer",
};

function printName() {
  console.log(person.name);
}

function printRole() {
  console.log(person.role);
}

module.exports = {
  // person,
  // printName,
  printRole,
};
```

[main.js]
```javascript
const aboutme = require("./aboutme");

console.log(aboutme);
```

![result](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/1f9run3714mh764gxl4z.png)

---

## ES Modules

To use `ES Modules`, I added this line into `package.json`.

```json
{
  ...
  "type": "module"
  ...
}
```

### Basic Usage

```javascript
const person = {
  name: "Lico",
  role: "Frontend Engineer",
};

function printName() {
  console.log(person.name);
}

function printRole() {
  console.log(person.role);
}

export default {
  person,
  printName,
  printRole,
};
```

```javascript
import aboutme from "./aboutme.js";

aboutme.printName();
aboutme.person.name = "lico!";
aboutme.printName();
```

It's very similar to `CommonJS`. You are also able to change the exported variables.

---

### Named Import

```javascript
import { printRole } from "./aboutme.js";

printRole();
```

It is going to occur an error like below.

```
SyntaxError: The requested module './aboutme.js' does not provide an export named 'printRole'
```

To use named import, you must export the functions.

```javascript
export function printRole() {
  console.log(person.role);
}
```

The error would be gone. you can export multiple functions and variables with only one `export` keyword instead of put `export` in front of every functions and variables that you want to export. 

```javascript
const person = {
  name: "Lico",
  role: "Frontend Engineer",
};

function printName() {
  console.log(person.name);
}

function printRole() {
  console.log(person.role);
}

export { person, printName, printRole };

export default {
  person,
  printName,
  printRole,
};
```

And you are able to import with name.

```javascript
import { printRole, printName } from "./aboutme.js";

printRole();
printName();
```

You also can use `default` and `Named Import` both together and you can use `as` keyword to rename them.

```javascript
import aboutme, { printRole as role } from "./aboutme.js";

console.log(aboutme);
aboutme.printName();
role();
```

![result](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/rb667tyxhmdn1brwd3jv.png)

---

### Import with the Asterisk

[aboutme.js]
```javascript
const person = {
  name: "Lico",
  role: "Frontend Engineer",
};

function printName() {
  console.log(person.name);
}

function printRole() {
  console.log(person.role);
}

export { person, printName, printRole };

export default {
  person,
  printName,
};
```

[main.js]
```javascript
import * as aboutme from "./aboutme.js";

console.log(aboutme);
```

![result](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/qad47hmz8dmsluj2vvbo.png)

You see `default`. That is the object which is exported using `export default`. 


---

## Import a module which uses `CommonJS` as a module system from `ES Modules`


![Project Folder Structure](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/9il86o6fboga5uytrcpu.png)

[lib/aboutme.js]
```javascript
const person = {
  name: "Lico",
  role: "Frontend Engineer",
};

function printName() {
  console.log(person.name);
}

function printRole() {
  console.log(person.role);
}

module.exports = {
  person,
  printName,
  printRole,
};
```

[main.js]
```javascript
import aboutme, { person, printName, printRole } from "./lib/aboutme.js";

console.log(person);
console.log(printName);
console.log(printRole);
console.log(aboutme);
```

![result](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/t5vif6jxfx4nj0vbnf12.png)

You can use `default` and `Named Import`.

[main.js]
```javascript
import * as aboutme from "./lib/aboutme.js";

console.log(aboutme);
```

![result](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/rcfm6lh9952kbeto2u6h.png)

As you see, there are default and exported functions and a variable.

You cannot import a module which uses `ES Modules` as a module system from `CommonJS`. If you try it, you will see like this error. (With a bundler, it will be working)

![error](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ykuzjbde3m3eyyheszkc.png)

---

I hope you found it useful.
Enjoy your coding!