Skip to content

Instantly share code, notes, and snippets.

@mhart
Last active December 22, 2025 03:14
Show Gist options
  • Select an option

  • Save mhart/dc7320acacd3e5a635f39db1fe767fd7 to your computer and use it in GitHub Desktop.

Select an option

Save mhart/dc7320acacd3e5a635f39db1fe767fd7 to your computer and use it in GitHub Desktop.
A utility function that creates/reads a byte stream (eg request.body) with larger chunks (defaults to 256KB)
export default {
async fetch(request: Request) {
const chunkedRequestBody = request.body && chunkStream(request.body);
return new Response(chunkedRequestBody);
},
};
// By default will emit chunks of length `chunkSize` (default 256KB).
// If you wish to emit as soon as available, you can pass in `allowPartial: true`,
// you may just end up with more buffers, some smaller than `chunkSize`.
function chunkStream(
sourceStream: ReadableStream<Uint8Array>,
{ chunkSize = 256 * 1024, allowPartial = false }: { chunkSize?: number; allowPartial?: boolean } = {},
): ReadableStream<Uint8Array> {
const reader = sourceStream.getReader({ mode: "byob" });
return new ReadableStream({
async pull(controller) {
const { done, value } = await reader.read(
new Uint8Array(new ArrayBuffer(chunkSize)),
// @ts-expect-error 2nd arg currently missing from @cloudflare/workers-types
allowPartial ? undefined : { min: chunkSize },
);
if (value != null && value.byteLength > 0) {
controller.enqueue(new Uint8Array(value.buffer, 0, value.byteLength));
}
if (done) {
controller.close();
}
},
cancel(reason) {
return reader.cancel(reason);
},
});
}
// Or a class version if you want to do `new ChunkedStream(sourceStream)`
class ChunkedStream extends ReadableStream<Uint8Array> {
constructor(
sourceStream: ReadableStream<Uint8Array>,
{ chunkSize = 256 * 1024, allowPartial = false }: { chunkSize?: number; allowPartial?: boolean } = {},
) {
const reader = sourceStream.getReader({ mode: "byob" });
super({
async pull(controller) {
// as above...
},
cancel(reason) {
// as above...
},
});
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment