@@ -1362,9 +1362,7 @@ transpiler hooks should only be used for development and testing purposes.
13621362` ` ` mjs
13631363// coffeescript-hooks.mjs
13641364import { readFile } from ' node:fs/promises' ;
1365- import { dirname , extname , resolve as resolvePath } from ' node:path' ;
1366- import { cwd } from ' node:process' ;
1367- import { fileURLToPath , pathToFileURL } from ' node:url' ;
1365+ import { findPackageJSON } from ' node:module' ;
13681366import coffeescript from ' coffeescript' ;
13691367
13701368const extensionsRegex = / \. (coffee| litcoffee| coffee\. md)$ / ;
@@ -1391,7 +1389,7 @@ export async function load(url, context, nextLoad) {
13911389 }
13921390
13931391 // Let Node.js handle all other URLs.
1394- return nextLoad (url);
1392+ return nextLoad (url, context );
13951393}
13961394
13971395async function getPackageType (url ) {
@@ -1402,37 +1400,25 @@ async function getPackageType(url) {
14021400 // this simple truthy check for whether `url` contains a file extension will
14031401 // work for most projects but does not cover some edge-cases (such as
14041402 // extensionless files or a url ending in a trailing space)
1405- const isFilePath = !! extname (url);
1406- // If it is a file path, get the directory it's in
1407- const dir = isFilePath ?
1408- dirname (fileURLToPath (url)) :
1409- url;
1410- // Compose a file path to a package.json in the same directory,
1411- // which may or may not exist
1412- const packagePath = resolvePath (dir, ' package.json' );
1413- // Try to read the possibly nonexistent package.json
1414- const type = await readFile (packagePath, { encoding: ' utf8' })
1415- .then ((filestring ) => JSON .parse (filestring).type )
1416- .catch ((err ) => {
1417- if (err? .code !== ' ENOENT' ) console .error (err);
1418- });
1419- // If package.json existed and contained a `type` field with a value, voilà
1420- if (type) return type;
1421- // Otherwise, (if not at the root) continue checking the next directory up
1422- // If at the root, stop and return false
1423- return dir .length > 1 && getPackageType (resolvePath (dir, ' ..' ));
1403+ const pJson = findPackageJSON (url);
1404+ if (pJson) {
1405+ try {
1406+ const file = await readFile (pJson, ' utf8' );
1407+ return JSON .parse (file)? .type ;
1408+ } catch {
1409+ return undefined ;
1410+ }
1411+ }
1412+ return undefined ;
14241413}
14251414` ` `
14261415
14271416##### Synchronous version
14281417
14291418` ` ` mjs
14301419// coffeescript-sync-hooks.mjs
1431- import { readFileSync } from ' node:fs/promises' ;
1432- import { registerHooks } from ' node:module' ;
1433- import { dirname , extname , resolve as resolvePath } from ' node:path' ;
1434- import { cwd } from ' node:process' ;
1435- import { fileURLToPath , pathToFileURL } from ' node:url' ;
1420+ import { readFileSync } from ' node:fs' ;
1421+ import { registerHooks , findPackageJSON } from ' node:module' ;
14361422import coffeescript from ' coffeescript' ;
14371423
14381424const extensionsRegex = / \. (coffee| litcoffee| coffee\. md)$ / ;
@@ -1451,23 +1437,20 @@ function load(url, context, nextLoad) {
14511437 };
14521438 }
14531439
1454- return nextLoad (url);
1440+ return nextLoad (url, context );
14551441}
14561442
14571443function getPackageType (url ) {
1458- const isFilePath = !! extname (url);
1459- const dir = isFilePath ? dirname (fileURLToPath (url)) : url;
1460- const packagePath = resolvePath (dir, ' package.json' );
1461-
1462- let type;
1463- try {
1464- const filestring = readFileSync (packagePath, { encoding: ' utf8' });
1465- type = JSON .parse (filestring).type ;
1466- } catch (err) {
1467- if (err? .code !== ' ENOENT' ) console .error (err);
1444+ const pJson = findPackageJSON (url);
1445+ if (pJson) {
1446+ try {
1447+ const file = readFileSync (pJson, ' utf-8' );
1448+ return JSON .parse (file)? .type ;
1449+ } catch {
1450+ return undefined ;
1451+ }
14681452 }
1469- if (type) return type;
1470- return dir .length > 1 && getPackageType (resolvePath (dir, ' ..' ));
1453+ return undefined ;
14711454}
14721455
14731456registerHooks ({ load });
@@ -1486,9 +1469,24 @@ console.log "Brought to you by Node.js version #{version}"
14861469
14871470` ` ` coffee
14881471# scream .coffee
1489- export scream = (str ) - > str .toUpperCase ()
1472+ exort scream = (str) - > str .toUpperCase ()
14901473` ` `
14911474
1475+ For the sake of running the example, add a ` package .json ` file containing the
1476+ module type of the CoffeeScript files.
1477+
1478+ ` ` ` json
1479+ {
1480+ " type" : " module"
1481+ }
1482+ ` ` `
1483+
1484+ This is only for running the example. In real world loaders, ` getPackageType ()` must be
1485+ able to return an ` format` known to Node.js even in the absence of an explicit type in a
1486+ ` package .json ` , or otherwise the ` nextLoad` call would throw ` ERR_UNKNOWN_FILE_EXTENSION `
1487+ (if undefined) or ` ERR_UNKNOWN_MODULE_FORMAT ` (if it's not a known format listed in
1488+ the [load hook][] documentation).
1489+
14921490With the preceding hooks modules, running
14931491` node -- import ' data:text/javascript,import { register } from "node:module"; import { pathToFileURL } from "node:url"; register(pathToFileURL("./coffeescript-hooks.mjs"));' ./main.coffee`
14941492or ` node --import ./coffeescript-sync-hooks.mjs ./main.coffee`
0 commit comments