@@ -2339,6 +2339,35 @@ if command -v node >/dev/null 2>&1; then
23392339 PI_NODE=$( command -v node)
23402340 PI_PROBE_DIR=" $TMPDIR /pi-node-probe"
23412341 mkdir -p " $PI_PROBE_DIR "
2342+ # The extension is loaded by the Pi host, not by bare Node, so the probe
2343+ # provides what that host provides: Node's builtins plus the packages Pi
2344+ # ships to extensions (`typebox` — Pi's schema library for tool
2345+ # parameters). Every import the generated file makes must come from that
2346+ # set, otherwise it loads in this probe and fails in a real install with
2347+ # ERR_MODULE_NOT_FOUND. The typebox stub is a Proxy: any Type.X(...) call
2348+ # returns a descriptor, so the probe never depends on which helpers the
2349+ # emitter uses; it only exercises the tool lifecycle.
2350+ PI_HOST_PACKAGES=" typebox"
2351+ mkdir -p " $PI_PROBE_DIR /node_modules/typebox"
2352+ cat > " $PI_PROBE_DIR /node_modules/typebox/package.json" << 'PITYPEBOXPKG '
2353+ { "name": "typebox", "version": "0.0.0-smoke-stub", "type": "module", "exports": "./index.mjs" }
2354+ PITYPEBOXPKG
2355+ cat > " $PI_PROBE_DIR /node_modules/typebox/index.mjs" << 'PITYPEBOXSTUB '
2356+ export const Type = new Proxy({}, {
2357+ get: (_target, helper) => (...args) => ({ smokeStubHelper: String(helper), args }),
2358+ });
2359+ export default { Type };
2360+ PITYPEBOXSTUB
2361+ PI_FOREIGN_IMPORTS=$( grep -oE " ^import .* from '[^']+'" " $PI_EXTENSION " |
2362+ sed -E " s/.* from '([^']+)'/\1/" | grep -vE ' ^node:' |
2363+ grep -vxF -f <(
2364+ # shellcheck disable=SC2086
2365+ printf ' %s\n' $PI_HOST_PACKAGES
2366+ ) || true)
2367+ if [ -n " $PI_FOREIGN_IMPORTS " ]; then
2368+ echo " FAIL 8al-node: generated Pi extension imports packages the Pi host does not provide: $( echo " $PI_FOREIGN_IMPORTS " | tr ' \n' ' ' ) "
2369+ exit 1
2370+ fi
23422371 python3 - " $PI_EXTENSION " " $PI_PROBE_DIR /cbmem.mjs" << 'PYPIADAPTER '
23432372import pathlib
23442373import sys
0 commit comments