Skip to content

Commit

Permalink
deps: update undici to 6.6.2
Browse files Browse the repository at this point in the history
PR-URL: nodejs#51667
Reviewed-By: Rafael Gonzaga <rafael.nunu@hotmail.com>
Reviewed-By: Marco Ippolito <marcoippolito54@gmail.com>
Reviewed-By: Matthew Aitken <maitken033380023@gmail.com>
Reviewed-By: Matteo Collina <matteo.collina@gmail.com>
Reviewed-By: Trivikram Kamat <trivikr.dev@gmail.com>
Reviewed-By: Luigi Pinca <luigipinca@gmail.com>
Reviewed-By: Michaël Zasso <targos@protonmail.com>
  • Loading branch information
nodejs-github-bot authored and rdw-msft committed Mar 20, 2024
1 parent 3880cc3 commit f33f447
Show file tree
Hide file tree
Showing 10 changed files with 1,268 additions and 536 deletions.
3 changes: 3 additions & 0 deletions deps/undici/src/index-fetch.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,4 +14,7 @@ module.exports.FormData = require('./lib/fetch/formdata').FormData
module.exports.Headers = require('./lib/fetch/headers').Headers
module.exports.Response = require('./lib/fetch/response').Response
module.exports.Request = require('./lib/fetch/request').Request

module.exports.WebSocket = require('./lib/websocket/websocket').WebSocket

module.exports.EventSource = require('./lib/eventsource/eventsource').EventSource
33 changes: 24 additions & 9 deletions deps/undici/src/lib/fetch/formdata.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,10 @@

const { isBlobLike, toUSVString, makeIterator } = require('./util')
const { kState } = require('./symbols')
const { kEnumerableProperty } = require('../core/util')
const { File: UndiciFile, FileLike, isFileLike } = require('./file')
const { webidl } = require('./webidl')
const { Blob, File: NativeFile } = require('node:buffer')
const { File: NativeFile } = require('node:buffer')

/** @type {globalThis['File']} */
const File = NativeFile ?? UndiciFile
Expand Down Expand Up @@ -158,29 +159,32 @@ class FormData {
webidl.brandCheck(this, FormData)

return makeIterator(
() => this[kState].map(pair => [pair.name, pair.value]),
() => this[kState],
'FormData',
'key+value'
'key+value',
'name', 'value'
)
}

keys () {
webidl.brandCheck(this, FormData)

return makeIterator(
() => this[kState].map(pair => [pair.name, pair.value]),
() => this[kState],
'FormData',
'key'
'key',
'name', 'value'
)
}

values () {
webidl.brandCheck(this, FormData)

return makeIterator(
() => this[kState].map(pair => [pair.name, pair.value]),
() => this[kState],
'FormData',
'value'
'value',
'name', 'value'
)
}

Expand All @@ -200,14 +204,25 @@ class FormData {
}

for (const [key, value] of this) {
callbackFn.apply(thisArg, [value, key, this])
callbackFn.call(thisArg, value, key, this)
}
}
}

FormData.prototype[Symbol.iterator] = FormData.prototype.entries

