Skip to content

fix(cli): recognise npm >=10.6.0 "npm error" prefix in ENOTEMPTY self-heal#3416

Open
krobipd wants to merge 1 commit into
ioBroker:masterfrom
krobipd:fix/enotempty-npm-error-prefix
Open

fix(cli): recognise npm >=10.6.0 "npm error" prefix in ENOTEMPTY self-heal#3416
krobipd wants to merge 1 commit into
ioBroker:masterfrom
krobipd:fix/enotempty-npm-error-prefix

Conversation

@krobipd

@krobipd krobipd commented Jul 14, 2026

Copy link
Copy Markdown

Problem

On npm >= 10.6.0 the automatic ENOTEMPTY recovery in handleNpmNotEmptyError() (packages/cli/src/lib/setup/setupInstall.ts) never removes the blocking npm temp directory, so an affected adapter install/upgrade aborts with:

Could not handle ENOTEMPTY, because no deletable files were found

even though the directory it needs to delete is right there.

Root cause

The failed destination path is read from result.stderr via:

?.find(line => line.startsWith('npm ERR! dest'))

Since npm/cli#7414 (npm v10.6.0, 2024-04-25) npm prints the log-level name instead of the old label, so the line is now npm error dest …. find(...) returns undefined, errorFilePath short-circuits to undefined, and the (correct) temp-dir deletion + retry is skipped.

Supported Node versions (18/20/22) ship npm from both eras — older npm prints npm ERR!, npm >= 10.6.0 prints npm error — so the parser must accept both.

Fix

Only the find predicate changes; extraction and deletion are untouched, so existing (old-npm) behaviour is unaffected and the previously-missed modern case now matches:

-            ?.find(line => line.startsWith('npm ERR! dest'))
+            ?.find(line => line.startsWith('npm ERR! dest') || line.startsWith('npm error dest'))

Verification

Real-world trigger: js-controller 7.2.2, Node 22.23.1, npm 10.9.8 — npm printed npm error dest /opt/iobroker/node_modules/.iobroker.govee-smart-b0IGQWNC. Removing that exact directory by hand (which the handler's rmSync targets and /^\..*-[a-zA-Z0-9]{8}$/ matches) unblocked the install, confirming the recovery logic is sound and only the stderr parsing was broken. Path extraction verified against both npm error dest … and npm ERR! dest …; npm run build passes.

Related field report: #3095 (ENOTEMPTY on update where the automatic recovery silently failed and the reporter was advised to run iob fix manually).

Follow-up: #3417 addresses the same stale npm ERR! assumption in the install success check (kept separate as it touches success/failure classification).

🤖 Generated with Claude Code

…-heal

handleNpmNotEmptyError() reads the failed destination path from stderr via
`startsWith('npm ERR! dest')`. Since npm/cli#7414 (npm v10.6.0) npm prints the
log-level name, so the line is `npm error dest ...`. The path is never
extracted, the temp-dir deletion + retry is skipped, and the install aborts
with "Could not handle ENOTEMPTY, because no deletable files were found".
Match both the old and current prefix.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant