MCPcopy Create free account
hub / github.com/WinterTC55/iter-streams / createNodeWriter

Function createNodeWriter

samples/12-nodejs-interop.ts:76–199  ·  view source on GitHub ↗

* Create a Writer that pipes to a Node.js Writable stream. * * Features: * - Proper backpressure handling (respects drain events) * - Error propagation from Node.js stream to writer * - Proper close/fail handling

(writable: Writable)

Source from the content-addressed store, hash-verified

74 * - Proper close/fail handling
75 */
76function createNodeWriter(writable: Writable): Writer {
77 let error: Error | null = null;
78 let drainResolve: (() => void) | null = null;
79 let closed = false;
80 let byteCount = 0;
81
82 // Listen for errors from the writable
83 writable.on('error', (err) => {
84 error = err;
85 // Resolve any pending drain wait
86 if (drainResolve) {
87 drainResolve();
88 drainResolve = null;
89 }
90 });
91
92 // Helper to wait for drain, optionally cancellable via signal
93 const waitForDrain = (signal?: AbortSignal): Promise<void> => {
94 return new Promise((resolve, reject) => {
95 if (signal?.aborted) {
96 reject(signal.reason);
97 return;
98 }
99 drainResolve = resolve;
100 const onDrain = () => {
101 signal?.removeEventListener('abort', onAbort);
102 drainResolve = null;
103 resolve();
104 };
105 const onAbort = () => {
106 writable.removeListener('drain', onDrain);
107 drainResolve = null;
108 reject(signal!.reason);
109 };
110 writable.once('drain', onDrain);
111 signal?.addEventListener('abort', onAbort, { once: true });
112 });
113 };
114
115 return {
116 get desiredSize(): number | null {
117 return closed || error ? null : 16384; // Reasonable default
118 },
119
120 async write(chunk: Uint8Array | string, options?: WriteOptions): Promise<void> {
121 if (error) throw error;
122 if (closed) throw new Error('Writer is closed');
123
124 const bytes = typeof chunk === 'string' ? textEncoder.encode(chunk) : chunk;
125 const buffer = Buffer.from(bytes.buffer, bytes.byteOffset, bytes.byteLength);
126
127 const canContinue = writable.write(buffer);
128 byteCount += buffer.length;
129
130 if (!canContinue) {
131 await waitForDrain(options?.signal);
132 if (error) throw error;
133 }

Callers 1

mainFunction · 0.85

Calls

no outgoing calls

Tested by

no test coverage detected