@whatwg-node/node-fetch 0.0.1-alpha-20221228110541-2aa6aea → 0.0.1-alpha-20221230075257-cc3a93b

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/Body.d.ts CHANGED
@@ -28,8 +28,9 @@ export declare class PonyfillBody implements Body {
28
28
  get body(): PonyfillReadableStream<Uint8Array> | null;
29
29
  arrayBuffer(): Promise<ArrayBuffer>;
30
30
  blob(): Promise<PonyfillBlob>;
31
- formData(): Promise<PonyfillFormData>;
31
+ formData(opts?: {
32
+ formDataLimits: FormDataLimits;
33
+ }): Promise<PonyfillFormData>;
32
34
  json(): Promise<any>;
33
35
  text(): Promise<string>;
34
- readable(): Readable | null;
35
36
  }
package/FormData.d.ts CHANGED
@@ -1,4 +1,5 @@
1
1
  import { PonyfillBlob } from './Blob';
2
+ import { PonyfillReadableStream } from './ReadableStream';
2
3
  export declare class PonyfillFormData implements FormData {
3
4
  private map;
4
5
  append(name: string, value: PonyfillBlob | string, fileName?: string): void;
@@ -7,6 +8,7 @@ export declare class PonyfillFormData implements FormData {
7
8
  getAll(name: string): FormDataEntryValue[];
8
9
  has(name: string): boolean;
9
10
  set(name: string, value: PonyfillBlob | string, fileName?: string): void;
10
- private getNormalizedFile;
11
+ [Symbol.iterator](): IterableIterator<[string, FormDataEntryValue]>;
11
12
  forEach(callback: (value: FormDataEntryValue, key: string, parent: this) => void): void;
13
+ stream(boundary?: string): PonyfillReadableStream<Uint8Array>;
12
14
  }
package/index.js CHANGED
@@ -95,17 +95,13 @@ class PonyfillReadableStream {
95
95
  }
96
96
  else if (underlyingSource && 'getReader' in underlyingSource) {
97
97
  let reader;
98
+ let started = false;
98
99
  this.readable = new stream.Readable({
99
- construct(callback) {
100
- try {
100
+ read() {
101
+ if (!started) {
102
+ started = true;
101
103
  reader = underlyingSource.getReader();
102
- callback(null);
103
- }
104
- catch (err) {
105
- callback(err);
106
104
  }
107
- },
108
- read() {
109
105
  reader
110
106
  .read()
111
107
  .then(({ value, done }) => {
@@ -126,23 +122,16 @@ class PonyfillReadableStream {
126
122
  });
127
123
  }
128
124
  else {
125
+ let started = false;
129
126
  this.readable = new stream.Readable({
130
- async construct(callback) {
131
- var _a;
132
- try {
133
- const controller = createController(0, this);
134
- await ((_a = underlyingSource === null || underlyingSource === void 0 ? void 0 : underlyingSource.start) === null || _a === void 0 ? void 0 : _a.call(underlyingSource, controller));
135
- controller._flush();
136
- callback(null);
137
- }
138
- catch (err) {
139
- callback(err);
140
- }
141
- },
142
127
  async read(desiredSize) {
143
- var _a;
128
+ var _a, _b;
144
129
  const controller = createController(desiredSize, this);
145
- await ((_a = underlyingSource === null || underlyingSource === void 0 ? void 0 : underlyingSource.pull) === null || _a === void 0 ? void 0 : _a.call(underlyingSource, controller));
130
+ if (!started) {
131
+ started = true;
132
+ await ((_a = underlyingSource === null || underlyingSource === void 0 ? void 0 : underlyingSource.start) === null || _a === void 0 ? void 0 : _a.call(underlyingSource, controller));
133
+ }
134
+ await ((_b = underlyingSource === null || underlyingSource === void 0 ? void 0 : underlyingSource.pull) === null || _b === void 0 ? void 0 : _b.call(underlyingSource, controller));
146
135
  controller._flush();
147
136
  },
148
137
  async destroy(err, callback) {
@@ -246,7 +235,7 @@ class PonyfillFormData {
246
235
  values = [];
247
236
  this.map.set(name, values);
248
237
  }
249
- const entry = value instanceof PonyfillBlob ? this.getNormalizedFile(name, value, fileName) : value;
238
+ const entry = value instanceof PonyfillBlob ? getNormalizedFile(name, value, fileName) : value;
250
239
  values.push(entry);
251
240
  }
252
241
  delete(name) {
@@ -263,25 +252,67 @@ class PonyfillFormData {
263
252
  return this.map.has(name);
264
253
  }
265
254
  set(name, value, fileName) {
266
- const entry = value instanceof PonyfillBlob ? this.getNormalizedFile(name, value, fileName) : value;
255
+ const entry = value instanceof PonyfillBlob ? getNormalizedFile(name, value, fileName) : value;
267
256
  this.map.set(name, [entry]);
268
257
  }
269
- getNormalizedFile(name, blob, fileName) {
270
- if (blob instanceof PonyfillFile) {
271
- if (fileName != null) {
272
- return new PonyfillFile([blob], fileName, { type: blob.type, lastModified: blob.lastModified });
258
+ *[Symbol.iterator]() {
259
+ for (const [key, values] of this.map) {
260
+ for (const value of values) {
261
+ yield [key, value];
273
262
  }
274
- return blob;
275
263
  }
276
- return new PonyfillFile([blob], fileName || name, { type: blob.type });
277
264
  }
278
265
  forEach(callback) {
279
- for (const [key, values] of this.map) {
280
- for (const value of values) {
281
- callback(value, key, this);
266
+ for (const [key, value] of this) {
267
+ callback(value, key, this);
268
+ }
269
+ }
270
+ stream(boundary = '---') {
271
+ const entries = [];
272
+ return new PonyfillReadableStream({
273
+ start: async (controller) => {
274
+ controller.enqueue(Buffer.from(`--${boundary}\r\n`));
275
+ this.forEach((value, key) => {
276
+ entries.push([key, value]);
277
+ });
278
+ },
279
+ pull: async (controller) => {
280
+ const entry = entries.shift();
281
+ if (entry) {
282
+ const [key, value] = entry;
283
+ if (value instanceof PonyfillBlob) {
284
+ let filenamePart = '';
285
+ if (value.name) {
286
+ filenamePart = `; filename="${value.name}"`;
287
+ }
288
+ controller.enqueue(Buffer.from(`Content-Disposition: form-data; name="${key}"${filenamePart}\r\n`));
289
+ controller.enqueue(Buffer.from(`Content-Type: ${value.type || 'application/octet-stream'}\r\n\r\n`));
290
+ controller.enqueue(Buffer.from(await value.arrayBuffer()));
291
+ }
292
+ else {
293
+ controller.enqueue(Buffer.from(`Content-Disposition: form-data; name="${key}"\r\n\r\n`));
294
+ controller.enqueue(Buffer.from(value));
295
+ }
296
+ if (entries.length === 0) {
297
+ controller.enqueue(Buffer.from(`\r\n--${boundary}--\r\n`));
298
+ controller.close();
299
+ }
300
+ else {
301
+ controller.enqueue(Buffer.from(`\r\n--${boundary}\r\n`));
302
+ }
303
+ }
282
304
  }
305
+ });
306
+ }
307
+ }
308
+ function getNormalizedFile(name, blob, fileName) {
309
+ if (blob instanceof PonyfillFile) {
310
+ if (fileName != null) {
311
+ return new PonyfillFile([blob], fileName, { type: blob.type, lastModified: blob.lastModified });
283
312
  }
313
+ return blob;
284
314
  }
315
+ return new PonyfillFile([blob], fileName || name, { type: blob.type });
285
316
  }
286
317
 
287
318
  var BodyInitType;
@@ -301,81 +332,11 @@ class PonyfillBody {
301
332
  this._body = null;
302
333
  this.contentType = null;
303
334
  this.contentLength = null;
304
- if (this.bodyInit == null) {
305
- this._body = null;
306
- }
307
- else if (typeof this.bodyInit === 'string') {
308
- this.bodyType = BodyInitType.String;
309
- const buffer = Buffer.from(this.bodyInit);
310
- this.contentType = 'text/plain;charset=UTF-8';
311
- this.contentLength = buffer.length;
312
- this._body = new PonyfillReadableStream(stream.Readable.from(buffer));
313
- }
314
- else if (this.bodyInit instanceof PonyfillReadableStream) {
315
- this.bodyType = BodyInitType.ReadableStream;
316
- this._body = this.bodyInit;
317
- }
318
- else if (this.bodyInit instanceof PonyfillBlob) {
319
- this.bodyType = BodyInitType.Blob;
320
- const blobStream = this.bodyInit.stream();
321
- this.contentType = this.bodyInit.type;
322
- this.contentLength = this.bodyInit.size;
323
- this._body = new PonyfillReadableStream(blobStream);
324
- }
325
- else if (this.bodyInit instanceof PonyfillFormData) {
326
- this.bodyType = BodyInitType.FormData;
327
- const boundary = Math.random().toString(36).substr(2);
328
- const formData = this.bodyInit;
329
- this.contentType = `multipart/form-data; boundary=${boundary}`;
330
- this._body = new PonyfillReadableStream({
331
- start: async (controller) => {
332
- controller.enqueue(Buffer.from(`--${boundary}\r\n`));
333
- const entries = [];
334
- formData.forEach((value, key) => {
335
- entries.push([key, value]);
336
- });
337
- for (const i in entries) {
338
- const [key, value] = entries[i];
339
- if (value instanceof PonyfillBlob) {
340
- let filenamePart = '';
341
- if (value.name) {
342
- filenamePart = `; filename="${value.name}"`;
343
- }
344
- controller.enqueue(Buffer.from(`Content-Disposition: form-data; name="${key}"${filenamePart}\r\n`));
345
- controller.enqueue(Buffer.from(`Content-Type: ${value.type || 'application/octet-stream'}\r\n\r\n`));
346
- controller.enqueue(Buffer.from(await value.arrayBuffer()));
347
- }
348
- else {
349
- controller.enqueue(Buffer.from(`Content-Disposition: form-data; name="${key}"\r\n\r\n`));
350
- controller.enqueue(Buffer.from(value));
351
- }
352
- if (Number(i) === entries.length - 1) {
353
- controller.enqueue(Buffer.from(`\r\n--${boundary}--\r\n`));
354
- }
355
- else {
356
- controller.enqueue(Buffer.from(`\r\n--${boundary}\r\n`));
357
- }
358
- }
359
- controller.close();
360
- },
361
- });
362
- }
363
- else if ('buffer' in this.bodyInit) {
364
- this.contentLength = this.bodyInit.byteLength;
365
- this._body = new PonyfillReadableStream(stream.Readable.from(this.bodyInit));
366
- }
367
- else if (this.bodyInit instanceof ArrayBuffer) {
368
- this.bodyType = BodyInitType.ArrayBuffer;
369
- this.contentLength = this.bodyInit.byteLength;
370
- this._body = new PonyfillReadableStream(stream.Readable.from(Buffer.from(this.bodyInit)));
371
- }
372
- else if (this.bodyInit instanceof stream.Readable) {
373
- this.bodyType = BodyInitType.Readable;
374
- this._body = new PonyfillReadableStream(this.bodyInit);
375
- }
376
- else {
377
- throw new Error('Unknown body type');
378
- }
335
+ const { body, contentType, contentLength, bodyType, } = processBodyInit(bodyInit);
336
+ this._body = body;
337
+ this.contentType = contentType;
338
+ this.contentLength = contentLength;
339
+ this.bodyType = bodyType;
379
340
  }
380
341
  get body() {
381
342
  if (this._body != null) {
@@ -421,7 +382,7 @@ class PonyfillBody {
421
382
  }
422
383
  return new PonyfillBlob(chunks);
423
384
  }
424
- formData() {
385
+ formData(opts) {
425
386
  if (this.bodyType === BodyInitType.FormData) {
426
387
  return Promise.resolve(this.bodyInit);
427
388
  }
@@ -429,7 +390,10 @@ class PonyfillBody {
429
390
  if (this._body == null) {
430
391
  return Promise.resolve(formData);
431
392
  }
432
- const formDataLimits = this.options.formDataLimits;
393
+ const formDataLimits = {
394
+ ...this.options.formDataLimits,
395
+ ...opts === null || opts === void 0 ? void 0 : opts.formDataLimits,
396
+ };
433
397
  return new Promise((resolve, reject) => {
434
398
  var _a;
435
399
  const bb = busboy({
@@ -493,15 +457,88 @@ class PonyfillBody {
493
457
  const blob = await this.blob();
494
458
  return blob.text();
495
459
  }
496
- readable() {
497
- if (this.bodyType === BodyInitType.Readable) {
498
- return this.bodyInit;
499
- }
500
- if (this._body != null) {
501
- return this._body.readable;
502
- }
503
- return null;
460
+ }
461
+ function processBodyInit(bodyInit) {
462
+ if (bodyInit == null) {
463
+ return {
464
+ body: null,
465
+ contentType: null,
466
+ contentLength: null,
467
+ };
504
468
  }
469
+ if (typeof bodyInit === 'string') {
470
+ const buffer = Buffer.from(bodyInit);
471
+ const readable = stream.Readable.from(buffer);
472
+ const body = new PonyfillReadableStream(readable);
473
+ return {
474
+ bodyType: BodyInitType.String,
475
+ contentType: 'text/plain;charset=UTF-8',
476
+ contentLength: buffer.length,
477
+ body,
478
+ };
479
+ }
480
+ if (bodyInit instanceof PonyfillReadableStream) {
481
+ return {
482
+ bodyType: BodyInitType.ReadableStream,
483
+ body: bodyInit,
484
+ contentType: null,
485
+ contentLength: null,
486
+ };
487
+ }
488
+ if (bodyInit instanceof PonyfillBlob) {
489
+ const readable = bodyInit.stream();
490
+ const body = new PonyfillReadableStream(readable);
491
+ return {
492
+ bodyType: BodyInitType.Blob,
493
+ contentType: bodyInit.type,
494
+ contentLength: bodyInit.size,
495
+ body,
496
+ };
497
+ }
498
+ if (bodyInit instanceof PonyfillFormData) {
499
+ const boundary = Math.random().toString(36).substr(2);
500
+ const contentType = `multipart/form-data; boundary=${boundary}`;
501
+ const body = bodyInit.stream(boundary);
502
+ return {
503
+ bodyType: BodyInitType.FormData,
504
+ contentType,
505
+ contentLength: null,
506
+ body,
507
+ };
508
+ }
509
+ if ('buffer' in bodyInit) {
510
+ const contentLength = bodyInit.byteLength;
511
+ const buffer = Buffer.from(bodyInit.buffer, bodyInit.byteOffset, bodyInit.byteLength);
512
+ const readable = stream.Readable.from(buffer);
513
+ const body = new PonyfillReadableStream(readable);
514
+ return {
515
+ contentLength,
516
+ contentType: null,
517
+ body,
518
+ };
519
+ }
520
+ if (bodyInit instanceof ArrayBuffer) {
521
+ const contentLength = bodyInit.byteLength;
522
+ const buffer = Buffer.from(bodyInit, undefined, bodyInit.byteLength);
523
+ const readable = stream.Readable.from(buffer);
524
+ const body = new PonyfillReadableStream(readable);
525
+ return {
526
+ bodyType: BodyInitType.ArrayBuffer,
527
+ contentType: null,
528
+ contentLength,
529
+ body,
530
+ };
531
+ }
532
+ if (bodyInit instanceof stream.Readable) {
533
+ const body = new PonyfillReadableStream(bodyInit);
534
+ return {
535
+ bodyType: BodyInitType.Readable,
536
+ contentType: null,
537
+ contentLength: null,
538
+ body,
539
+ };
540
+ }
541
+ throw new Error('Unknown body type');
505
542
  }
506
543
 
507
544
  class PonyfillHeaders {
@@ -522,7 +559,7 @@ class PonyfillHeaders {
522
559
  }
523
560
  else if ('get' in headersInit) {
524
561
  headersInit.forEach((value, key) => {
525
- this.set(key, value);
562
+ this.append(key, value);
526
563
  });
527
564
  }
528
565
  else {
@@ -735,7 +772,11 @@ const fetchPonyfill = (info, init) => {
735
772
  return;
736
773
  }
737
774
  const requestFn = getRequestFnForProtocol(protocol);
738
- const nodeReadable = fetchRequest.body;
775
+ const nodeReadable = (fetchRequest.body != null
776
+ ? 'pipe' in fetchRequest.body
777
+ ? fetchRequest.body
778
+ : stream.Readable.from(fetchRequest.body)
779
+ : null);
739
780
  const nodeHeaders = getHeadersObj(fetchRequest.headers);
740
781
  const abortListener = function abortListener(event) {
741
782
  nodeRequest.destroy();
@@ -746,7 +787,8 @@ const fetchPonyfill = (info, init) => {
746
787
  // signal: fetchRequest.signal will be added when v14 reaches EOL
747
788
  method: fetchRequest.method,
748
789
  headers: nodeHeaders,
749
- }, nodeResponse => {
790
+ });
791
+ nodeRequest.once('response', nodeResponse => {
750
792
  if (nodeResponse.headers.location) {
751
793
  if (fetchRequest.redirect === 'error') {
752
794
  const redirectError = new Error('Redirects are not allowed');
@@ -774,7 +816,7 @@ const fetchPonyfill = (info, init) => {
774
816
  });
775
817
  resolve(ponyfillResponse);
776
818
  });
777
- nodeRequest.on('error', reject);
819
+ nodeRequest.once('error', reject);
778
820
  if (nodeReadable) {
779
821
  nodeReadable.pipe(nodeRequest);
780
822
  }
package/index.mjs CHANGED
@@ -89,17 +89,13 @@ class PonyfillReadableStream {
89
89
  }
90
90
  else if (underlyingSource && 'getReader' in underlyingSource) {
91
91
  let reader;
92
+ let started = false;
92
93
  this.readable = new Readable({
93
- construct(callback) {
94
- try {
94
+ read() {
95
+ if (!started) {
96
+ started = true;
95
97
  reader = underlyingSource.getReader();
96
- callback(null);
97
- }
98
- catch (err) {
99
- callback(err);
100
98
  }
101
- },
102
- read() {
103
99
  reader
104
100
  .read()
105
101
  .then(({ value, done }) => {
@@ -120,23 +116,16 @@ class PonyfillReadableStream {
120
116
  });
121
117
  }
122
118
  else {
119
+ let started = false;
123
120
  this.readable = new Readable({
124
- async construct(callback) {
125
- var _a;
126
- try {
127
- const controller = createController(0, this);
128
- await ((_a = underlyingSource === null || underlyingSource === void 0 ? void 0 : underlyingSource.start) === null || _a === void 0 ? void 0 : _a.call(underlyingSource, controller));
129
- controller._flush();
130
- callback(null);
131
- }
132
- catch (err) {
133
- callback(err);
134
- }
135
- },
136
121
  async read(desiredSize) {
137
- var _a;
122
+ var _a, _b;
138
123
  const controller = createController(desiredSize, this);
139
- await ((_a = underlyingSource === null || underlyingSource === void 0 ? void 0 : underlyingSource.pull) === null || _a === void 0 ? void 0 : _a.call(underlyingSource, controller));
124
+ if (!started) {
125
+ started = true;
126
+ await ((_a = underlyingSource === null || underlyingSource === void 0 ? void 0 : underlyingSource.start) === null || _a === void 0 ? void 0 : _a.call(underlyingSource, controller));
127
+ }
128
+ await ((_b = underlyingSource === null || underlyingSource === void 0 ? void 0 : underlyingSource.pull) === null || _b === void 0 ? void 0 : _b.call(underlyingSource, controller));
140
129
  controller._flush();
141
130
  },
142
131
  async destroy(err, callback) {
@@ -240,7 +229,7 @@ class PonyfillFormData {
240
229
  values = [];
241
230
  this.map.set(name, values);
242
231
  }
243
- const entry = value instanceof PonyfillBlob ? this.getNormalizedFile(name, value, fileName) : value;
232
+ const entry = value instanceof PonyfillBlob ? getNormalizedFile(name, value, fileName) : value;
244
233
  values.push(entry);
245
234
  }
246
235
  delete(name) {
@@ -257,25 +246,67 @@ class PonyfillFormData {
257
246
  return this.map.has(name);
258
247
  }
259
248
  set(name, value, fileName) {
260
- const entry = value instanceof PonyfillBlob ? this.getNormalizedFile(name, value, fileName) : value;
249
+ const entry = value instanceof PonyfillBlob ? getNormalizedFile(name, value, fileName) : value;
261
250
  this.map.set(name, [entry]);
262
251
  }
263
- getNormalizedFile(name, blob, fileName) {
264
- if (blob instanceof PonyfillFile) {
265
- if (fileName != null) {
266
- return new PonyfillFile([blob], fileName, { type: blob.type, lastModified: blob.lastModified });
252
+ *[Symbol.iterator]() {
253
+ for (const [key, values] of this.map) {
254
+ for (const value of values) {
255
+ yield [key, value];
267
256
  }
268
- return blob;
269
257
  }
270
- return new PonyfillFile([blob], fileName || name, { type: blob.type });
271
258
  }
272
259
  forEach(callback) {
273
- for (const [key, values] of this.map) {
274
- for (const value of values) {
275
- callback(value, key, this);
260
+ for (const [key, value] of this) {
261
+ callback(value, key, this);
262
+ }
263
+ }
264
+ stream(boundary = '---') {
265
+ const entries = [];
266
+ return new PonyfillReadableStream({
267
+ start: async (controller) => {
268
+ controller.enqueue(Buffer.from(`--${boundary}\r\n`));
269
+ this.forEach((value, key) => {
270
+ entries.push([key, value]);
271
+ });
272
+ },
273
+ pull: async (controller) => {
274
+ const entry = entries.shift();
275
+ if (entry) {
276
+ const [key, value] = entry;
277
+ if (value instanceof PonyfillBlob) {
278
+ let filenamePart = '';
279
+ if (value.name) {
280
+ filenamePart = `; filename="${value.name}"`;
281
+ }
282
+ controller.enqueue(Buffer.from(`Content-Disposition: form-data; name="${key}"${filenamePart}\r\n`));
283
+ controller.enqueue(Buffer.from(`Content-Type: ${value.type || 'application/octet-stream'}\r\n\r\n`));
284
+ controller.enqueue(Buffer.from(await value.arrayBuffer()));
285
+ }
286
+ else {
287
+ controller.enqueue(Buffer.from(`Content-Disposition: form-data; name="${key}"\r\n\r\n`));
288
+ controller.enqueue(Buffer.from(value));
289
+ }
290
+ if (entries.length === 0) {
291
+ controller.enqueue(Buffer.from(`\r\n--${boundary}--\r\n`));
292
+ controller.close();
293
+ }
294
+ else {
295
+ controller.enqueue(Buffer.from(`\r\n--${boundary}\r\n`));
296
+ }
297
+ }
276
298
  }
299
+ });
300
+ }
301
+ }
302
+ function getNormalizedFile(name, blob, fileName) {
303
+ if (blob instanceof PonyfillFile) {
304
+ if (fileName != null) {
305
+ return new PonyfillFile([blob], fileName, { type: blob.type, lastModified: blob.lastModified });
277
306
  }
307
+ return blob;
278
308
  }
309
+ return new PonyfillFile([blob], fileName || name, { type: blob.type });
279
310
  }
280
311
 
281
312
  var BodyInitType;
@@ -295,81 +326,11 @@ class PonyfillBody {
295
326
  this._body = null;
296
327
  this.contentType = null;
297
328
  this.contentLength = null;
298
- if (this.bodyInit == null) {
299
- this._body = null;
300
- }
301
- else if (typeof this.bodyInit === 'string') {
302
- this.bodyType = BodyInitType.String;
303
- const buffer = Buffer.from(this.bodyInit);
304
- this.contentType = 'text/plain;charset=UTF-8';
305
- this.contentLength = buffer.length;
306
- this._body = new PonyfillReadableStream(Readable.from(buffer));
307
- }
308
- else if (this.bodyInit instanceof PonyfillReadableStream) {
309
- this.bodyType = BodyInitType.ReadableStream;
310
- this._body = this.bodyInit;
311
- }
312
- else if (this.bodyInit instanceof PonyfillBlob) {
313
- this.bodyType = BodyInitType.Blob;
314
- const blobStream = this.bodyInit.stream();
315
- this.contentType = this.bodyInit.type;
316
- this.contentLength = this.bodyInit.size;
317
- this._body = new PonyfillReadableStream(blobStream);
318
- }
319
- else if (this.bodyInit instanceof PonyfillFormData) {
320
- this.bodyType = BodyInitType.FormData;
321
- const boundary = Math.random().toString(36).substr(2);
322
- const formData = this.bodyInit;
323
- this.contentType = `multipart/form-data; boundary=${boundary}`;
324
- this._body = new PonyfillReadableStream({
325
- start: async (controller) => {
326
- controller.enqueue(Buffer.from(`--${boundary}\r\n`));
327
- const entries = [];
328
- formData.forEach((value, key) => {
329
- entries.push([key, value]);
330
- });
331
- for (const i in entries) {
332
- const [key, value] = entries[i];
333
- if (value instanceof PonyfillBlob) {
334
- let filenamePart = '';
335
- if (value.name) {
336
- filenamePart = `; filename="${value.name}"`;
337
- }
338
- controller.enqueue(Buffer.from(`Content-Disposition: form-data; name="${key}"${filenamePart}\r\n`));
339
- controller.enqueue(Buffer.from(`Content-Type: ${value.type || 'application/octet-stream'}\r\n\r\n`));
340
- controller.enqueue(Buffer.from(await value.arrayBuffer()));
341
- }
342
- else {
343
- controller.enqueue(Buffer.from(`Content-Disposition: form-data; name="${key}"\r\n\r\n`));
344
- controller.enqueue(Buffer.from(value));
345
- }
346
- if (Number(i) === entries.length - 1) {
347
- controller.enqueue(Buffer.from(`\r\n--${boundary}--\r\n`));
348
- }
349
- else {
350
- controller.enqueue(Buffer.from(`\r\n--${boundary}\r\n`));
351
- }
352
- }
353
- controller.close();
354
- },
355
- });
356
- }
357
- else if ('buffer' in this.bodyInit) {
358
- this.contentLength = this.bodyInit.byteLength;
359
- this._body = new PonyfillReadableStream(Readable.from(this.bodyInit));
360
- }
361
- else if (this.bodyInit instanceof ArrayBuffer) {
362
- this.bodyType = BodyInitType.ArrayBuffer;
363
- this.contentLength = this.bodyInit.byteLength;
364
- this._body = new PonyfillReadableStream(Readable.from(Buffer.from(this.bodyInit)));
365
- }
366
- else if (this.bodyInit instanceof Readable) {
367
- this.bodyType = BodyInitType.Readable;
368
- this._body = new PonyfillReadableStream(this.bodyInit);
369
- }
370
- else {
371
- throw new Error('Unknown body type');
372
- }
329
+ const { body, contentType, contentLength, bodyType, } = processBodyInit(bodyInit);
330
+ this._body = body;
331
+ this.contentType = contentType;
332
+ this.contentLength = contentLength;
333
+ this.bodyType = bodyType;
373
334
  }
374
335
  get body() {
375
336
  if (this._body != null) {
@@ -415,7 +376,7 @@ class PonyfillBody {
415
376
  }
416
377
  return new PonyfillBlob(chunks);
417
378
  }
418
- formData() {
379
+ formData(opts) {
419
380
  if (this.bodyType === BodyInitType.FormData) {
420
381
  return Promise.resolve(this.bodyInit);
421
382
  }
@@ -423,7 +384,10 @@ class PonyfillBody {
423
384
  if (this._body == null) {
424
385
  return Promise.resolve(formData);
425
386
  }
426
- const formDataLimits = this.options.formDataLimits;
387
+ const formDataLimits = {
388
+ ...this.options.formDataLimits,
389
+ ...opts === null || opts === void 0 ? void 0 : opts.formDataLimits,
390
+ };
427
391
  return new Promise((resolve, reject) => {
428
392
  var _a;
429
393
  const bb = busboy({
@@ -487,15 +451,88 @@ class PonyfillBody {
487
451
  const blob = await this.blob();
488
452
  return blob.text();
489
453
  }
490
- readable() {
491
- if (this.bodyType === BodyInitType.Readable) {
492
- return this.bodyInit;
493
- }
494
- if (this._body != null) {
495
- return this._body.readable;
496
- }
497
- return null;
454
+ }
455
+ function processBodyInit(bodyInit) {
456
+ if (bodyInit == null) {
457
+ return {
458
+ body: null,
459
+ contentType: null,
460
+ contentLength: null,
461
+ };
498
462
  }
463
+ if (typeof bodyInit === 'string') {
464
+ const buffer = Buffer.from(bodyInit);
465
+ const readable = Readable.from(buffer);
466
+ const body = new PonyfillReadableStream(readable);
467
+ return {
468
+ bodyType: BodyInitType.String,
469
+ contentType: 'text/plain;charset=UTF-8',
470
+ contentLength: buffer.length,
471
+ body,
472
+ };
473
+ }
474
+ if (bodyInit instanceof PonyfillReadableStream) {
475
+ return {
476
+ bodyType: BodyInitType.ReadableStream,
477
+ body: bodyInit,
478
+ contentType: null,
479
+ contentLength: null,
480
+ };
481
+ }
482
+ if (bodyInit instanceof PonyfillBlob) {
483
+ const readable = bodyInit.stream();
484
+ const body = new PonyfillReadableStream(readable);
485
+ return {
486
+ bodyType: BodyInitType.Blob,
487
+ contentType: bodyInit.type,
488
+ contentLength: bodyInit.size,
489
+ body,
490
+ };
491
+ }
492
+ if (bodyInit instanceof PonyfillFormData) {
493
+ const boundary = Math.random().toString(36).substr(2);
494
+ const contentType = `multipart/form-data; boundary=${boundary}`;
495
+ const body = bodyInit.stream(boundary);
496
+ return {
497
+ bodyType: BodyInitType.FormData,
498
+ contentType,
499
+ contentLength: null,
500
+ body,
501
+ };
502
+ }
503
+ if ('buffer' in bodyInit) {
504
+ const contentLength = bodyInit.byteLength;
505
+ const buffer = Buffer.from(bodyInit.buffer, bodyInit.byteOffset, bodyInit.byteLength);
506
+ const readable = Readable.from(buffer);
507
+ const body = new PonyfillReadableStream(readable);
508
+ return {
509
+ contentLength,
510
+ contentType: null,
511
+ body,
512
+ };
513
+ }
514
+ if (bodyInit instanceof ArrayBuffer) {
515
+ const contentLength = bodyInit.byteLength;
516
+ const buffer = Buffer.from(bodyInit, undefined, bodyInit.byteLength);
517
+ const readable = Readable.from(buffer);
518
+ const body = new PonyfillReadableStream(readable);
519
+ return {
520
+ bodyType: BodyInitType.ArrayBuffer,
521
+ contentType: null,
522
+ contentLength,
523
+ body,
524
+ };
525
+ }
526
+ if (bodyInit instanceof Readable) {
527
+ const body = new PonyfillReadableStream(bodyInit);
528
+ return {
529
+ bodyType: BodyInitType.Readable,
530
+ contentType: null,
531
+ contentLength: null,
532
+ body,
533
+ };
534
+ }
535
+ throw new Error('Unknown body type');
499
536
  }
500
537
 
501
538
  class PonyfillHeaders {
@@ -516,7 +553,7 @@ class PonyfillHeaders {
516
553
  }
517
554
  else if ('get' in headersInit) {
518
555
  headersInit.forEach((value, key) => {
519
- this.set(key, value);
556
+ this.append(key, value);
520
557
  });
521
558
  }
522
559
  else {
@@ -729,7 +766,11 @@ const fetchPonyfill = (info, init) => {
729
766
  return;
730
767
  }
731
768
  const requestFn = getRequestFnForProtocol(protocol);
732
- const nodeReadable = fetchRequest.body;
769
+ const nodeReadable = (fetchRequest.body != null
770
+ ? 'pipe' in fetchRequest.body
771
+ ? fetchRequest.body
772
+ : Readable.from(fetchRequest.body)
773
+ : null);
733
774
  const nodeHeaders = getHeadersObj(fetchRequest.headers);
734
775
  const abortListener = function abortListener(event) {
735
776
  nodeRequest.destroy();
@@ -740,7 +781,8 @@ const fetchPonyfill = (info, init) => {
740
781
  // signal: fetchRequest.signal will be added when v14 reaches EOL
741
782
  method: fetchRequest.method,
742
783
  headers: nodeHeaders,
743
- }, nodeResponse => {
784
+ });
785
+ nodeRequest.once('response', nodeResponse => {
744
786
  if (nodeResponse.headers.location) {
745
787
  if (fetchRequest.redirect === 'error') {
746
788
  const redirectError = new Error('Redirects are not allowed');
@@ -768,7 +810,7 @@ const fetchPonyfill = (info, init) => {
768
810
  });
769
811
  resolve(ponyfillResponse);
770
812
  });
771
- nodeRequest.on('error', reject);
813
+ nodeRequest.once('error', reject);
772
814
  if (nodeReadable) {
773
815
  nodeReadable.pipe(nodeRequest);
774
816
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@whatwg-node/node-fetch",
3
- "version": "0.0.1-alpha-20221228110541-2aa6aea",
3
+ "version": "0.0.1-alpha-20221230075257-cc3a93b",
4
4
  "description": "Fetch API implementation for Node",
5
5
  "sideEffects": false,
6
6
  "peerDependencies": {