It is not obvious from the post but it seems like the allow list for the scripts supports whitelisting packages instead of a global setting. This should make it easier to maintain org-wise rules to allow scripts only for specific packages.
Is there a linter that could be used for scenarios like this to prevent unsafe default on package manager config?
My big question as an OSS dev distributing some precompiled binaries via npm for easy installation: does allowScripts also default to disabled when directly installing a package (globally or otherwise)?
I bet there have been a hundred different discussions about this inside of NPM since it was disclosed 10 years ago. With Shai Halud it's gotten too big to ignore.
I do love that javascript's history is basically just coder mentality distilled. "oh yeah we'll fix that shortly" is almost always "oh fuck now we have to"
There's an easy way to stop most supply chain attacks:
1. Publishing users must approve each and every release from a smartphone app.
2. Publishing users must provide verified government ID.
The first step prevents the types of attacks where an attacker gets control of a maintainer's computer and publishes a new release.
The second step discourages attacks where a user tries to get a malicious package used by others.
When combined with the security features that already exist, e.g. delays and automatic scanning, it would make it considerably harder to pull off a successful attack.
Issue is this is such a pain (and shuts out a large percentage of the world population) that you'll inevitably get a parallel ecosystem of packages without these onerous controls that everyone would end up using.
I don't know how to square the circle but any variation of "make it safer but really painful and difficult for anyone to publish a package" has this problem
If you force every user to just use "--enable-unsecure-feature", guess what will happen?
This is not about improving security. This is about shifting blame.
A much better alternative would've been the introduction of sandboxes or simulation runs that would output which scripts and programs are running due to unpredictable dependencies. This way the user could check before the actual execution, and maintain an allow list much easier. That could be done via an npm update && npm upgrade workflow where the update generates the list that the user has to manually confirm.
Heck, even a chroot would be an improvement, and they're almost pointless these days, considering how good malware got at escaping chroots.
I don't think it's pointless. A large number (the majority?) of users probably don't need install scripts, so disabling them by default is a net security improvement. Those that do can enable the insecure behavior, which will become an explicit decision that is trackable, auditable, etc.
You're not wrong about sandboxing, but sandboxing isn't something that can just be blithely introduced to a large packaging ecosystem that previously assumed full system access. Doing so results in the same kind of regression you point out: if the sandboxing breaks peoples' builds, they'll just disable it and move on with their goals.
Most users don't need it. Having it on by default is a feature for malware writers not users.
But to your point, Node has had permission flags for a while[0] but allows everything by default. Npm could use them to increase security even more. I just hope it doesn't take them another 10 years to change the default.
Are the current LTS node versions (iirc 22, 24, 26) going to update the bundled npm to v12 to benefit from these security fixes? All come with npm v11 now
I wonder if there are still reasons to use yarn? Has yarn also implemented safeguards to protect against supply chain attacks? Until now, I only knew about pnpm. It’s great that npm has followed up.
Though I mostly use pnpm these days, yarn still has a feature that I frequently miss: the project-local cache[0]. Basically, every dependency archive fetched from a registry is stored in your repo in .yarn/cache, so unless you're adding/updating dependencies a `yarn install` will work fully offline.
I'm sure there are drawbacks to this method regarding repo size etc., but it just feels good knowing that my repo contains everything needed to install and run any version of my project.
I should add: this is enabled by adding `enableGlobalCache: false` to .yarnrc.yml, though I think it was the default for a bit when Yarn 2 first released.
54 comments
[ 2.3 ms ] story [ 83.2 ms ] threadhttps://red.anthropic.com/2026/n-days/
So that is a poor bandaid to use now. Maybe instead validate things before, and have more of a cathedral and human reputation system.
Which was a little weird for the modules that don't run standalone but whatever.
https://www.kb.cert.org/vuls/id/319816
Couldn’t this effectively result in the same process we get in pre-12 defaults?
Is there a linter that could be used for scenarios like this to prevent unsafe default on package manager config?
But if you're already following the os + cpu + optionalDependencies model to distribute your precompiled binaries you should be fine.
Finally.
Nice that they're following pnpm's lead on this after [checks watch]... 18 months?
1. Publishing users must approve each and every release from a smartphone app.
2. Publishing users must provide verified government ID.
The first step prevents the types of attacks where an attacker gets control of a maintainer's computer and publishes a new release.
The second step discourages attacks where a user tries to get a malicious package used by others.
When combined with the security features that already exist, e.g. delays and automatic scanning, it would make it considerably harder to pull off a successful attack.
I don't know how to square the circle but any variation of "make it safer but really painful and difficult for anyone to publish a package" has this problem
See also https://wikipedia.org/wiki/Confused_deputy_problem
You don't need permission to publish an exploit, you just need someone or something else to do it for you.
If you force every user to just use "--enable-unsecure-feature", guess what will happen?
This is not about improving security. This is about shifting blame.
A much better alternative would've been the introduction of sandboxes or simulation runs that would output which scripts and programs are running due to unpredictable dependencies. This way the user could check before the actual execution, and maintain an allow list much easier. That could be done via an npm update && npm upgrade workflow where the update generates the list that the user has to manually confirm.
Heck, even a chroot would be an improvement, and they're almost pointless these days, considering how good malware got at escaping chroots.
You're not wrong about sandboxing, but sandboxing isn't something that can just be blithely introduced to a large packaging ecosystem that previously assumed full system access. Doing so results in the same kind of regression you point out: if the sandboxing breaks peoples' builds, they'll just disable it and move on with their goals.
But to your point, Node has had permission flags for a while[0] but allows everything by default. Npm could use them to increase security even more. I just hope it doesn't take them another 10 years to change the default.
[0] https://nodejs.org/api/permissions.html
If you force every user to just write "mut", guess what will happen?
They will write "mut" when they need mutable variables, which in practice turns out to be the minority of variables.
It's the same with "Option". The vast majority of variables or struct members do not need to be nullable at all.
I'm sure there are drawbacks to this method regarding repo size etc., but it just feels good knowing that my repo contains everything needed to install and run any version of my project.
[0]: https://yarnpkg.com/features/caching#offline-mirror