diff --git a/lib/internal/blob.js b/lib/internal/blob.js index 20f7078d1d0915..40238b3f5b2cbb 100644 --- a/lib/internal/blob.js +++ b/lib/internal/blob.js @@ -455,9 +455,13 @@ function createBlobReaderStream(reader) { this.pendingPulls = []; // Register a wakeup callback that the C++ side can invoke // when new data is available after a STATUS_BLOCK. + let immediate; reader.setWakeup(() => { if (this.pendingPulls.length > 0) { - this.readNext(c); + immediate ??= setImmediate(() => { + immediate = undefined; + this.readNext(c); + }); } }); }, @@ -544,7 +548,13 @@ const kMaxBatchChunks = 16; async function* createBlobReaderIterable(reader, options = kEmptyObject) { const { getReadError } = options; let wakeup = PromiseWithResolvers(); - reader.setWakeup(wakeup.resolve); + let immediate; + reader.setWakeup(() => { + immediate ??= setImmediate(() => { + immediate = undefined; + wakeup.resolve?.(); + }); + }); try { while (true) { @@ -591,7 +601,6 @@ async function* createBlobReaderIterable(reader, options = kEmptyObject) { if (blocked) { const fin = await wakeup.promise; wakeup = PromiseWithResolvers(); - reader.setWakeup(wakeup.resolve); // If the wakeup was triggered by FIN (EndReadable), the DataQueue // is capped. Continue the loop to pull again -- the next pull will // return EOS. Without this, a race between the data notification