diff --git a/lib/core/util.js b/lib/core/util.js index dfefac6d15c..71071aff47f 100644 --- a/lib/core/util.js +++ b/lib/core/util.js @@ -600,20 +600,25 @@ function ReadableStreamFrom (iterable) { async start () { iterator = iterable[Symbol.asyncIterator]() }, - async pull (controller) { - const { done, value } = await iterator.next() - if (done) { - queueMicrotask(() => { - controller.close() - controller.byobRequest?.respond(0) - }) - } else { - const buf = Buffer.isBuffer(value) ? value : Buffer.from(value) - if (buf.byteLength) { - controller.enqueue(new Uint8Array(buf)) + pull (controller) { + async function pull () { + const { done, value } = await iterator.next() + if (done) { + queueMicrotask(() => { + controller.close() + controller.byobRequest?.respond(0) + }) + } else { + const buf = Buffer.isBuffer(value) ? value : Buffer.from(value) + if (buf.byteLength) { + controller.enqueue(new Uint8Array(buf)) + } else { + return await pull() + } } } - return controller.desiredSize > 0 + + return pull() }, async cancel () { await iterator.return() diff --git a/test/fetch/issue-node-56474.js b/test/fetch/issue-node-56474.js new file mode 100644 index 00000000000..5c704a1bfcc --- /dev/null +++ b/test/fetch/issue-node-56474.js @@ -0,0 +1,30 @@ +'use strict' + +const { test } = require('node:test') +const { deepStrictEqual } = require('node:assert') +const { Response } = require('../..') + +// https://github.com/nodejs/node/issues/56474 +test('ReadableStream empty enqueue then other enqueued', async () => { + const iterable = { + async * [Symbol.asyncIterator] () { + yield '' + yield '3' + yield '4' + } + } + + const response = new Response(iterable) + deepStrictEqual(await response.text(), '34') +}) + +test('ReadableStream empty enqueue', async () => { + const iterable = { + async * [Symbol.asyncIterator] () { + yield '' + } + } + + const response = new Response(iterable) + deepStrictEqual(await response.text(), '') +})