ESM is the modern standard: import and export with static analysis-friendly syntax. New Node projects set "type": "module" in package.json; this playground runs as ESM (.mjs).
Named and default exports
// math.mjs
export function add(a, b) { return a + b; }
export default function multiply(a, b) { return a * b; }
// app.mjs
import multiply, { add } from './math.mjs';
Built-in imports
import fs from 'node:fs/promises';
import { readFile } from 'node:fs/promises';
import path from 'node:path';
The node: prefix clarifies built-ins and avoids npm name collisions.
Dynamic import
const mod = await import('./feature.mjs');
Loads conditionally—useful for lazy loading or optional dependencies.
Important interview questions and answers
- Q: .mjs vs .js with "type":"module"?
A: Both run as ESM;.mjsforces ESM even without package.json type;.cjsforces CommonJS. - Q: Can you require an ESM module?
A: Not with syncrequire—use dynamicimport()from CommonJS instead.
Self-check
- What does the
node:prefix indicate? - When use dynamic
import()?
Tip: Use node: prefix for built-ins (import fs from 'node:fs/promises')—clearer and avoids shadowing npm packages named fs.
Interview prep
- ESM vs CommonJS default?
New Node projects use
"type": "module"in package.json for ESM;.cjsforces CommonJS,.mjsforces ESM regardless of package type.