Skip to content
Nilay Kabariya

Entry No.002·Fixes·Updated ·3 min read

Fix: require, __dirname not defined in ES module scope

ReferenceError: require, __dirname or __filename is not defined in ES module scope. Why Node says it, and the fixes, tested on Node 24 and 26.

by Nilay#node#esm#javascript#npmFIXED

The error, verbatim

Jump to the fix ↓
ReferenceError: __dirname is not defined in ES module scope
ReferenceError: require is not defined in ES module scope, you can use import instead
This file is being treated as an ES module because it has a '.js' file
extension and 'package.json' contains "type": "module".
✓ Reproduced on Windows 11 Pro

Tested on

Node
24.14.0 and 26.11.1; re-run on 20.20.2, 22.23.4, 24.22.1 and 26.13.0 (Linux)
Module type
"type": "module" and .mjs
OS
Windows 11 Pro

✓ Last re-run on GitHub Actions · see the run · all repros

Contents
  1. __dirname and __filename01
  2. require02
  3. require() of a JSON file03
  4. What didn’t work04
  5. Versions I checked05

require, __dirname and __filename aren’t real globals. Node adds them to every CommonJS file, and ES modules don’t get them. So the moment Node treats your file as an ES module, all three are gone, with one of these errors:

ReferenceError: require is not defined in ES module scope, you can use import instead
ReferenceError: __dirname is not defined in ES module scope
ReferenceError: __filename is not defined in ES module scope

Node runs a file as an ES module in two cases, and the second line of its message says which one applies to you:

  • the file ends in .js and the nearest package.json has "type": "module"
  • the file ends in .mjs, whatever package.json says
This file is being treated as an ES module because it has a '.js' file extension and 'D:\project\package.json' contains "type": "module". To treat it as a CommonJS script, rename it to use the '.cjs' file extension.

On October 31, 2026 I re-ran all three on Node 24.14.0 and 26.11.1: the same errors on both. Node 26 prints the package.json path with a \\?\ prefix on Windows ('\\?\D:\project\package.json'), but the meaning is the same.

The usual way into this is copying CommonJS code into a project that was set up as ES modules (most new templates are), or adding "type": "module" to an older project.

__dirname and __filename

Use import.meta.dirname and import.meta.filename. They’re built into Node and need no imports:

import path from "node:path";

const dataFile = path.join(import.meta.dirname, "data.json");
console.log(import.meta.dirname);  // folder of this file
console.log(import.meta.filename); // full path of this file

import.meta.dirname and import.meta.filename were added in Node 20.11. On an older Node, use the classic two-line fallback:

import path from "node:path";
import { fileURLToPath } from "node:url";

const __filename = fileURLToPath(import.meta.url);
const __dirname = path.dirname(__filename);

require

1. Use import (the normal fix in an ES module project):

import isNumber from 'is-number';

2. Keep require with createRequire, for code you can’t easily change:

import { createRequire } from 'node:module';
const require = createRequire(import.meta.url);
const isNumber = require('is-number');

3. Make that one file CommonJS by renaming it to .cjs. It can then use require, __dirname and __filename, while the rest of the project stays ES modules.

require() of a JSON file

const data = require('./data.json') is a common reason to reach for require. A plain import doesn’t work for JSON:

TypeError [ERR_IMPORT_ATTRIBUTE_MISSING]: Module "file:///D:/project/data.json" needs an import attribute of "type: json"

Add the import attribute:

import data from './data.json' with { type: 'json' };

Leave the with part out and the import fails before your code runs: TypeError [ERR_IMPORT_ATTRIBUTE_MISSING]: Module "…/data.json" needs an import attribute of "type: json" on Node 22, 24 and 26, and ERR_IMPORT_ASSERTION_TYPE_MISSING on Node 20.

What didn’t work

Versions I checked

A folder with "type": "module" in its package.json, one file per case (require, __dirname, __filename), a data.json, a file using every fix above, and a .cjs file, run with Node 24.14.0 and Node 26.11.1 on Windows 11 Pro on October 31, 2026. The original tests were on Node 24.14.0 in September and October. Error text is copied from the runs; only the project path is shortened.

November 3, 2026: every case ran on Node 20.20.2, 22.23.4, 24.22.1 and 26.13.0 on Linux (GitHub Actions ubuntu-latest). The three ReferenceError messages were word for word the same on all four, .mjs still failed the same way, and import.meta.dirname / import.meta.filename, the fileURLToPath fallback, import, createRequire, a .cjs file and the JSON import with with { type: 'json' } all worked on every version. The script and the run are public.

— N.K., end of entry No.002

Useful? Pass it on:Post on XFollow @EmotionalMatter

Related entries

  1. No.001

    Fix: “Cannot use import statement outside a module”

    Why Node, Jest, TypeScript output or your browser refuses import (or throws Unexpected token 'export'), and the fix for each. Tested on Node 20 to 26.

    > SyntaxError: Cannot use import statement outside a module

    FIXED6 min
  2. No.093

    Fix: bigint Failed to load bindings, pure JS will be used

    bigint: Failed to load bindings, pure JS will be used. Why npm 12 shows it on every install, whether it matters, and how to get the native build back.

    > bigint: Failed to load bindings, pure JS will be used (try npm run rebuild?)

    FIXED3 minWindows
  3. No.091

    Fix: npm error code EALLOWREMOTE (and EALLOWGIT), tested

    npm error code EALLOWREMOTE: Fetching packages of type remote have been disabled. Every case reproduced on npm 12, from npx to npm ci, with each fix.

    > npm error code EALLOWREMOTE

    FIXED4 min

Post card · Every Sunday

What broke this week.

One email on Sundays: the Node, TypeScript, Python and AI SDK releases that broke builds that week, each one reproduced, with a link to the fix that worked. Never shared, and you can leave any time.

— Nilay

or follow by RSSor on X

By subscribing you agree to the privacy note. One click to leave.

tip: paste the exact error text