Import ES6 Modules in Node.js
Janne Kemppainen |With the ECMAScript modules definition we can use the import
and export
keywords to load and publish library code. However, if you try to use them in your Node.js project you might encounter the following error:
SyntaxError: Cannot use import statement outside a module
This happens because while Node.js fully supports ES module imports and exports it treats your JavaScript code as CommonJS by default. Node expects your packages to be imported with the require
function like this:
const axios = require("axios");
but gives an error message because it sees this instead:
import axios from "axios";
The fix is simple, enable ES modules with one of these ways:
- rename your ES6 modules from the
.js
extension to.mjs
- add
"type": "module"
to yourpackage.json
file to load all files under it as ES modules
If you pass the code through STDIN
or with the --eval
argument as a string parameter you will need to add --input-type=module
to your node
command. This does not work for code that you run from a file, use one of the two other options instead!
Support for ECMAScript nodules became stable on Node 15. In prior versions the support is labeled experimental so you may see some warnings.
Now you can to use the import
keyword without errors! If you need a refresher on the ES6 module syntax there are great examples on the MDN Web Docs.
Can you mix import and require?
In one file you need to stick to one type of import syntax. The ES module syntax supports importing from CommonJS files so you don’t necessarily need to make the switch for all files in a large project. If the type definition in the package.json
is set to module
you can rename the remaining CommonJS formatted files to the .cjs
extension.
An alternative way is to create a package.json
file inside the directory that contains your CommonJS files and define the type as commonjs
. Node will then handle them properly. The type definition can be the only thing in the configuration file, so the following is also a valid package.json
:
{ "type": "commonjs" }
If your CommonJS module looks something like this:
// age.cjs
function printAge(age) {
console.log(`The age is ${age}`);
}
module.exports = { printAge }
Then you can import and use it normally on the ES6 side:
// main.js
import { printAge } from './age.cjs'
...
The opposite is not true, so you cannot require
ES6 modules since they are loaded asynchronously. You could use the dynamic import() function which is asynchronous but try to avoid it if at all possible. You can’t await code on the top level of CommonJS code which makes the dynamic import a real hassle to use.
For more details check the official Node documentation. It should answer most of your questions, though at times it can be hard to find what you’re looking for.
I hope this has answered some at least some of your questions. If you found these instructions unclear or find something that needs to be corrected then add your comment on the embedded tweet!
Discuss on Twitter
I didn't know how to use ES6 modules in Node.js, so I decided that a blog post could be usefulhttps://t.co/Bt7BP68CXS
— Janne Kemppainen (@pakstech) January 5, 2021
Previous post
GitHub Actions Repository Dispatch