@whatwg-node/node-fetch 0.7.23-alpha-20250726012104-80b722590ec2d4fb9c98bfa7a74d8daf31fcf4bf → 0.7.23-alpha-20250726021628-c861bb0cd6c3ada6f0e3083708b8efbc457229ab
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/cjs/Body.js +24 -5
- package/cjs/Request.js +2 -0
- package/cjs/fetchCurl.js +6 -10
- package/cjs/fetchNodeHttp.js +4 -8
- package/cjs/utils.js +0 -44
- package/esm/Body.js +26 -7
- package/esm/Request.js +2 -0
- package/esm/fetchCurl.js +7 -11
- package/esm/fetchNodeHttp.js +6 -10
- package/esm/utils.js +0 -43
- package/package.json +1 -1
- package/typings/Body.d.cts +0 -1
- package/typings/Body.d.ts +0 -1
- package/typings/Request.d.cts +1 -0
- package/typings/Request.d.ts +1 -0
- package/typings/utils.d.cts +0 -6
- package/typings/utils.d.ts +0 -6
package/cjs/Body.js
CHANGED
|
@@ -27,23 +27,45 @@ class PonyfillBody {
|
|
|
27
27
|
bodyUsed = false;
|
|
28
28
|
contentType = null;
|
|
29
29
|
contentLength = null;
|
|
30
|
-
_signal = null;
|
|
31
30
|
constructor(bodyInit, options = {}) {
|
|
32
31
|
this.bodyInit = bodyInit;
|
|
33
32
|
this.options = options;
|
|
34
|
-
this._signal = options.signal || null;
|
|
35
33
|
const { bodyFactory, contentType, contentLength, bodyType, buffer } = processBodyInit(bodyInit);
|
|
36
34
|
this._bodyFactory = bodyFactory;
|
|
37
35
|
this.contentType = contentType;
|
|
38
36
|
this.contentLength = contentLength;
|
|
39
37
|
this.bodyType = bodyType;
|
|
40
38
|
this._buffer = buffer;
|
|
39
|
+
if (!buffer) {
|
|
40
|
+
this._chunks = this._doCollectChunksFromReadableJob();
|
|
41
|
+
}
|
|
41
42
|
}
|
|
42
43
|
bodyType;
|
|
43
44
|
_bodyFactory = () => null;
|
|
44
45
|
_generatedBody = null;
|
|
45
46
|
_buffer;
|
|
46
47
|
generateBody() {
|
|
48
|
+
if (!this._buffer && this._chunks) {
|
|
49
|
+
if ((0, promise_helpers_1.isPromise)(this._chunks)) {
|
|
50
|
+
const chunks$ = this._chunks;
|
|
51
|
+
this._generatedBody = new ReadableStream_js_1.PonyfillReadableStream({
|
|
52
|
+
start: controller => {
|
|
53
|
+
chunks$.then(chunks => {
|
|
54
|
+
this._buffer = node_buffer_1.Buffer.concat(chunks);
|
|
55
|
+
for (const chunk of chunks) {
|
|
56
|
+
controller.enqueue(chunk);
|
|
57
|
+
}
|
|
58
|
+
controller.close();
|
|
59
|
+
});
|
|
60
|
+
},
|
|
61
|
+
});
|
|
62
|
+
}
|
|
63
|
+
else {
|
|
64
|
+
this._buffer = node_buffer_1.Buffer.concat(this._chunks);
|
|
65
|
+
this._generatedBody = new ReadableStream_js_1.PonyfillReadableStream(node_stream_1.Readable.from(this._buffer));
|
|
66
|
+
}
|
|
67
|
+
return this._generatedBody;
|
|
68
|
+
}
|
|
47
69
|
if (this._generatedBody?.readable?.destroyed && this._buffer) {
|
|
48
70
|
this._generatedBody.readable = node_stream_1.Readable.from(this._buffer);
|
|
49
71
|
}
|
|
@@ -217,9 +239,6 @@ class PonyfillBody {
|
|
|
217
239
|
limits: formDataLimits,
|
|
218
240
|
defCharset: 'utf-8',
|
|
219
241
|
});
|
|
220
|
-
if (this._signal) {
|
|
221
|
-
(0, node_stream_1.addAbortSignal)(this._signal, bb);
|
|
222
|
-
}
|
|
223
242
|
let completed = false;
|
|
224
243
|
const complete = (err) => {
|
|
225
244
|
if (completed)
|
package/cjs/Request.js
CHANGED
|
@@ -76,6 +76,7 @@ class PonyfillRequest extends Body_js_1.PonyfillBody {
|
|
|
76
76
|
this.agent = requestInit.agent;
|
|
77
77
|
}
|
|
78
78
|
}
|
|
79
|
+
this._signal = requestInit?.signal || undefined;
|
|
79
80
|
}
|
|
80
81
|
headersSerializer;
|
|
81
82
|
cache;
|
|
@@ -91,6 +92,7 @@ class PonyfillRequest extends Body_js_1.PonyfillBody {
|
|
|
91
92
|
referrer;
|
|
92
93
|
referrerPolicy;
|
|
93
94
|
_url;
|
|
95
|
+
_signal;
|
|
94
96
|
get signal() {
|
|
95
97
|
this._signal ||= new AbortController().signal;
|
|
96
98
|
return this._signal;
|
package/cjs/fetchCurl.js
CHANGED
|
@@ -22,7 +22,7 @@ function fetchCurl(fetchRequest) {
|
|
|
22
22
|
}
|
|
23
23
|
curlHandle.enable(CurlFeature.StreamResponse);
|
|
24
24
|
let signal;
|
|
25
|
-
if (fetchRequest._signal
|
|
25
|
+
if (fetchRequest._signal === null) {
|
|
26
26
|
signal = undefined;
|
|
27
27
|
}
|
|
28
28
|
else if (fetchRequest._signal) {
|
|
@@ -104,12 +104,8 @@ function fetchCurl(fetchRequest) {
|
|
|
104
104
|
}
|
|
105
105
|
});
|
|
106
106
|
curlHandle.once('stream', function streamListener(stream, status, headersBuf) {
|
|
107
|
-
const
|
|
108
|
-
|
|
109
|
-
src: stream,
|
|
110
|
-
dest: passThrough,
|
|
111
|
-
signal,
|
|
112
|
-
onError: deferredPromise.reject,
|
|
107
|
+
const outputStream = stream.pipe(new node_stream_1.PassThrough(), {
|
|
108
|
+
end: true,
|
|
113
109
|
});
|
|
114
110
|
const headersFlat = headersBuf
|
|
115
111
|
.toString('utf8')
|
|
@@ -122,7 +118,7 @@ function fetchCurl(fetchRequest) {
|
|
|
122
118
|
if (!stream.destroyed) {
|
|
123
119
|
stream.resume();
|
|
124
120
|
}
|
|
125
|
-
|
|
121
|
+
outputStream.destroy();
|
|
126
122
|
deferredPromise.reject(new Error('redirect is not allowed'));
|
|
127
123
|
}
|
|
128
124
|
return true;
|
|
@@ -130,14 +126,14 @@ function fetchCurl(fetchRequest) {
|
|
|
130
126
|
return false;
|
|
131
127
|
});
|
|
132
128
|
const headersInit = headersFlat.map(headerFlat => headerFlat.split(/:\s(.+)/).slice(0, 2));
|
|
133
|
-
const ponyfillResponse = new Response_js_1.PonyfillResponse(
|
|
129
|
+
const ponyfillResponse = new Response_js_1.PonyfillResponse(outputStream, {
|
|
134
130
|
status,
|
|
135
131
|
headers: headersInit,
|
|
136
132
|
url: curlHandle.getInfo(Curl.info.REDIRECT_URL)?.toString() || fetchRequest.url,
|
|
137
133
|
redirected: Number(curlHandle.getInfo(Curl.info.REDIRECT_COUNT)) > 0,
|
|
138
134
|
});
|
|
139
135
|
deferredPromise.resolve(ponyfillResponse);
|
|
140
|
-
streamResolved =
|
|
136
|
+
streamResolved = outputStream;
|
|
141
137
|
});
|
|
142
138
|
setImmediate(() => {
|
|
143
139
|
curlHandle.perform();
|
package/cjs/fetchNodeHttp.js
CHANGED
|
@@ -92,14 +92,10 @@ function fetchNodeHttp(fetchRequest) {
|
|
|
92
92
|
return;
|
|
93
93
|
}
|
|
94
94
|
}
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
signal,
|
|
100
|
-
onError: reject,
|
|
101
|
-
});
|
|
102
|
-
}
|
|
95
|
+
outputStream ||= new node_stream_1.PassThrough();
|
|
96
|
+
nodeResponse.pipe(outputStream, {
|
|
97
|
+
end: true,
|
|
98
|
+
});
|
|
103
99
|
const statusCode = nodeResponse.statusCode || 200;
|
|
104
100
|
let statusText = nodeResponse.statusMessage || node_http_1.STATUS_CODES[statusCode];
|
|
105
101
|
if (statusText == null) {
|
package/cjs/utils.js
CHANGED
|
@@ -7,7 +7,6 @@ exports.isArrayBufferView = isArrayBufferView;
|
|
|
7
7
|
exports.isNodeReadable = isNodeReadable;
|
|
8
8
|
exports.isIterable = isIterable;
|
|
9
9
|
exports.shouldRedirect = shouldRedirect;
|
|
10
|
-
exports.pipeThrough = pipeThrough;
|
|
11
10
|
exports.endStream = endStream;
|
|
12
11
|
exports.safeWrite = safeWrite;
|
|
13
12
|
const node_events_1 = require("node:events");
|
|
@@ -49,42 +48,6 @@ function isIterable(value) {
|
|
|
49
48
|
function shouldRedirect(status) {
|
|
50
49
|
return status === 301 || status === 302 || status === 303 || status === 307 || status === 308;
|
|
51
50
|
}
|
|
52
|
-
function pipeThrough({ src, dest, signal, onError, }) {
|
|
53
|
-
if (onError) {
|
|
54
|
-
// listen for errors on the destination stream if necessary. if the readable
|
|
55
|
-
// stream (src) emits an error, the writable destination (dest) will be
|
|
56
|
-
// destroyed with that error (see below)
|
|
57
|
-
dest.once('error', onError);
|
|
58
|
-
}
|
|
59
|
-
src.once('error', (e) => {
|
|
60
|
-
// if the readable stream (src) emits an error during pipe, the writable
|
|
61
|
-
// destination (dest) is not closed automatically. that needs to be
|
|
62
|
-
// done manually. the readable stream is closed when error is emitted,
|
|
63
|
-
// so only the writable destination needs to be destroyed
|
|
64
|
-
dest.destroy(e);
|
|
65
|
-
});
|
|
66
|
-
if (signal) {
|
|
67
|
-
// this is faster than `import('node:signal').addAbortSignal(signal, src)`
|
|
68
|
-
const srcRef = new WeakRef(src);
|
|
69
|
-
const signalRef = new WeakRef(signal);
|
|
70
|
-
function cleanup() {
|
|
71
|
-
signalRef.deref()?.removeEventListener('abort', onAbort);
|
|
72
|
-
srcRef.deref()?.removeListener('end', cleanup);
|
|
73
|
-
srcRef.deref()?.removeListener('error', cleanup);
|
|
74
|
-
srcRef.deref()?.removeListener('close', cleanup);
|
|
75
|
-
}
|
|
76
|
-
function onAbort() {
|
|
77
|
-
srcRef.deref()?.destroy(new AbortError());
|
|
78
|
-
cleanup();
|
|
79
|
-
}
|
|
80
|
-
signal.addEventListener('abort', onAbort, { once: true });
|
|
81
|
-
// this is faster than `import('node:signal').finished(src, cleanup)`
|
|
82
|
-
src.once('end', cleanup);
|
|
83
|
-
src.once('error', cleanup);
|
|
84
|
-
src.once('close', cleanup);
|
|
85
|
-
}
|
|
86
|
-
src.pipe(dest, { end: true /* already default */ });
|
|
87
|
-
}
|
|
88
51
|
function endStream(stream) {
|
|
89
52
|
// @ts-expect-error Avoid arguments adaptor trampoline https://v8.dev/blog/adaptor-frame
|
|
90
53
|
return stream.end(null, null, null);
|
|
@@ -95,10 +58,3 @@ function safeWrite(chunk, stream) {
|
|
|
95
58
|
return (0, node_events_1.once)(stream, 'drain');
|
|
96
59
|
}
|
|
97
60
|
}
|
|
98
|
-
// https://github.com/nodejs/node/blob/f692878dec6354c0a82241f224906981861bc840/lib/internal/errors.js#L961-L973
|
|
99
|
-
class AbortError extends Error {
|
|
100
|
-
constructor(message = 'The operation was aborted', options = undefined) {
|
|
101
|
-
super(message, options);
|
|
102
|
-
this.name = 'AbortError';
|
|
103
|
-
}
|
|
104
|
-
}
|
package/esm/Body.js
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
/* eslint-disable @typescript-eslint/ban-ts-comment */
|
|
2
2
|
import { Buffer } from 'node:buffer';
|
|
3
|
-
import {
|
|
3
|
+
import { Readable } from 'node:stream';
|
|
4
4
|
import { Busboy } from '@fastify/busboy';
|
|
5
|
-
import { handleMaybePromise } from '@whatwg-node/promise-helpers';
|
|
5
|
+
import { handleMaybePromise, isPromise } from '@whatwg-node/promise-helpers';
|
|
6
6
|
import { hasArrayBufferMethod, hasBufferMethod, hasBytesMethod, PonyfillBlob } from './Blob.js';
|
|
7
7
|
import { PonyfillFile } from './File.js';
|
|
8
8
|
import { getStreamFromFormData, PonyfillFormData } from './FormData.js';
|
|
@@ -24,23 +24,45 @@ export class PonyfillBody {
|
|
|
24
24
|
bodyUsed = false;
|
|
25
25
|
contentType = null;
|
|
26
26
|
contentLength = null;
|
|
27
|
-
_signal = null;
|
|
28
27
|
constructor(bodyInit, options = {}) {
|
|
29
28
|
this.bodyInit = bodyInit;
|
|
30
29
|
this.options = options;
|
|
31
|
-
this._signal = options.signal || null;
|
|
32
30
|
const { bodyFactory, contentType, contentLength, bodyType, buffer } = processBodyInit(bodyInit);
|
|
33
31
|
this._bodyFactory = bodyFactory;
|
|
34
32
|
this.contentType = contentType;
|
|
35
33
|
this.contentLength = contentLength;
|
|
36
34
|
this.bodyType = bodyType;
|
|
37
35
|
this._buffer = buffer;
|
|
36
|
+
if (!buffer) {
|
|
37
|
+
this._chunks = this._doCollectChunksFromReadableJob();
|
|
38
|
+
}
|
|
38
39
|
}
|
|
39
40
|
bodyType;
|
|
40
41
|
_bodyFactory = () => null;
|
|
41
42
|
_generatedBody = null;
|
|
42
43
|
_buffer;
|
|
43
44
|
generateBody() {
|
|
45
|
+
if (!this._buffer && this._chunks) {
|
|
46
|
+
if (isPromise(this._chunks)) {
|
|
47
|
+
const chunks$ = this._chunks;
|
|
48
|
+
this._generatedBody = new PonyfillReadableStream({
|
|
49
|
+
start: controller => {
|
|
50
|
+
chunks$.then(chunks => {
|
|
51
|
+
this._buffer = Buffer.concat(chunks);
|
|
52
|
+
for (const chunk of chunks) {
|
|
53
|
+
controller.enqueue(chunk);
|
|
54
|
+
}
|
|
55
|
+
controller.close();
|
|
56
|
+
});
|
|
57
|
+
},
|
|
58
|
+
});
|
|
59
|
+
}
|
|
60
|
+
else {
|
|
61
|
+
this._buffer = Buffer.concat(this._chunks);
|
|
62
|
+
this._generatedBody = new PonyfillReadableStream(Readable.from(this._buffer));
|
|
63
|
+
}
|
|
64
|
+
return this._generatedBody;
|
|
65
|
+
}
|
|
44
66
|
if (this._generatedBody?.readable?.destroyed && this._buffer) {
|
|
45
67
|
this._generatedBody.readable = Readable.from(this._buffer);
|
|
46
68
|
}
|
|
@@ -214,9 +236,6 @@ export class PonyfillBody {
|
|
|
214
236
|
limits: formDataLimits,
|
|
215
237
|
defCharset: 'utf-8',
|
|
216
238
|
});
|
|
217
|
-
if (this._signal) {
|
|
218
|
-
addAbortSignal(this._signal, bb);
|
|
219
|
-
}
|
|
220
239
|
let completed = false;
|
|
221
240
|
const complete = (err) => {
|
|
222
241
|
if (completed)
|
package/esm/Request.js
CHANGED
|
@@ -73,6 +73,7 @@ export class PonyfillRequest extends PonyfillBody {
|
|
|
73
73
|
this.agent = requestInit.agent;
|
|
74
74
|
}
|
|
75
75
|
}
|
|
76
|
+
this._signal = requestInit?.signal || undefined;
|
|
76
77
|
}
|
|
77
78
|
headersSerializer;
|
|
78
79
|
cache;
|
|
@@ -88,6 +89,7 @@ export class PonyfillRequest extends PonyfillBody {
|
|
|
88
89
|
referrer;
|
|
89
90
|
referrerPolicy;
|
|
90
91
|
_url;
|
|
92
|
+
_signal;
|
|
91
93
|
get signal() {
|
|
92
94
|
this._signal ||= new AbortController().signal;
|
|
93
95
|
return this._signal;
|
package/esm/fetchCurl.js
CHANGED
|
@@ -2,7 +2,7 @@ import { PassThrough, Readable } from 'node:stream';
|
|
|
2
2
|
import { rootCertificates } from 'node:tls';
|
|
3
3
|
import { createDeferredPromise } from '@whatwg-node/promise-helpers';
|
|
4
4
|
import { PonyfillResponse } from './Response.js';
|
|
5
|
-
import { defaultHeadersSerializer, isNodeReadable,
|
|
5
|
+
import { defaultHeadersSerializer, isNodeReadable, shouldRedirect } from './utils.js';
|
|
6
6
|
export function fetchCurl(fetchRequest) {
|
|
7
7
|
const { Curl, CurlFeature, CurlPause, CurlProgressFunc } = globalThis['libcurl'];
|
|
8
8
|
const curlHandle = new Curl();
|
|
@@ -19,7 +19,7 @@ export function fetchCurl(fetchRequest) {
|
|
|
19
19
|
}
|
|
20
20
|
curlHandle.enable(CurlFeature.StreamResponse);
|
|
21
21
|
let signal;
|
|
22
|
-
if (fetchRequest._signal
|
|
22
|
+
if (fetchRequest._signal === null) {
|
|
23
23
|
signal = undefined;
|
|
24
24
|
}
|
|
25
25
|
else if (fetchRequest._signal) {
|
|
@@ -101,12 +101,8 @@ export function fetchCurl(fetchRequest) {
|
|
|
101
101
|
}
|
|
102
102
|
});
|
|
103
103
|
curlHandle.once('stream', function streamListener(stream, status, headersBuf) {
|
|
104
|
-
const
|
|
105
|
-
|
|
106
|
-
src: stream,
|
|
107
|
-
dest: passThrough,
|
|
108
|
-
signal,
|
|
109
|
-
onError: deferredPromise.reject,
|
|
104
|
+
const outputStream = stream.pipe(new PassThrough(), {
|
|
105
|
+
end: true,
|
|
110
106
|
});
|
|
111
107
|
const headersFlat = headersBuf
|
|
112
108
|
.toString('utf8')
|
|
@@ -119,7 +115,7 @@ export function fetchCurl(fetchRequest) {
|
|
|
119
115
|
if (!stream.destroyed) {
|
|
120
116
|
stream.resume();
|
|
121
117
|
}
|
|
122
|
-
|
|
118
|
+
outputStream.destroy();
|
|
123
119
|
deferredPromise.reject(new Error('redirect is not allowed'));
|
|
124
120
|
}
|
|
125
121
|
return true;
|
|
@@ -127,14 +123,14 @@ export function fetchCurl(fetchRequest) {
|
|
|
127
123
|
return false;
|
|
128
124
|
});
|
|
129
125
|
const headersInit = headersFlat.map(headerFlat => headerFlat.split(/:\s(.+)/).slice(0, 2));
|
|
130
|
-
const ponyfillResponse = new PonyfillResponse(
|
|
126
|
+
const ponyfillResponse = new PonyfillResponse(outputStream, {
|
|
131
127
|
status,
|
|
132
128
|
headers: headersInit,
|
|
133
129
|
url: curlHandle.getInfo(Curl.info.REDIRECT_URL)?.toString() || fetchRequest.url,
|
|
134
130
|
redirected: Number(curlHandle.getInfo(Curl.info.REDIRECT_COUNT)) > 0,
|
|
135
131
|
});
|
|
136
132
|
deferredPromise.resolve(ponyfillResponse);
|
|
137
|
-
streamResolved =
|
|
133
|
+
streamResolved = outputStream;
|
|
138
134
|
});
|
|
139
135
|
setImmediate(() => {
|
|
140
136
|
curlHandle.perform();
|
package/esm/fetchNodeHttp.js
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
import { request as httpRequest, STATUS_CODES } from 'node:http';
|
|
2
2
|
import { request as httpsRequest } from 'node:https';
|
|
3
|
-
import { Readable } from 'node:stream';
|
|
3
|
+
import { PassThrough, Readable } from 'node:stream';
|
|
4
4
|
import { createBrotliDecompress, createGunzip, createInflate, createInflateRaw } from 'node:zlib';
|
|
5
5
|
import { handleMaybePromise } from '@whatwg-node/promise-helpers';
|
|
6
6
|
import { PonyfillRequest } from './Request.js';
|
|
7
7
|
import { PonyfillResponse } from './Response.js';
|
|
8
8
|
import { PonyfillURL } from './URL.js';
|
|
9
|
-
import { endStream, getHeadersObj, isNodeReadable,
|
|
9
|
+
import { endStream, getHeadersObj, isNodeReadable, safeWrite, shouldRedirect } from './utils.js';
|
|
10
10
|
function getRequestFnForProtocol(url) {
|
|
11
11
|
if (url.startsWith('http:')) {
|
|
12
12
|
return httpRequest;
|
|
@@ -89,14 +89,10 @@ export function fetchNodeHttp(fetchRequest) {
|
|
|
89
89
|
return;
|
|
90
90
|
}
|
|
91
91
|
}
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
signal,
|
|
97
|
-
onError: reject,
|
|
98
|
-
});
|
|
99
|
-
}
|
|
92
|
+
outputStream ||= new PassThrough();
|
|
93
|
+
nodeResponse.pipe(outputStream, {
|
|
94
|
+
end: true,
|
|
95
|
+
});
|
|
100
96
|
const statusCode = nodeResponse.statusCode || 200;
|
|
101
97
|
let statusText = nodeResponse.statusMessage || STATUS_CODES[statusCode];
|
|
102
98
|
if (statusText == null) {
|
package/esm/utils.js
CHANGED
|
@@ -36,42 +36,6 @@ export function isIterable(value) {
|
|
|
36
36
|
export function shouldRedirect(status) {
|
|
37
37
|
return status === 301 || status === 302 || status === 303 || status === 307 || status === 308;
|
|
38
38
|
}
|
|
39
|
-
export function pipeThrough({ src, dest, signal, onError, }) {
|
|
40
|
-
if (onError) {
|
|
41
|
-
// listen for errors on the destination stream if necessary. if the readable
|
|
42
|
-
// stream (src) emits an error, the writable destination (dest) will be
|
|
43
|
-
// destroyed with that error (see below)
|
|
44
|
-
dest.once('error', onError);
|
|
45
|
-
}
|
|
46
|
-
src.once('error', (e) => {
|
|
47
|
-
// if the readable stream (src) emits an error during pipe, the writable
|
|
48
|
-
// destination (dest) is not closed automatically. that needs to be
|
|
49
|
-
// done manually. the readable stream is closed when error is emitted,
|
|
50
|
-
// so only the writable destination needs to be destroyed
|
|
51
|
-
dest.destroy(e);
|
|
52
|
-
});
|
|
53
|
-
if (signal) {
|
|
54
|
-
// this is faster than `import('node:signal').addAbortSignal(signal, src)`
|
|
55
|
-
const srcRef = new WeakRef(src);
|
|
56
|
-
const signalRef = new WeakRef(signal);
|
|
57
|
-
function cleanup() {
|
|
58
|
-
signalRef.deref()?.removeEventListener('abort', onAbort);
|
|
59
|
-
srcRef.deref()?.removeListener('end', cleanup);
|
|
60
|
-
srcRef.deref()?.removeListener('error', cleanup);
|
|
61
|
-
srcRef.deref()?.removeListener('close', cleanup);
|
|
62
|
-
}
|
|
63
|
-
function onAbort() {
|
|
64
|
-
srcRef.deref()?.destroy(new AbortError());
|
|
65
|
-
cleanup();
|
|
66
|
-
}
|
|
67
|
-
signal.addEventListener('abort', onAbort, { once: true });
|
|
68
|
-
// this is faster than `import('node:signal').finished(src, cleanup)`
|
|
69
|
-
src.once('end', cleanup);
|
|
70
|
-
src.once('error', cleanup);
|
|
71
|
-
src.once('close', cleanup);
|
|
72
|
-
}
|
|
73
|
-
src.pipe(dest, { end: true /* already default */ });
|
|
74
|
-
}
|
|
75
39
|
export function endStream(stream) {
|
|
76
40
|
// @ts-expect-error Avoid arguments adaptor trampoline https://v8.dev/blog/adaptor-frame
|
|
77
41
|
return stream.end(null, null, null);
|
|
@@ -82,10 +46,3 @@ export function safeWrite(chunk, stream) {
|
|
|
82
46
|
return once(stream, 'drain');
|
|
83
47
|
}
|
|
84
48
|
}
|
|
85
|
-
// https://github.com/nodejs/node/blob/f692878dec6354c0a82241f224906981861bc840/lib/internal/errors.js#L961-L973
|
|
86
|
-
class AbortError extends Error {
|
|
87
|
-
constructor(message = 'The operation was aborted', options = undefined) {
|
|
88
|
-
super(message, options);
|
|
89
|
-
this.name = 'AbortError';
|
|
90
|
-
}
|
|
91
|
-
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@whatwg-node/node-fetch",
|
|
3
|
-
"version": "0.7.23-alpha-
|
|
3
|
+
"version": "0.7.23-alpha-20250726021628-c861bb0cd6c3ada6f0e3083708b8efbc457229ab",
|
|
4
4
|
"description": "Fetch API implementation for Node",
|
|
5
5
|
"sideEffects": false,
|
|
6
6
|
"dependencies": {
|
package/typings/Body.d.cts
CHANGED
|
@@ -24,7 +24,6 @@ export declare class PonyfillBody<TJSON = any> implements Body {
|
|
|
24
24
|
bodyUsed: boolean;
|
|
25
25
|
contentType: string | null;
|
|
26
26
|
contentLength: number | null;
|
|
27
|
-
_signal?: AbortSignal | null;
|
|
28
27
|
constructor(bodyInit: BodyPonyfillInit | null, options?: PonyfillBodyOptions);
|
|
29
28
|
private bodyType?;
|
|
30
29
|
private _bodyFactory;
|
package/typings/Body.d.ts
CHANGED
|
@@ -24,7 +24,6 @@ export declare class PonyfillBody<TJSON = any> implements Body {
|
|
|
24
24
|
bodyUsed: boolean;
|
|
25
25
|
contentType: string | null;
|
|
26
26
|
contentLength: number | null;
|
|
27
|
-
_signal?: AbortSignal | null;
|
|
28
27
|
constructor(bodyInit: BodyPonyfillInit | null, options?: PonyfillBodyOptions);
|
|
29
28
|
private bodyType?;
|
|
30
29
|
private _bodyFactory;
|
package/typings/Request.d.cts
CHANGED
|
@@ -26,6 +26,7 @@ export declare class PonyfillRequest<TJSON = any> extends PonyfillBody<TJSON> im
|
|
|
26
26
|
referrer: string;
|
|
27
27
|
referrerPolicy: ReferrerPolicy;
|
|
28
28
|
_url: string | undefined;
|
|
29
|
+
_signal: AbortSignal | undefined;
|
|
29
30
|
get signal(): AbortSignal;
|
|
30
31
|
get url(): string;
|
|
31
32
|
_parsedUrl: URL | undefined;
|
package/typings/Request.d.ts
CHANGED
|
@@ -26,6 +26,7 @@ export declare class PonyfillRequest<TJSON = any> extends PonyfillBody<TJSON> im
|
|
|
26
26
|
referrer: string;
|
|
27
27
|
referrerPolicy: ReferrerPolicy;
|
|
28
28
|
_url: string | undefined;
|
|
29
|
+
_signal: AbortSignal | undefined;
|
|
29
30
|
get signal(): AbortSignal;
|
|
30
31
|
get url(): string;
|
|
31
32
|
_parsedUrl: URL | undefined;
|
package/typings/utils.d.cts
CHANGED
|
@@ -6,12 +6,6 @@ export declare function isArrayBufferView(obj: any): obj is ArrayBufferView;
|
|
|
6
6
|
export declare function isNodeReadable(obj: any): obj is Readable;
|
|
7
7
|
export declare function isIterable(value: any): value is Iterable<unknown>;
|
|
8
8
|
export declare function shouldRedirect(status?: number): boolean;
|
|
9
|
-
export declare function pipeThrough({ src, dest, signal, onError, }: {
|
|
10
|
-
src: Readable;
|
|
11
|
-
dest: Writable;
|
|
12
|
-
signal?: AbortSignal | undefined;
|
|
13
|
-
onError?: ((e: Error) => void) | undefined;
|
|
14
|
-
}): void;
|
|
15
9
|
export declare function endStream(stream: {
|
|
16
10
|
end: () => void;
|
|
17
11
|
}): void;
|
package/typings/utils.d.ts
CHANGED
|
@@ -6,12 +6,6 @@ export declare function isArrayBufferView(obj: any): obj is ArrayBufferView;
|
|
|
6
6
|
export declare function isNodeReadable(obj: any): obj is Readable;
|
|
7
7
|
export declare function isIterable(value: any): value is Iterable<unknown>;
|
|
8
8
|
export declare function shouldRedirect(status?: number): boolean;
|
|
9
|
-
export declare function pipeThrough({ src, dest, signal, onError, }: {
|
|
10
|
-
src: Readable;
|
|
11
|
-
dest: Writable;
|
|
12
|
-
signal?: AbortSignal | undefined;
|
|
13
|
-
onError?: ((e: Error) => void) | undefined;
|
|
14
|
-
}): void;
|
|
15
9
|
export declare function endStream(stream: {
|
|
16
10
|
end: () => void;
|
|
17
11
|
}): void;
|