|
1 | 1 | 'use strict';
|
2 | 2 |
|
3 | 3 | const {
|
| 4 | + ArrayPrototypeFilter, |
| 5 | + ArrayPrototypeMap, |
| 6 | + Boolean, |
| 7 | + ObjectEntries, |
4 | 8 | PromisePrototypeThen,
|
5 | 9 | PromiseResolve,
|
6 | 10 | SafePromiseAll,
|
7 | 11 | SafePromisePrototypeFinally,
|
| 12 | + SafeSet, |
8 | 13 | TypedArrayPrototypeGetBuffer,
|
9 |
| - TypedArrayPrototypeGetByteOffset, |
10 | 14 | TypedArrayPrototypeGetByteLength,
|
| 15 | + TypedArrayPrototypeGetByteOffset, |
| 16 | + TypeError, |
11 | 17 | Uint8Array,
|
12 | 18 | } = primordials;
|
13 | 19 |
|
@@ -82,6 +88,38 @@ const { UV_EOF } = internalBinding('uv');
|
82 | 88 |
|
83 | 89 | const encoder = new TextEncoder();
|
84 | 90 |
|
| 91 | +// Collect all negative (error) ZLIB codes and Z_NEED_DICT |
| 92 | +const ZLIB_FAILURES = new SafeSet([ |
| 93 | + ...ArrayPrototypeFilter( |
| 94 | + ArrayPrototypeMap( |
| 95 | + ObjectEntries(internalBinding('constants').zlib), |
| 96 | + ({ 0: code, 1: value }) => (value < 0 ? code : null), |
| 97 | + ), |
| 98 | + Boolean, |
| 99 | + ), |
| 100 | + 'Z_NEED_DICT', |
| 101 | +]); |
| 102 | + |
| 103 | +/** |
| 104 | + * @param {Error|null} cause |
| 105 | + * @returns {Error|null} |
| 106 | + */ |
| 107 | +function handleKnownInternalErrors(cause) { |
| 108 | + switch (true) { |
| 109 | + case cause?.code === 'ERR_STREAM_PREMATURE_CLOSE': { |
| 110 | + return new AbortError(undefined, { cause }); |
| 111 | + } |
| 112 | + case ZLIB_FAILURES.has(cause?.code): { |
| 113 | + // eslint-disable-next-line no-restricted-syntax |
| 114 | + const error = new TypeError(undefined, { cause }); |
| 115 | + error.code = cause.code; |
| 116 | + return error; |
| 117 | + } |
| 118 | + default: |
| 119 | + return cause; |
| 120 | + } |
| 121 | +} |
| 122 | + |
85 | 123 | /**
|
86 | 124 | * @typedef {import('../../stream').Writable} Writable
|
87 | 125 | * @typedef {import('../../stream').Readable} Readable
|
@@ -137,10 +175,7 @@ function newWritableStreamFromStreamWritable(streamWritable) {
|
137 | 175 | }
|
138 | 176 |
|
139 | 177 | const cleanup = finished(streamWritable, (error) => {
|
140 |
| - if (error?.code === 'ERR_STREAM_PREMATURE_CLOSE') { |
141 |
| - const err = new AbortError(undefined, { cause: error }); |
142 |
| - error = err; |
143 |
| - } |
| 178 | + error = handleKnownInternalErrors(error); |
144 | 179 |
|
145 | 180 | cleanup();
|
146 | 181 | // This is a protection against non-standard, legacy streams
|
@@ -440,10 +475,7 @@ function newReadableStreamFromStreamReadable(streamReadable, options = kEmptyObj
|
440 | 475 | streamReadable.pause();
|
441 | 476 |
|
442 | 477 | const cleanup = finished(streamReadable, (error) => {
|
443 |
| - if (error?.code === 'ERR_STREAM_PREMATURE_CLOSE') { |
444 |
| - const err = new AbortError(undefined, { cause: error }); |
445 |
| - error = err; |
446 |
| - } |
| 478 | + error = handleKnownInternalErrors(error); |
447 | 479 |
|
448 | 480 | cleanup();
|
449 | 481 | // This is a protection against non-standard, legacy streams
|
|
0 commit comments