Skip to content

src: report libuv error when openAsBlob cannot stat - #65517

Merged
nodejs-github-bot merged 1 commit into
nodejs:mainfrom
bitpshr:fs/openasblob-uv-error
Aug 28, 2026
Merged

src: report libuv error when openAsBlob cannot stat#65517
nodejs-github-bot merged 1 commit into
nodejs:mainfrom
bitpshr:fs/openasblob-uv-error

Conversation

@bitpshr

@bitpshr bitpshr commented Aug 24, 2026

Copy link
Copy Markdown
Contributor

Fixes: #65514

FdEntry::Create() dropped the uv_fs_stat() status and returned nullptr, so BlobFromFilePath() reported every failure as ERR_INVALID_ARG_VALUE: Unable to open file as blob. A missing file is not a malformed argument, and the TypeError had no errno, syscall, or path to work with. This threads the status out and throws a UVException instead:

$ node -e 'require("fs").openAsBlob("./nope.txt")'
# before: TypeError [ERR_INVALID_ARG_VALUE]: Unable to open file as blob
# after:  Error: ENOENT: no such file or directory, stat './nope.txt'

which matches what fs.stat() reports for the same path, errno/syscall/path included.

Two notes:

  • The reported EACCES case does not actually reach this path. stat only needs traversal permission on the parent, so an unreadable file still opens fine and fails later at read time with NotReadableError. The stat failures this affects are ENOENT, ENOTDIR, ELOOP and friends.
  • fs: fix always return promise from fs.openAsBlob #62655 fixes the separate sync-throw half of fs.openAsBlob reports a missing file as ERR_INVALID_ARG_VALUE, discarding the ENOENT #65514 and its new test asserts ERR_INVALID_ARG_VALUE for a missing file, which would need updating if that lands after this. I wrote the test here as assert.rejects(async () => openAsBlob(missing), ...) so it passes either way, and I am happy to fold this into that PR instead if the reviewers there would rather keep it in one place.

I also left the directory case alone (openAsBlob("./some-dir") still succeeds and fails at read time). There is an existing TODO(@jasnell, @flakey5) on FdEntry about rejecting non-regular files, and that felt like a separate behavior change rather than something to slip in here. Glad to take it on as a follow-up.

`FdEntry::Create()` returned nullptr for any failed `uv_fs_stat()`,
discarding the status, and `BlobFromFilePath()` turned that into
`ERR_INVALID_ARG_VALUE: Unable to open file as blob`. A missing file is
not a malformed argument, and the resulting `TypeError` carried no
`errno`, `syscall`, or `path`, so ENOENT could not be told apart from
any other reason the path was unusable.

Thread the libuv status out of `CreateFdEntry()` and throw a
`UVException` instead, so `fs.openAsBlob()` reports the same error
`fs.stat()` does for the same path.

Fixes: nodejs#65514
Signed-off-by: Paul Bouchon <mail@bitpshr.net>
@nodejs-github-bot nodejs-github-bot added c++ Issues and PRs that require attention from people who are familiar with C++. needs-ci PRs that need a full CI run. labels Aug 24, 2026
@codecov

codecov Bot commented Aug 24, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 88.88889% with 1 line in your changes missing coverage. Please review.
✅ Project coverage is 90.16%. Comparing base (46a7dbd) to head (0e065fe).
⚠️ Report is 62 commits behind head on main.

Files with missing lines Patch % Lines
src/dataqueue/queue.cc 83.33% 0 Missing and 1 partial ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main   #65517      +/-   ##
==========================================
- Coverage   90.21%   90.16%   -0.06%     
==========================================
  Files         751      751              
  Lines      253550   253589      +39     
  Branches    47813    47782      -31     
==========================================
- Hits       228733   228640      -93     
- Misses      16076    16207     +131     
- Partials     8741     8742       +1     
Files with missing lines Coverage Δ
src/node_blob.cc 73.29% <100.00%> (+0.59%) ⬆️
src/dataqueue/queue.cc 67.74% <83.33%> (-0.20%) ⬇️

... and 31 files with indirect coverage changes

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@addaleax addaleax added author ready PRs with CI started, the required approvals, and no outstanding review comments. request-ci Add this label to start a Jenkins CI on a PR. labels Aug 27, 2026
@github-actions github-actions Bot removed the request-ci Add this label to start a Jenkins CI on a PR. label Aug 27, 2026
@nodejs-github-bot

Copy link
Copy Markdown
Collaborator

@trivikr trivikr added the commit-queue PRs queued for automated landing through the Commit Queue. label Aug 28, 2026
@nodejs-github-bot nodejs-github-bot added the lacks-second-approval Commit Queue PRs awaiting a second collaborator approval or completion of the required wait. label Aug 28, 2026
@nodejs-github-bot
nodejs-github-bot merged commit 0544741 into nodejs:main Aug 28, 2026
99 of 100 checks passed
@nodejs-github-bot

Copy link
Copy Markdown
Collaborator

Landed in 0544741

@nodejs-github-bot nodejs-github-bot removed commit-queue PRs queued for automated landing through the Commit Queue. lacks-second-approval Commit Queue PRs awaiting a second collaborator approval or completion of the required wait. labels Aug 28, 2026
aduh95 pushed a commit that referenced this pull request Aug 29, 2026
`FdEntry::Create()` returned nullptr for any failed `uv_fs_stat()`,
discarding the status, and `BlobFromFilePath()` turned that into
`ERR_INVALID_ARG_VALUE: Unable to open file as blob`. A missing file is
not a malformed argument, and the resulting `TypeError` carried no
`errno`, `syscall`, or `path`, so ENOENT could not be told apart from
any other reason the path was unusable.

Thread the libuv status out of `CreateFdEntry()` and throw a
`UVException` instead, so `fs.openAsBlob()` reports the same error
`fs.stat()` does for the same path.

Fixes: #65514
Signed-off-by: Paul Bouchon <mail@bitpshr.net>
PR-URL: #65517
Reviewed-By: Anna Henningsen <anna@addaleax.net>
Reviewed-By: Antoine du Hamel <duhamelantoine1995@gmail.com>
aduh95 pushed a commit that referenced this pull request Sep 3, 2026
`FdEntry::Create()` returned nullptr for any failed `uv_fs_stat()`,
discarding the status, and `BlobFromFilePath()` turned that into
`ERR_INVALID_ARG_VALUE: Unable to open file as blob`. A missing file is
not a malformed argument, and the resulting `TypeError` carried no
`errno`, `syscall`, or `path`, so ENOENT could not be told apart from
any other reason the path was unusable.

Thread the libuv status out of `CreateFdEntry()` and throw a
`UVException` instead, so `fs.openAsBlob()` reports the same error
`fs.stat()` does for the same path.

Fixes: #65514
Signed-off-by: Paul Bouchon <mail@bitpshr.net>
PR-URL: #65517
Reviewed-By: Anna Henningsen <anna@addaleax.net>
Reviewed-By: Antoine du Hamel <duhamelantoine1995@gmail.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

author ready PRs with CI started, the required approvals, and no outstanding review comments. c++ Issues and PRs that require attention from people who are familiar with C++. needs-ci PRs that need a full CI run.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

fs.openAsBlob reports a missing file as ERR_INVALID_ARG_VALUE, discarding the ENOENT

5 participants