async function mergeResponses(responsePromises, headers) { | |
const readers = responsePromises.map(p => Promise.resolve(p).then(r => r.body.getReader())); | |
let doneResolve; | |
let doneReject; | |
const done = new Promise((r, rr) => { | |
doneResolve = r; | |
doneReject = rr; | |
}); | |
const readable = new ReadableStream({ | |
async pull(controller) { | |
const reader = await readers[0]; | |
try { | |
const {done, value} = await reader.read(); | |
if (done) { | |
readers.shift(); | |
if (!readers[0]) { | |
controller.close(); | |
doneResolve(); | |
return; | |
} | |
return this.pull(controller); | |
} | |
controller.enqueue(value); | |
} | |
catch (err) { | |
doneReject(err); | |
throw err; | |
} | |
}, | |
cancel() { | |
doneResolve(); | |
} | |
}); | |
const response = await responsePromises[0]; | |
return { | |
done, | |
response: new Response(readable, { | |
headers: headers || response.headers | |
}) | |
}; | |
} |
// This depends on transform streams & async iterators | |
async function mergeResponses(responsePromises, headers) { | |
const {readable, writable} = new TransformStream(); | |
const done = (async function() { | |
for await (const response of responsePromises) { | |
await response.body.pipeTo(writable, {preventClose: true}); | |
} | |
writable.getWriter().close(); | |
})(); | |
return { | |
done, | |
response: new Response(readable, { | |
headers: headers || (await responsePromises[0]).headers | |
}) | |
}; | |
} |
This comment has been minimized.
This comment has been minimized.
Ah, well spotted! |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
This comment has been minimized.
Maybe a couple of bugs in this? Not sure if you can do a PR to a gist, but I had to change these:
Line 27:
Line 41:
Thanks for writing this. Very useful for a demo I'm doing for a talk this weekend!