/flags/javascript/node-input-type
node --input-type=module: run -e and stdin code as an ES module
- tool
- JavaScript
- command
- node
- flag
- --input-type=<type>
- default
- no value: Node.js detects the syntax (commonjs when --no-experimental-detect-module is passed)
- since
- Node.js 12.0.0
node --input-type=module -e "..." tells Node.js to run the code passed with -e/--eval, -p/--print or on standard input as an ES module, so import, top-level await and import.meta are available and require is not. --input-type=commonjs forces CommonJS instead. The option has no effect on files: node app.js still follows the file extension and package.json "type".
The four values
node --input-type=module -e 'import os from "node:os"; console.log("module:", typeof os.cpus, typeof require, typeof import.meta.url)'
node --input-type=commonjs -e 'console.log("commonjs:", typeof require, typeof module, typeof __filename)'
echo 'const n: number = 2; console.log("module-typescript:", n * 21)' | node --input-type=module-typescript
node --input-type=module -e 'require("node:path")' 2>&1 | grep Error
node --input-type=commonjs -e 'import fs from "node:fs"' 2>&1 | grep Error
node --input-type=esm -e '1' 2>&1 | sed 's/^.*node[^:]*: //'; echo "exit: ${PIPESTATUS[0]}"Output
module: function undefined string commonjs: function object string module-typescript: 42 ReferenceError: require is not defined in ES module scope, you can use import instead SyntaxError: Cannot use import statement outside a module --input-type must be "module","commonjs", "module-typescript" or "commonjs-typescript" exit: 9
Forcing the wrong type gives the two classic module errors: require is not defined in ES module scope in a module, and Cannot use import statement outside a module in CommonJS. An unknown value is rejected with the list of accepted ones.
| Value | Runs the input as | Since |
|---|---|---|
| module | ES module: import, export, top-level await, import.meta | Node.js 12.0.0 |
| commonjs | CommonJS: require, module, __filename | Node.js 12.0.0 |
| module-typescript | ES module after stripping TypeScript types | Node.js 23.6.0, 22.18.0 |
| commonjs-typescript | CommonJS after stripping TypeScript types | Node.js 23.6.0, 22.18.0 |
| (not set) | Detected: CommonJS first, then ES module, then with types stripped | Detection on by default since 22.7.0, 20.19.0 |
The -typescript values are not available together with --no-strip-types.
Do you still need it?
On current Node.js, input that contains module syntax is detected automatically:
node -e 'const { setTimeout: sleep } = await import("node:timers/promises"); await sleep(10); console.log("top-level await, detected as module")'
node -e 'console.log("no module syntax -> commonjs:", typeof require)'
echo 'console.log("stdin, module forced:", typeof require)' | node --input-type=moduleOutput
top-level await, detected as module no module syntax -> commonjs: function stdin, module forced: undefined
Code that has no import, export or top-level await is valid CommonJS, so detection keeps it CommonJS. Pass --input-type=module when you need ES module semantics for such code anyway (strict mode by default, no require, this is undefined at top level), in scripts that must behave the same on older Node.js versions, and to skip the detection step, which first tries to compile the input as CommonJS.
Common uses
# one-liner with named imports
node --input-type=module -e 'import { readFile } from "node:fs/promises"; console.log((await readFile("package.json", "utf8")).length)'
# heredoc script in CI, run as ESM
node --input-type=module <<'EOF'
import { execSync } from "node:child_process";
console.log(execSync("git rev-parse --short HEAD").toString().trim());
EOFFor files, use .mjs or "type": "module" in package.json; the differences between the two systems are explained in require vs import.
FAQ
Does --input-type change how node app.js is loaded?
No. It applies only to code given with --eval (-e), --print (-p) or on standard input. Files are ES modules or CommonJS according to their extension (.mjs, .cjs) and the type field in the nearest package.json.
Why does node -e with import work without --input-type?
Since Node.js 22.7 and 20.19, syntax detection is on by default: Node.js first tries the input as CommonJS and, if that fails because of module syntax, runs it as an ES module. --input-type skips the guess.
How do I run TypeScript passed with -e?
Use --input-type=module-typescript or commonjs-typescript (Node.js 23.6 and 22.18 or later). Types are stripped, not checked, so type errors are not reported.