2024-09-23 npm clean-install --ignore scripts - it's a trap

A few days ago I was scripting a Node.js project and I had a very specific need. I wrote a script run as postinstall, but I wanted to launch it only in specific circumstances. When I found out that npm clean-install has an --ignore-scripts option, I was really glad – until I tried it out.

This is what the documentation says about this option:
If true, npm does not run scripts specified in package.json files.
Note that commands explicitly intended to run a particular script, such as npm start, npm stop, npm restart, npm test, and npm run-script will still run their intended script if ignore-scripts is set, but they will not run any pre- or post-scripts.

Does that imply that – for example – the postinstall script is not run? Yes, it does. Does it imply that when installing individual packages into node_modules, their postinstall scripts are not run? Hard to say, but that is exactly what happens! In my case, the project contained the esbuild package, which relies on postinstall to do some rather mysterious stuff related to installing its binary components. (I tried to fathom its postinstall script, but gave up after a few minutes – it’s certainly doable, but I don’t need this knowledge that much.)

One way to solve this is to issue the npm rebuild command, either in every subdirectory of node_modules (which, I’m afraid, might take ages…) or just in those ones which actually need it. The question is, how do I know which ones do? It occurred to me later that I can easily write some code to parse package.json of every installed module, but this is definitely a case of fighting tools which were supposed to help you…

(Warning: rant incoming, again…)

What’s even worse, while writing this post, I discovered that the npm documentation’s search feature is practically worthless. For example, typing postinstall (or post-install, for that matter) into the search box reveals no results. Interestingly, while I type postinstall, different things happen. After typing p, a bunch of 20 suggestions appears; funnily enough, one of them is a page not found link. Well, it actually starts with p, so it seems legit… When I type o (so I have po in the search box), another set of 20 suggestions appears. I have a hunch that there are less pages matching po than just p, so there must be a limit of 20 suggestions shown. Why someone decided that a 404 page is useful enough to include in the suggestions for the p prefix is of course beyond me.

But wait, there’s more. When I type the next few letters, arriving at posti, I get no suggestions at all. But typing n (so that now I have postin in the search box) yields a suggestion of Reporting malware in an npm package, a page which does not seem to contain the string postin anywhere! I have no idea how this can happen… Even assuming it has postin in some kind of metadata, how come posti didn’t reveal it as well?

Last but not least, as I said, typing postinstall (or post-install) does not reveal anything at all.

Now, I am pretty accustomed to using the Info documentation system present in Emacs. It works infinitely better than npm’s docs:

Compared to Emacs manuals in Info, npm docs are technologically inferior and have significantly lower quality. It appears that I’m better off using DuckDuckGo (or better, Kagi) with a site: filter.

Anyway, it’s time for a conclusion – except that I don’t have any, apart from the obvious one that both the design and documentation of npm are less than ideal. Just be warned that the npm CLI tool does not always do what you wish it were doing…

CategoryEnglish, CategoryBlog, CategoryJavaScript