@whatwg-node/node-fetch 0.0.1-alpha-20230117084928-a052439 → 0.0.1-alpha-20230117095738-14df726
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/AbortSignal.d.ts +2 -0
- package/index.js +89 -11
- package/index.mjs +91 -13
- package/package.json +1 -1
package/AbortSignal.d.ts
CHANGED
@@ -6,4 +6,6 @@ export declare class PonyfillAbortSignal extends EventTarget implements AbortSig
|
|
6
6
|
throwIfAborted(): void;
|
7
7
|
get onabort(): ((this: AbortSignal, ev: Event) => any) | null;
|
8
8
|
set onabort(value: ((this: AbortSignal, ev: Event) => any) | null);
|
9
|
+
abort(reason?: any): void;
|
10
|
+
static timeout(milliseconds: number): PonyfillAbortSignal;
|
9
11
|
}
|
package/index.js
CHANGED
@@ -16,7 +16,7 @@ const fs = require('fs');
|
|
16
16
|
// Will be removed after v14 reaches EOL
|
17
17
|
class PonyfillAbortError extends Error {
|
18
18
|
constructor(reason) {
|
19
|
-
super('The operation was aborted
|
19
|
+
super('The operation was aborted' + reason || '', {
|
20
20
|
cause: reason,
|
21
21
|
});
|
22
22
|
this.name = 'AbortError';
|
@@ -46,6 +46,14 @@ class PonyfillAbortSignal extends events.EventTarget {
|
|
46
46
|
}
|
47
47
|
this.addEventListener('abort', value);
|
48
48
|
}
|
49
|
+
abort(reason) {
|
50
|
+
this.dispatchEvent(new CustomEvent('abort', { detail: reason }));
|
51
|
+
}
|
52
|
+
static timeout(milliseconds) {
|
53
|
+
const signal = new PonyfillAbortSignal();
|
54
|
+
setTimeout(() => signal.abort(`Operation timed out`), milliseconds);
|
55
|
+
return signal;
|
56
|
+
}
|
49
57
|
}
|
50
58
|
|
51
59
|
// Will be removed after v14 reaches EOL
|
@@ -303,6 +311,10 @@ class PonyfillFormData {
|
|
303
311
|
controller.enqueue(Buffer.from(`\r\n--${boundary}\r\n`));
|
304
312
|
}
|
305
313
|
}
|
314
|
+
else {
|
315
|
+
controller.enqueue(Buffer.from(`\r\n--${boundary}--\r\n`));
|
316
|
+
controller.close();
|
317
|
+
}
|
306
318
|
},
|
307
319
|
});
|
308
320
|
}
|
@@ -540,6 +552,39 @@ function processBodyInit(bodyInit) {
|
|
540
552
|
body,
|
541
553
|
};
|
542
554
|
}
|
555
|
+
if ('stream' in bodyInit) {
|
556
|
+
const bodyStream = bodyInit.stream();
|
557
|
+
const body = new PonyfillReadableStream(bodyStream);
|
558
|
+
return {
|
559
|
+
contentType: bodyInit.type,
|
560
|
+
contentLength: bodyInit.size,
|
561
|
+
body,
|
562
|
+
};
|
563
|
+
}
|
564
|
+
if (bodyInit instanceof URLSearchParams) {
|
565
|
+
const contentType = 'application/x-www-form-urlencoded;charset=UTF-8';
|
566
|
+
const body = new PonyfillReadableStream(stream.Readable.from(bodyInit.toString()));
|
567
|
+
return {
|
568
|
+
bodyType: BodyInitType.String,
|
569
|
+
contentType,
|
570
|
+
contentLength: null,
|
571
|
+
body,
|
572
|
+
};
|
573
|
+
}
|
574
|
+
if ('forEach' in bodyInit) {
|
575
|
+
const formData = new PonyfillFormData();
|
576
|
+
bodyInit.forEach((value, key) => {
|
577
|
+
formData.append(key, value);
|
578
|
+
});
|
579
|
+
const boundary = Math.random().toString(36).substr(2);
|
580
|
+
const contentType = `multipart/form-data; boundary=${boundary}`;
|
581
|
+
const body = formData.stream(boundary);
|
582
|
+
return {
|
583
|
+
contentType,
|
584
|
+
contentLength: null,
|
585
|
+
body,
|
586
|
+
};
|
587
|
+
}
|
543
588
|
throw new Error('Unknown body type');
|
544
589
|
}
|
545
590
|
|
@@ -620,6 +665,7 @@ function isRequest(input) {
|
|
620
665
|
}
|
621
666
|
class PonyfillRequest extends PonyfillBody {
|
622
667
|
constructor(input, options) {
|
668
|
+
var _a;
|
623
669
|
let url;
|
624
670
|
let bodyInit = null;
|
625
671
|
let requestInit;
|
@@ -646,7 +692,7 @@ class PonyfillRequest extends PonyfillBody {
|
|
646
692
|
this.headers = new PonyfillHeaders(requestInit === null || requestInit === void 0 ? void 0 : requestInit.headers);
|
647
693
|
this.integrity = (requestInit === null || requestInit === void 0 ? void 0 : requestInit.integrity) || '';
|
648
694
|
this.keepalive = (requestInit === null || requestInit === void 0 ? void 0 : requestInit.keepalive) || true;
|
649
|
-
this.method = (requestInit === null || requestInit === void 0 ? void 0 : requestInit.method) || 'GET';
|
695
|
+
this.method = ((_a = requestInit === null || requestInit === void 0 ? void 0 : requestInit.method) === null || _a === void 0 ? void 0 : _a.toUpperCase()) || 'GET';
|
650
696
|
this.mode = (requestInit === null || requestInit === void 0 ? void 0 : requestInit.mode) || 'cors';
|
651
697
|
this.redirect = (requestInit === null || requestInit === void 0 ? void 0 : requestInit.redirect) || 'follow';
|
652
698
|
this.referrer = (requestInit === null || requestInit === void 0 ? void 0 : requestInit.referrer) || 'about:client';
|
@@ -752,9 +798,9 @@ function getResponseForFile(url$1) {
|
|
752
798
|
}
|
753
799
|
function getRequestFnForProtocol(protocol) {
|
754
800
|
switch (protocol) {
|
755
|
-
case 'http':
|
801
|
+
case 'http:':
|
756
802
|
return http.request;
|
757
|
-
case 'https':
|
803
|
+
case 'https:':
|
758
804
|
return https.request;
|
759
805
|
}
|
760
806
|
throw new Error(`Unsupported protocol: ${protocol}`);
|
@@ -767,13 +813,39 @@ function fetchPonyfill(info, init) {
|
|
767
813
|
const fetchRequest = info;
|
768
814
|
return new Promise((resolve, reject) => {
|
769
815
|
try {
|
770
|
-
const
|
771
|
-
if (protocol === '
|
772
|
-
const
|
816
|
+
const url = new URL(fetchRequest.url, 'http://localhost');
|
817
|
+
if (url.protocol === 'data:') {
|
818
|
+
const [mimeType = 'text/plain', base64FlagOrText, base64String] = url.pathname.split(',');
|
819
|
+
if (base64FlagOrText === 'base64' && base64String) {
|
820
|
+
const buffer = Buffer.from(base64String, 'base64');
|
821
|
+
const response = new PonyfillResponse(buffer, {
|
822
|
+
status: 200,
|
823
|
+
statusText: 'OK',
|
824
|
+
headers: {
|
825
|
+
'content-type': mimeType,
|
826
|
+
},
|
827
|
+
});
|
828
|
+
resolve(response);
|
829
|
+
return;
|
830
|
+
}
|
831
|
+
if (base64FlagOrText) {
|
832
|
+
const response = new PonyfillResponse(base64FlagOrText, {
|
833
|
+
status: 200,
|
834
|
+
statusText: 'OK',
|
835
|
+
headers: {
|
836
|
+
'content-type': mimeType,
|
837
|
+
},
|
838
|
+
});
|
839
|
+
resolve(response);
|
840
|
+
return;
|
841
|
+
}
|
842
|
+
}
|
843
|
+
if (url.protocol === 'file:') {
|
844
|
+
const response = getResponseForFile(url);
|
773
845
|
resolve(response);
|
774
846
|
return;
|
775
847
|
}
|
776
|
-
const requestFn = getRequestFnForProtocol(protocol);
|
848
|
+
const requestFn = getRequestFnForProtocol(url.protocol);
|
777
849
|
const nodeReadable = (fetchRequest.body != null
|
778
850
|
? 'pipe' in fetchRequest.body
|
779
851
|
? fetchRequest.body
|
@@ -782,10 +854,16 @@ function fetchPonyfill(info, init) {
|
|
782
854
|
const nodeHeaders = getHeadersObj(fetchRequest.headers);
|
783
855
|
const abortListener = function abortListener(event) {
|
784
856
|
nodeRequest.destroy();
|
785
|
-
|
857
|
+
const reason = event.detail;
|
858
|
+
if (reason instanceof Error) {
|
859
|
+
reject(reason);
|
860
|
+
}
|
861
|
+
else {
|
862
|
+
reject(new PonyfillAbortError(reason));
|
863
|
+
}
|
786
864
|
};
|
787
865
|
fetchRequest.signal.addEventListener('abort', abortListener);
|
788
|
-
const nodeRequest = requestFn(
|
866
|
+
const nodeRequest = requestFn(url, {
|
789
867
|
// signal: fetchRequest.signal will be added when v14 reaches EOL
|
790
868
|
method: fetchRequest.method,
|
791
869
|
headers: nodeHeaders,
|
@@ -799,7 +877,7 @@ function fetchPonyfill(info, init) {
|
|
799
877
|
return;
|
800
878
|
}
|
801
879
|
if (fetchRequest.redirect === 'follow') {
|
802
|
-
const redirectedUrl = new URL(nodeResponse.headers.location,
|
880
|
+
const redirectedUrl = new URL(nodeResponse.headers.location, url);
|
803
881
|
const redirectResponse$ = fetchPonyfill(redirectedUrl, info);
|
804
882
|
resolve(redirectResponse$.then(redirectResponse => {
|
805
883
|
redirectResponse.redirected = true;
|
package/index.mjs
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
import { request as request$1 } from 'http';
|
2
2
|
import { request } from 'https';
|
3
|
-
import { EventTarget, CustomEvent } from '@whatwg-node/events';
|
3
|
+
import { EventTarget, CustomEvent as CustomEvent$1 } from '@whatwg-node/events';
|
4
4
|
import { Blob } from 'buffer';
|
5
5
|
import { Readable } from 'stream';
|
6
6
|
import busboy from 'busboy';
|
@@ -10,7 +10,7 @@ import { createReadStream } from 'fs';
|
|
10
10
|
// Will be removed after v14 reaches EOL
|
11
11
|
class PonyfillAbortError extends Error {
|
12
12
|
constructor(reason) {
|
13
|
-
super('The operation was aborted
|
13
|
+
super('The operation was aborted' + reason || '', {
|
14
14
|
cause: reason,
|
15
15
|
});
|
16
16
|
this.name = 'AbortError';
|
@@ -40,6 +40,14 @@ class PonyfillAbortSignal extends EventTarget {
|
|
40
40
|
}
|
41
41
|
this.addEventListener('abort', value);
|
42
42
|
}
|
43
|
+
abort(reason) {
|
44
|
+
this.dispatchEvent(new CustomEvent('abort', { detail: reason }));
|
45
|
+
}
|
46
|
+
static timeout(milliseconds) {
|
47
|
+
const signal = new PonyfillAbortSignal();
|
48
|
+
setTimeout(() => signal.abort(`Operation timed out`), milliseconds);
|
49
|
+
return signal;
|
50
|
+
}
|
43
51
|
}
|
44
52
|
|
45
53
|
// Will be removed after v14 reaches EOL
|
@@ -48,7 +56,7 @@ class PonyfillAbortController {
|
|
48
56
|
this.signal = new PonyfillAbortSignal();
|
49
57
|
}
|
50
58
|
abort(reason) {
|
51
|
-
this.signal.dispatchEvent(new CustomEvent('abort', { detail: reason }));
|
59
|
+
this.signal.dispatchEvent(new CustomEvent$1('abort', { detail: reason }));
|
52
60
|
}
|
53
61
|
}
|
54
62
|
|
@@ -297,6 +305,10 @@ class PonyfillFormData {
|
|
297
305
|
controller.enqueue(Buffer.from(`\r\n--${boundary}\r\n`));
|
298
306
|
}
|
299
307
|
}
|
308
|
+
else {
|
309
|
+
controller.enqueue(Buffer.from(`\r\n--${boundary}--\r\n`));
|
310
|
+
controller.close();
|
311
|
+
}
|
300
312
|
},
|
301
313
|
});
|
302
314
|
}
|
@@ -534,6 +546,39 @@ function processBodyInit(bodyInit) {
|
|
534
546
|
body,
|
535
547
|
};
|
536
548
|
}
|
549
|
+
if ('stream' in bodyInit) {
|
550
|
+
const bodyStream = bodyInit.stream();
|
551
|
+
const body = new PonyfillReadableStream(bodyStream);
|
552
|
+
return {
|
553
|
+
contentType: bodyInit.type,
|
554
|
+
contentLength: bodyInit.size,
|
555
|
+
body,
|
556
|
+
};
|
557
|
+
}
|
558
|
+
if (bodyInit instanceof URLSearchParams) {
|
559
|
+
const contentType = 'application/x-www-form-urlencoded;charset=UTF-8';
|
560
|
+
const body = new PonyfillReadableStream(Readable.from(bodyInit.toString()));
|
561
|
+
return {
|
562
|
+
bodyType: BodyInitType.String,
|
563
|
+
contentType,
|
564
|
+
contentLength: null,
|
565
|
+
body,
|
566
|
+
};
|
567
|
+
}
|
568
|
+
if ('forEach' in bodyInit) {
|
569
|
+
const formData = new PonyfillFormData();
|
570
|
+
bodyInit.forEach((value, key) => {
|
571
|
+
formData.append(key, value);
|
572
|
+
});
|
573
|
+
const boundary = Math.random().toString(36).substr(2);
|
574
|
+
const contentType = `multipart/form-data; boundary=${boundary}`;
|
575
|
+
const body = formData.stream(boundary);
|
576
|
+
return {
|
577
|
+
contentType,
|
578
|
+
contentLength: null,
|
579
|
+
body,
|
580
|
+
};
|
581
|
+
}
|
537
582
|
throw new Error('Unknown body type');
|
538
583
|
}
|
539
584
|
|
@@ -614,6 +659,7 @@ function isRequest(input) {
|
|
614
659
|
}
|
615
660
|
class PonyfillRequest extends PonyfillBody {
|
616
661
|
constructor(input, options) {
|
662
|
+
var _a;
|
617
663
|
let url;
|
618
664
|
let bodyInit = null;
|
619
665
|
let requestInit;
|
@@ -640,7 +686,7 @@ class PonyfillRequest extends PonyfillBody {
|
|
640
686
|
this.headers = new PonyfillHeaders(requestInit === null || requestInit === void 0 ? void 0 : requestInit.headers);
|
641
687
|
this.integrity = (requestInit === null || requestInit === void 0 ? void 0 : requestInit.integrity) || '';
|
642
688
|
this.keepalive = (requestInit === null || requestInit === void 0 ? void 0 : requestInit.keepalive) || true;
|
643
|
-
this.method = (requestInit === null || requestInit === void 0 ? void 0 : requestInit.method) || 'GET';
|
689
|
+
this.method = ((_a = requestInit === null || requestInit === void 0 ? void 0 : requestInit.method) === null || _a === void 0 ? void 0 : _a.toUpperCase()) || 'GET';
|
644
690
|
this.mode = (requestInit === null || requestInit === void 0 ? void 0 : requestInit.mode) || 'cors';
|
645
691
|
this.redirect = (requestInit === null || requestInit === void 0 ? void 0 : requestInit.redirect) || 'follow';
|
646
692
|
this.referrer = (requestInit === null || requestInit === void 0 ? void 0 : requestInit.referrer) || 'about:client';
|
@@ -746,9 +792,9 @@ function getResponseForFile(url) {
|
|
746
792
|
}
|
747
793
|
function getRequestFnForProtocol(protocol) {
|
748
794
|
switch (protocol) {
|
749
|
-
case 'http':
|
795
|
+
case 'http:':
|
750
796
|
return request$1;
|
751
|
-
case 'https':
|
797
|
+
case 'https:':
|
752
798
|
return request;
|
753
799
|
}
|
754
800
|
throw new Error(`Unsupported protocol: ${protocol}`);
|
@@ -761,13 +807,39 @@ function fetchPonyfill(info, init) {
|
|
761
807
|
const fetchRequest = info;
|
762
808
|
return new Promise((resolve, reject) => {
|
763
809
|
try {
|
764
|
-
const
|
765
|
-
if (protocol === '
|
766
|
-
const
|
810
|
+
const url = new URL(fetchRequest.url, 'http://localhost');
|
811
|
+
if (url.protocol === 'data:') {
|
812
|
+
const [mimeType = 'text/plain', base64FlagOrText, base64String] = url.pathname.split(',');
|
813
|
+
if (base64FlagOrText === 'base64' && base64String) {
|
814
|
+
const buffer = Buffer.from(base64String, 'base64');
|
815
|
+
const response = new PonyfillResponse(buffer, {
|
816
|
+
status: 200,
|
817
|
+
statusText: 'OK',
|
818
|
+
headers: {
|
819
|
+
'content-type': mimeType,
|
820
|
+
},
|
821
|
+
});
|
822
|
+
resolve(response);
|
823
|
+
return;
|
824
|
+
}
|
825
|
+
if (base64FlagOrText) {
|
826
|
+
const response = new PonyfillResponse(base64FlagOrText, {
|
827
|
+
status: 200,
|
828
|
+
statusText: 'OK',
|
829
|
+
headers: {
|
830
|
+
'content-type': mimeType,
|
831
|
+
},
|
832
|
+
});
|
833
|
+
resolve(response);
|
834
|
+
return;
|
835
|
+
}
|
836
|
+
}
|
837
|
+
if (url.protocol === 'file:') {
|
838
|
+
const response = getResponseForFile(url);
|
767
839
|
resolve(response);
|
768
840
|
return;
|
769
841
|
}
|
770
|
-
const requestFn = getRequestFnForProtocol(protocol);
|
842
|
+
const requestFn = getRequestFnForProtocol(url.protocol);
|
771
843
|
const nodeReadable = (fetchRequest.body != null
|
772
844
|
? 'pipe' in fetchRequest.body
|
773
845
|
? fetchRequest.body
|
@@ -776,10 +848,16 @@ function fetchPonyfill(info, init) {
|
|
776
848
|
const nodeHeaders = getHeadersObj(fetchRequest.headers);
|
777
849
|
const abortListener = function abortListener(event) {
|
778
850
|
nodeRequest.destroy();
|
779
|
-
|
851
|
+
const reason = event.detail;
|
852
|
+
if (reason instanceof Error) {
|
853
|
+
reject(reason);
|
854
|
+
}
|
855
|
+
else {
|
856
|
+
reject(new PonyfillAbortError(reason));
|
857
|
+
}
|
780
858
|
};
|
781
859
|
fetchRequest.signal.addEventListener('abort', abortListener);
|
782
|
-
const nodeRequest = requestFn(
|
860
|
+
const nodeRequest = requestFn(url, {
|
783
861
|
// signal: fetchRequest.signal will be added when v14 reaches EOL
|
784
862
|
method: fetchRequest.method,
|
785
863
|
headers: nodeHeaders,
|
@@ -793,7 +871,7 @@ function fetchPonyfill(info, init) {
|
|
793
871
|
return;
|
794
872
|
}
|
795
873
|
if (fetchRequest.redirect === 'follow') {
|
796
|
-
const redirectedUrl = new URL(nodeResponse.headers.location,
|
874
|
+
const redirectedUrl = new URL(nodeResponse.headers.location, url);
|
797
875
|
const redirectResponse$ = fetchPonyfill(redirectedUrl, info);
|
798
876
|
resolve(redirectResponse$.then(redirectResponse => {
|
799
877
|
redirectResponse.redirected = true;
|
package/package.json
CHANGED