Skip to content

Instantly share code, notes, and snippets.

@osher
Last active August 29, 2024 11:16
Show Gist options
  • Save osher/860ffc96e81bc8b1d5b375850cca7bf0 to your computer and use it in GitHub Desktop.
Save osher/860ffc96e81bc8b1d5b375850cca7bf0 to your computer and use it in GitHub Desktop.
A script that analyses node_modules for stats of CJS and ESM usage
{
CJS=0; ESM=0; DUAL=0; UN=0; UNP=''; TYPES=0;
# for each `package.json` in the `node_modules` first and second levels:
for P in $({
ls node_modules/*/package.json;
ls node_modules/*/*/package.json || true;
ls node_modules/**/node_modules/*/package.json || true;
ls node_modules/**/node_modules/*/*/package.json || true;
} | sort); do
echo "checking: $P";
# unless the name implies it's a types project
if [ "$P" = "${P/@types//}" ] && [ "$P" = "${P/-types}" ] && [ "$P" = "${P%/types/package.json}" ]; then
# find declared type from package.json:type
T=$(node -p "require('./$P').type || 'null'");
case "$T" in
commonjs)
CJS=$(( CJS + 1 ));;
module)
ESM=$(( ESM + 1));;
null)
#is it a dual support module?
T=$(node -p "require('./$P').exports || 'null'");
if [ ! "$T" = "null" ]; then
# it has an exports section - count as dual support
DUAL=$(( DUAL + 1 ));
else # - need to take a peek in the main module
# find the main module
M=$(dirname "$P")/$(node -p "require('./$P').main || 'index.js'");
# does the module expecting the sufix to be detected?
[ -f "$M.js" ] && M="$M.js";
[ -f "$M.mjs" ] && M="$M.mjs";
# does the module name a directory, expecting the index to be detected?
[ -f "$M/index.js" ] && M="$M/index.js";
[ -f "$M/index.mjs" ] && M="$M/index.mjs";
# count the cases, or count an unidentified
if [ "'use strict'" = "$(grep . $M | sed 's/;//')" ]; #it's empty - its a stub for a types project
then $(( TYPES + 1));
elif grep -E 'require|module.exports|exports.' $M > /dev/null || [ -f "$M/index.json" ];
then CJS=$(( CJS + 1 ));
else # I give up. Count as unidentified.
UN=$(( UN + 1)); UNP="$UNP,${P//node_modules\//}";
fi
fi;;
esac;
else TYPES=$(( TYPES + 1));
fi
done
UNP="${UNP//\/package.json/}";
echo -e "Unknown:
${UNP//,/\n - }
Summary:
CJS: $CJS
ESM: $ESM
DUAL: $DUAL
TYPES: $TYPES
Unkown: $UN
";
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment