ES Modules in JavaScript
Introduction
ES modules (import / export) are the standard way to split code across files in modern JavaScript. Browsers and Node.js both support them when configured correctly. This chapter covers named and default exports, re-exports, and running module files in Node.
Prerequisites
Named Export
// math.mjs
export function add(a, b) {
return a + b;
}
export const PI = 3.14159;// main.mjs
import { add, PI } from "./math.mjs";
console.log(add(2, 3));
console.log(PI);Default Export
// logger.mjs
export default function log(message) {
console.log(`[log] ${message}`);
}// app.mjs
import log from "./logger.mjs";
log("server started");One default export per module; combine with named exports when useful.
Rename on Import
// import with alias
import { add as sum } from "./math.mjs";
console.log(sum(1, 1));Re-export Barrel File
// index.mjs
export { add, PI } from "./math.mjs";
export { default as log } from "./logger.mjs";Node.js: Enable ES Modules
Option A — use .mjs extension (shown above).
Option B — package.json:
{
"type": "module"
}Then .js files are treated as ES modules.
Warning
With "type": "module", require() is not available in .js files—use import or separate CommonJS files (see CommonJS).
import() Dynamic Import
// Load module lazily
async function loadPlugin() {
const mod = await import("./plugin.mjs");
mod.run();
}
loadPlugin();Returns a Promise—useful for code splitting and conditional loading.
Mini Example: Config Module
// config.mjs
export const port = Number(process.env.PORT ?? 3000);
export const host = "127.0.0.1";// server-stub.mjs
import { port, host } from "./config.mjs";
console.log(`Would listen on ${host}:${port}`);FAQ
.mjs vs .js?
.mjs always ES module; .js depends on nearest package.json "type".
Can I import JSON?
Node supports import data from "./file.json" with { type: "json" } in recent versions—check your Node LTS docs.
Circular imports?
Possible but tricky—refactor shared code into a third module when cycles appear.