Object.defineProperties(FormData.prototype, {
append: kEnumerableProperty,
delete: kEnumerableProperty,
get: kEnumerableProperty,
getAll: kEnumerableProperty,
has: kEnumerableProperty,
set: kEnumerableProperty,
entries: kEnumerableProperty,
keys: kEnumerableProperty,
values: kEnumerableProperty,
forEach: kEnumerableProperty,
[Symbol.iterator]: { enumerable: false },
[Symbol.toStringTag]: {
value: 'FormData',
configurable: true
Expand All @@ -225,7 +240,7 @@ function makeEntry (name, value, filename) {
// 1. Set name to the result of converting name into a scalar value string.
// "To convert a string into a scalar value string, replace any surrogates
// with U+FFFD."
// see: https://nodejs.org/dist/latest-v18.x/docs/api/buffer.html#buftostringencoding-start-end
// see: https://nodejs.org/dist/latest-v20.x/docs/api/buffer.html#buftostringencoding-start-end
name = Buffer.from(name).toString('utf8')

// 2. If value is a string, then set value to the result of converting
Expand Down
35 changes: 10 additions & 25 deletions deps/undici/src/lib/fetch/headers.js
Original file line number Diff line number Diff line change
Expand Up @@ -492,48 +492,33 @@ class Headers {
keys () {
webidl.brandCheck(this, Headers)

if (this[kGuard] === 'immutable') {
const value = this[kHeadersSortedMap]
return makeIterator(() => value, 'Headers',
'key')
}

return makeIterator(
() => [...this[kHeadersSortedMap].values()],
() => this[kHeadersSortedMap],
'Headers',
'key'
'key',
0, 1
)
}

values () {
webidl.brandCheck(this, Headers)

if (this[kGuard] === 'immutable') {
const value = this[kHeadersSortedMap]
return makeIterator(() => value, 'Headers',
'value')
}

return makeIterator(
() => [...this[kHeadersSortedMap].values()],
() => this[kHeadersSortedMap],
'Headers',
'value'
'value',
0, 1
)
}

entries () {
webidl.brandCheck(this, Headers)

if (this[kGuard] === 'immutable') {
const value = this[kHeadersSortedMap]
return makeIterator(() => value, 'Headers',
'key+value')
}

return makeIterator(
() => [...this[kHeadersSortedMap].values()],
() => this[kHeadersSortedMap],
'Headers',
'key+value'
'key+value',
0, 1
)
}

Expand All @@ -553,7 +538,7 @@ class Headers {
}

for (const [key, value] of this) {
callbackFn.apply(thisArg, [value, key, this])
callbackFn.call(thisArg, value, key, this)
}
}

Expand Down
25 changes: 16 additions & 9 deletions deps/undici/src/lib/fetch/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -1099,11 +1099,12 @@ function fetchFinale (fetchParams, response) {

const byteStream = new ReadableStream({
readableStream: transformStream.readable,
async start (controller) {
const reader = this.readableStream.getReader()

while (true) {
const { done, value } = await reader.read()
async start () {
this._bodyReader = this.readableStream.getReader()
},
async pull (controller) {
while (controller.desiredSize >= 0) {
const { done, value } = await this._bodyReader.read()

if (done) {
queueMicrotask(() => readableStreamClose(controller))
Expand All @@ -1113,6 +1114,7 @@ function fetchFinale (fetchParams, response) {
controller.enqueue(value)
}
},
queuingStrategy: new ByteLengthQueuingStrategy({ highWaterMark: 16384 }),
type: 'bytes'
})

Expand Down Expand Up @@ -1326,6 +1328,9 @@ function httpRedirectFetch (fetchParams, response) {
// https://fetch.spec.whatwg.org/#cors-non-wildcard-request-header-name
request.headersList.delete('authorization', true)

// https://fetch.spec.whatwg.org/#authentication-entries
request.headersList.delete('proxy-authorization', true)

// "Cookie" and "Host" are forbidden request-headers, which undici doesn't implement.
request.headersList.delete('cookie', true)
request.headersList.delete('host', true)
Expand Down Expand Up @@ -1901,8 +1906,8 @@ async function httpNetworkFetch (

// 11. Let pullAlgorithm be an action that resumes the ongoing fetch
// if it is suspended.
const pullAlgorithm = () => {
fetchParams.controller.resume()
const pullAlgorithm = async () => {
await fetchParams.controller.resume()
}

// 12. Let cancelAlgorithm be an algorithm that aborts fetchParams’s
Expand All @@ -1924,6 +1929,7 @@ async function httpNetworkFetch (
// cancelAlgorithm set to cancelAlgorithm.
const stream = new ReadableStream(
{
highWaterMark: 16384,
async start (controller) {
fetchParams.controller.controller = controller
},
Expand All @@ -1933,7 +1939,8 @@ async function httpNetworkFetch (
async cancel (reason) {
await cancelAlgorithm(reason)
},
type: 'bytes'
type: 'bytes',
queuingStrategy: new ByteLengthQueuingStrategy({ highWaterMark: 16384 })
}
)

Expand Down Expand Up @@ -2026,7 +2033,7 @@ async function httpNetworkFetch (

// 9. If stream doesn’t need more data ask the user agent to suspend
// the ongoing fetch.
if (!fetchParams.controller.controller.desiredSize) {
if (fetchParams.controller.controller.desiredSize <= 0) {
return
}
}
Expand Down
122 changes: 62 additions & 60 deletions deps/undici/src/lib/fetch/util.js
Original file line number Diff line number Diff line change
Expand Up @@ -739,19 +739,23 @@ const esIteratorPrototype = Object.getPrototypeOf(Object.getPrototypeOf([][Symbo

/**
* @see https://webidl.spec.whatwg.org/#dfn-iterator-prototype-object
* @param {() => unknown[]} iterator
* @param {() => unknown} iterator
* @param {string} name name of the instance
* @param {'key'|'value'|'key+value'} kind
* @param {string | number} [keyIndex]
* @param {string | number} [valueIndex]
*/
function makeIterator (iterator, name, kind) {
function makeIterator (iterator, name, kind, keyIndex = 0, valueIndex = 1) {
const object = {
index: 0,
kind,
target: iterator
}
// The [[Prototype]] internal slot of an iterator prototype object must be %IteratorPrototype%.
const iteratorObject = Object.create(esIteratorPrototype)

const i = {
next () {
Object.defineProperty(iteratorObject, 'next', {
value: function next () {
// 1. Let interface be the interface for which the iterator prototype object exists.

// 2. Let thisValue be the this value.
Expand All @@ -763,7 +767,7 @@ function makeIterator (iterator, name, kind) {

// 5. If object is not a default iterator object for interface,
// then throw a TypeError.
if (Object.getPrototypeOf(this) !== i) {
if (Object.getPrototypeOf(this) !== iteratorObject) {
throw new TypeError(
`'next' called on an object that does not implement interface ${name} Iterator.`
)
Expand All @@ -783,68 +787,66 @@ function makeIterator (iterator, name, kind) {
if (index >= len) {
return { value: undefined, done: true }
}

// 11. Let pair be the entry in values at index index.
const pair = values[index]

const { [keyIndex]: key, [valueIndex]: value } = values[index]
// 12. Set object’s index to index + 1.
object.index = index + 1

// 13. Return the iterator result for pair and kind.
return iteratorResult(pair, kind)
// https://webidl.spec.whatwg.org/#iterator-result
// 1. Let result be a value determined by the value of kind:
let result
switch (kind) {
case 'key':
// 1. Let idlKey be pair’s key.
// 2. Let key be the result of converting idlKey to an
// ECMAScript value.
// 3. result is key.
result = key
break
case 'value':
// 1. Let idlValue be pair’s value.
// 2. Let value be the result of converting idlValue to
// an ECMAScript value.
// 3. result is value.
result = value
break
case 'key+value':
// 1. Let idlKey be pair’s key.
// 2. Let idlValue be pair’s value.
// 3. Let key be the result of converting idlKey to an
// ECMAScript value.
// 4. Let value be the result of converting idlValue to
// an ECMAScript value.
// 5. Let array be ! ArrayCreate(2).
// 6. Call ! CreateDataProperty(array, "0", key).
// 7. Call ! CreateDataProperty(array, "1", value).
// 8. result is array.
result = [key, value]
break
}
// 2. Return CreateIterResultObject(result, false).
return {
value: result,
done: false
}
},
// The class string of an iterator prototype object for a given interface is the
// result of concatenating the identifier of the interface and the string " Iterator".
[Symbol.toStringTag]: `${name} Iterator`
}

// The [[Prototype]] internal slot of an iterator prototype object must be %IteratorPrototype%.
Object.setPrototypeOf(i, esIteratorPrototype)
// esIteratorPrototype needs to be the prototype of i
// which is the prototype of an empty object. Yes, it's confusing.
return Object.setPrototypeOf({}, i)
}
writable: true,
enumerable: true,
configurable: true
})

// https://webidl.spec.whatwg.org/#iterator-result
function iteratorResult (pair, kind) {
let result

// 1. Let result be a value determined by the value of kind:
switch (kind) {
case 'key': {
// 1. Let idlKey be pair’s key.
// 2. Let key be the result of converting idlKey to an
// ECMAScript value.
// 3. result is key.
result = pair[0]
break
}
case 'value': {
// 1. Let idlValue be pair’s value.
// 2. Let value be the result of converting idlValue to
// an ECMAScript value.
// 3. result is value.
result = pair[1]
break
}
case 'key+value': {
// 1. Let idlKey be pair’s key.
// 2. Let idlValue be pair’s value.
// 3. Let key be the result of converting idlKey to an
// ECMAScript value.
// 4. Let value be the result of converting idlValue to
// an ECMAScript value.
// 5. Let array be ! ArrayCreate(2).
// 6. Call ! CreateDataProperty(array, "0", key).
// 7. Call ! CreateDataProperty(array, "1", value).
// 8. result is array.
result = pair
break
}
}
// The class string of an iterator prototype object for a given interface is the
// result of concatenating the identifier of the interface and the string " Iterator".
Object.defineProperty(iteratorObject, Symbol.toStringTag, {
value: `${name} Iterator`,
writable: false,
enumerable: false,
configurable: true
})

// 2. Return CreateIterResultObject(result, false).
return { value: result, done: false }
// esIteratorPrototype needs to be the prototype of iteratorObject
// which is the prototype of an empty object. Yes, it's confusing.
return Object.create(iteratorObject)
}

/**
Expand Down
Loading

0 comments on commit f33f447

Please sign in to comment.