diff --git a/deps/undici/src/docs/docs/api/ProxyAgent.md b/deps/undici/src/docs/docs/api/ProxyAgent.md index 17f3f4b6798bb7..a1a0d4651c82be 100644 --- a/deps/undici/src/docs/docs/api/ProxyAgent.md +++ b/deps/undici/src/docs/docs/api/ProxyAgent.md @@ -22,8 +22,9 @@ For detailed information on the parsing process and potential validation errors, * **token** `string` (optional) - It can be passed by a string of token for authentication. * **auth** `string` (**deprecated**) - Use token. * **clientFactory** `(origin: URL, opts: Object) => Dispatcher` (optional) - Default: `(origin, opts) => new Pool(origin, opts)` -* **requestTls** `BuildOptions` (optional) - Options object passed when creating the underlying socket via the connector builder for the request. See [TLS](https://nodejs.org/api/tls.html#tlsconnectoptions-callback). -* **proxyTls** `BuildOptions` (optional) - Options object passed when creating the underlying socket via the connector builder for the proxy server. See [TLS](https://nodejs.org/api/tls.html#tlsconnectoptions-callback). +* **requestTls** `BuildOptions` (optional) - Options object passed when creating the underlying socket via the connector builder for the request. It extends from [`Client#ConnectOptions`](/docs/docs/api/Client.md#parameter-connectoptions). +* **proxyTls** `BuildOptions` (optional) - Options object passed when creating the underlying socket via the connector builder for the proxy server. It extends from [`Client#ConnectOptions`](/docs/docs/api/Client.md#parameter-connectoptions). +* **proxyTunnel** `boolean` (optional) - For connections involving secure protocols, Undici will always establish a tunnel via the HTTP2 CONNECT extension. If proxyTunnel is set to true, this will occur for unsecured proxy/endpoint connections as well. Currently, there is no way to facilitate HTTP1 IP tunneling as described in https://www.rfc-editor.org/rfc/rfc9484.html#name-http-11-request. If proxyTunnel is set to false (the default), ProxyAgent connections where both the Proxy and Endpoint are unsecured will issue all requests to the Proxy, and prefix the endpoint request path with the endpoint origin address. Examples: diff --git a/deps/undici/src/index-fetch.js b/deps/undici/src/index-fetch.js index 01df32d2fb4ded..711d7e8a1e4de5 100644 --- a/deps/undici/src/index-fetch.js +++ b/deps/undici/src/index-fetch.js @@ -26,6 +26,9 @@ module.exports.createFastMessageEvent = createFastMessageEvent module.exports.EventSource = require('./lib/web/eventsource/eventsource').EventSource +const api = require('./lib/api') +const Dispatcher = require('./lib/dispatcher/dispatcher') +Object.assign(Dispatcher.prototype, api) // Expose the fetch implementation to be enabled in Node.js core via a flag module.exports.EnvHttpProxyAgent = EnvHttpProxyAgent module.exports.getGlobalDispatcher = getGlobalDispatcher diff --git a/deps/undici/src/lib/core/errors.js b/deps/undici/src/lib/core/errors.js index 9257875c1c32f4..535c7339e3900e 100644 --- a/deps/undici/src/lib/core/errors.js +++ b/deps/undici/src/lib/core/errors.js @@ -1,13 +1,21 @@ 'use strict' +const kUndiciError = Symbol.for('undici.error.UND_ERR') class UndiciError extends Error { constructor (message) { super(message) this.name = 'UndiciError' this.code = 'UND_ERR' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kUndiciError] === true + } + + [kUndiciError] = true } +const kConnectTimeoutError = Symbol.for('undici.error.UND_ERR_CONNECT_TIMEOUT') class ConnectTimeoutError extends UndiciError { constructor (message) { super(message) @@ -15,8 +23,15 @@ class ConnectTimeoutError extends UndiciError { this.message = message || 'Connect Timeout Error' this.code = 'UND_ERR_CONNECT_TIMEOUT' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kConnectTimeoutError] === true + } + + [kConnectTimeoutError] = true } +const kHeadersTimeoutError = Symbol.for('undici.error.UND_ERR_HEADERS_TIMEOUT') class HeadersTimeoutError extends UndiciError { constructor (message) { super(message) @@ -24,8 +39,15 @@ class HeadersTimeoutError extends UndiciError { this.message = message || 'Headers Timeout Error' this.code = 'UND_ERR_HEADERS_TIMEOUT' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kHeadersTimeoutError] === true + } + + [kHeadersTimeoutError] = true } +const kHeadersOverflowError = Symbol.for('undici.error.UND_ERR_HEADERS_OVERFLOW') class HeadersOverflowError extends UndiciError { constructor (message) { super(message) @@ -33,8 +55,15 @@ class HeadersOverflowError extends UndiciError { this.message = message || 'Headers Overflow Error' this.code = 'UND_ERR_HEADERS_OVERFLOW' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kHeadersOverflowError] === true + } + + [kHeadersOverflowError] = true } +const kBodyTimeoutError = Symbol.for('undici.error.UND_ERR_BODY_TIMEOUT') class BodyTimeoutError extends UndiciError { constructor (message) { super(message) @@ -42,8 +71,15 @@ class BodyTimeoutError extends UndiciError { this.message = message || 'Body Timeout Error' this.code = 'UND_ERR_BODY_TIMEOUT' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kBodyTimeoutError] === true + } + + [kBodyTimeoutError] = true } +const kResponseStatusCodeError = Symbol.for('undici.error.UND_ERR_RESPONSE_STATUS_CODE') class ResponseStatusCodeError extends UndiciError { constructor (message, statusCode, headers, body) { super(message) @@ -55,8 +91,15 @@ class ResponseStatusCodeError extends UndiciError { this.statusCode = statusCode this.headers = headers } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kResponseStatusCodeError] === true + } + + [kResponseStatusCodeError] = true } +const kInvalidArgumentError = Symbol.for('undici.error.UND_ERR_INVALID_ARG') class InvalidArgumentError extends UndiciError { constructor (message) { super(message) @@ -64,8 +107,15 @@ class InvalidArgumentError extends UndiciError { this.message = message || 'Invalid Argument Error' this.code = 'UND_ERR_INVALID_ARG' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kInvalidArgumentError] === true + } + + [kInvalidArgumentError] = true } +const kInvalidReturnValueError = Symbol.for('undici.error.UND_ERR_INVALID_RETURN_VALUE') class InvalidReturnValueError extends UndiciError { constructor (message) { super(message) @@ -73,16 +123,31 @@ class InvalidReturnValueError extends UndiciError { this.message = message || 'Invalid Return Value Error' this.code = 'UND_ERR_INVALID_RETURN_VALUE' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kInvalidReturnValueError] === true + } + + [kInvalidReturnValueError] = true } +const kAbortError = Symbol.for('undici.error.UND_ERR_ABORT') class AbortError extends UndiciError { constructor (message) { super(message) this.name = 'AbortError' this.message = message || 'The operation was aborted' + this.code = 'UND_ERR_ABORT' + } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kAbortError] === true } + + [kAbortError] = true } +const kRequestAbortedError = Symbol.for('undici.error.UND_ERR_ABORTED') class RequestAbortedError extends AbortError { constructor (message) { super(message) @@ -90,8 +155,15 @@ class RequestAbortedError extends AbortError { this.message = message || 'Request aborted' this.code = 'UND_ERR_ABORTED' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kRequestAbortedError] === true + } + + [kRequestAbortedError] = true } +const kInformationalError = Symbol.for('undici.error.UND_ERR_INFO') class InformationalError extends UndiciError { constructor (message) { super(message) @@ -99,8 +171,15 @@ class InformationalError extends UndiciError { this.message = message || 'Request information' this.code = 'UND_ERR_INFO' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kInformationalError] === true + } + + [kInformationalError] = true } +const kRequestContentLengthMismatchError = Symbol.for('undici.error.UND_ERR_REQ_CONTENT_LENGTH_MISMATCH') class RequestContentLengthMismatchError extends UndiciError { constructor (message) { super(message) @@ -108,8 +187,15 @@ class RequestContentLengthMismatchError extends UndiciError { this.message = message || 'Request body length does not match content-length header' this.code = 'UND_ERR_REQ_CONTENT_LENGTH_MISMATCH' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kRequestContentLengthMismatchError] === true + } + + [kRequestContentLengthMismatchError] = true } +const kResponseContentLengthMismatchError = Symbol.for('undici.error.UND_ERR_RES_CONTENT_LENGTH_MISMATCH') class ResponseContentLengthMismatchError extends UndiciError { constructor (message) { super(message) @@ -117,8 +203,15 @@ class ResponseContentLengthMismatchError extends UndiciError { this.message = message || 'Response body length does not match content-length header' this.code = 'UND_ERR_RES_CONTENT_LENGTH_MISMATCH' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kResponseContentLengthMismatchError] === true + } + + [kResponseContentLengthMismatchError] = true } +const kClientDestroyedError = Symbol.for('undici.error.UND_ERR_DESTROYED') class ClientDestroyedError extends UndiciError { constructor (message) { super(message) @@ -126,8 +219,15 @@ class ClientDestroyedError extends UndiciError { this.message = message || 'The client is destroyed' this.code = 'UND_ERR_DESTROYED' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kClientDestroyedError] === true + } + + [kClientDestroyedError] = true } +const kClientClosedError = Symbol.for('undici.error.UND_ERR_CLOSED') class ClientClosedError extends UndiciError { constructor (message) { super(message) @@ -135,8 +235,15 @@ class ClientClosedError extends UndiciError { this.message = message || 'The client is closed' this.code = 'UND_ERR_CLOSED' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kClientClosedError] === true + } + + [kClientClosedError] = true } +const kSocketError = Symbol.for('undici.error.UND_ERR_SOCKET') class SocketError extends UndiciError { constructor (message, socket) { super(message) @@ -145,8 +252,15 @@ class SocketError extends UndiciError { this.code = 'UND_ERR_SOCKET' this.socket = socket } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kSocketError] === true + } + + [kSocketError] = true } +const kNotSupportedError = Symbol.for('undici.error.UND_ERR_NOT_SUPPORTED') class NotSupportedError extends UndiciError { constructor (message) { super(message) @@ -154,8 +268,15 @@ class NotSupportedError extends UndiciError { this.message = message || 'Not supported error' this.code = 'UND_ERR_NOT_SUPPORTED' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kNotSupportedError] === true + } + + [kNotSupportedError] = true } +const kBalancedPoolMissingUpstreamError = Symbol.for('undici.error.UND_ERR_BPL_MISSING_UPSTREAM') class BalancedPoolMissingUpstreamError extends UndiciError { constructor (message) { super(message) @@ -163,8 +284,15 @@ class BalancedPoolMissingUpstreamError extends UndiciError { this.message = message || 'No upstream has been added to the BalancedPool' this.code = 'UND_ERR_BPL_MISSING_UPSTREAM' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kBalancedPoolMissingUpstreamError] === true + } + + [kBalancedPoolMissingUpstreamError] = true } +const kHTTPParserError = Symbol.for('undici.error.UND_ERR_HTTP_PARSER') class HTTPParserError extends Error { constructor (message, code, data) { super(message) @@ -172,8 +300,15 @@ class HTTPParserError extends Error { this.code = code ? `HPE_${code}` : undefined this.data = data ? data.toString() : undefined } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kHTTPParserError] === true + } + + [kHTTPParserError] = true } +const kResponseExceededMaxSizeError = Symbol.for('undici.error.UND_ERR_RES_EXCEEDED_MAX_SIZE') class ResponseExceededMaxSizeError extends UndiciError { constructor (message) { super(message) @@ -181,8 +316,15 @@ class ResponseExceededMaxSizeError extends UndiciError { this.message = message || 'Response content exceeded max size' this.code = 'UND_ERR_RES_EXCEEDED_MAX_SIZE' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kResponseExceededMaxSizeError] === true + } + + [kResponseExceededMaxSizeError] = true } +const kRequestRetryError = Symbol.for('undici.error.UND_ERR_REQ_RETRY') class RequestRetryError extends UndiciError { constructor (message, code, { headers, data }) { super(message) @@ -193,8 +335,15 @@ class RequestRetryError extends UndiciError { this.data = data this.headers = headers } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kRequestRetryError] === true + } + + [kRequestRetryError] = true } +const kResponseError = Symbol.for('undici.error.UND_ERR_RESPONSE') class ResponseError extends UndiciError { constructor (message, code, { headers, data }) { super(message) @@ -205,8 +354,15 @@ class ResponseError extends UndiciError { this.data = data this.headers = headers } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kResponseError] === true + } + + [kResponseError] = true } +const kSecureProxyConnectionError = Symbol.for('undici.error.UND_ERR_PRX_TLS') class SecureProxyConnectionError extends UndiciError { constructor (cause, message, options) { super(message, { cause, ...(options ?? {}) }) @@ -215,6 +371,12 @@ class SecureProxyConnectionError extends UndiciError { this.code = 'UND_ERR_PRX_TLS' this.cause = cause } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kSecureProxyConnectionError] === true + } + + [kSecureProxyConnectionError] = true } module.exports = { diff --git a/deps/undici/src/lib/dispatcher/proxy-agent.js b/deps/undici/src/lib/dispatcher/proxy-agent.js index c439d7cd555167..fed1803890923e 100644 --- a/deps/undici/src/lib/dispatcher/proxy-agent.js +++ b/deps/undici/src/lib/dispatcher/proxy-agent.js @@ -1,12 +1,13 @@ 'use strict' -const { kProxy, kClose, kDestroy, kInterceptors } = require('../core/symbols') +const { kProxy, kClose, kDestroy, kDispatch, kInterceptors } = require('../core/symbols') const { URL } = require('node:url') const Agent = require('./agent') const Pool = require('./pool') const DispatcherBase = require('./dispatcher-base') const { InvalidArgumentError, RequestAbortedError, SecureProxyConnectionError } = require('../core/errors') const buildConnector = require('../core/connect') +const Client = require('./client') const kAgent = Symbol('proxy agent') const kClient = Symbol('proxy client') @@ -14,6 +15,7 @@ const kProxyHeaders = Symbol('proxy headers') const kRequestTls = Symbol('request tls settings') const kProxyTls = Symbol('proxy tls settings') const kConnectEndpoint = Symbol('connect endpoint function') +const kTunnelProxy = Symbol('tunnel proxy') function defaultProtocolPort (protocol) { return protocol === 'https:' ? 443 : 80 @@ -25,6 +27,69 @@ function defaultFactory (origin, opts) { const noop = () => {} +function defaultAgentFactory (origin, opts) { + if (opts.connections === 1) { + return new Client(origin, opts) + } + return new Pool(origin, opts) +} + +class Http1ProxyWrapper extends DispatcherBase { + #client + + constructor (proxyUrl, { headers = {}, connect, factory }) { + super() + if (!proxyUrl) { + throw new InvalidArgumentError('Proxy URL is mandatory') + } + + this[kProxyHeaders] = headers + if (factory) { + this.#client = factory(proxyUrl, { connect }) + } else { + this.#client = new Client(proxyUrl, { connect }) + } + } + + [kDispatch] (opts, handler) { + const onHeaders = handler.onHeaders + handler.onHeaders = function (statusCode, data, resume) { + if (statusCode === 407) { + if (typeof handler.onError === 'function') { + handler.onError(new InvalidArgumentError('Proxy Authentication Required (407)')) + } + return + } + if (onHeaders) onHeaders.call(this, statusCode, data, resume) + } + + // Rewrite request as an HTTP1 Proxy request, without tunneling. + const { + origin, + path = '/', + headers = {} + } = opts + + opts.path = origin + path + + if (!('host' in headers) && !('Host' in headers)) { + const { host } = new URL(origin) + headers.host = host + } + opts.headers = { ...this[kProxyHeaders], ...headers } + + return this.#client[kDispatch](opts, handler) + } + + async [kClose] () { + return this.#client.close() + } + + async [kDestroy] (err) { + return this.#client.destroy(err) + } +} + class ProxyAgent extends DispatcherBase { constructor (opts) { super() @@ -38,6 +103,8 @@ class ProxyAgent extends DispatcherBase { throw new InvalidArgumentError('Proxy opts.clientFactory must be a function.') } + const { proxyTunnel = true } = opts + const url = this.#getUrl(opts) const { href, origin, port, protocol, username, password, hostname: proxyHostname } = url @@ -48,6 +115,7 @@ class ProxyAgent extends DispatcherBase { this[kRequestTls] = opts.requestTls this[kProxyTls] = opts.proxyTls this[kProxyHeaders] = opts.headers || {} + this[kTunnelProxy] = proxyTunnel if (opts.auth && opts.token) { throw new InvalidArgumentError('opts.auth cannot be used in combination with opts.token') @@ -62,9 +130,23 @@ class ProxyAgent extends DispatcherBase { const connect = buildConnector({ ...opts.proxyTls }) this[kConnectEndpoint] = buildConnector({ ...opts.requestTls }) + + const agentFactory = opts.factory || defaultAgentFactory + const factory = (origin, options) => { + const { protocol } = new URL(origin) + if (!this[kTunnelProxy] && protocol === 'http:' && this[kProxy].protocol === 'http:') { + return new Http1ProxyWrapper(this[kProxy].uri, { + headers: this[kProxyHeaders], + connect, + factory: agentFactory + }) + } + return agentFactory(origin, options) + } this[kClient] = clientFactory(url, { connect }) this[kAgent] = new Agent({ ...opts, + factory, connect: async (opts, callback) => { let requestedPath = opts.host if (!opts.port) { diff --git a/deps/undici/src/lib/llhttp/wasm_build_env.txt b/deps/undici/src/lib/llhttp/wasm_build_env.txt index 5ce088f4338bde..2940bf6d0c62de 100644 --- a/deps/undici/src/lib/llhttp/wasm_build_env.txt +++ b/deps/undici/src/lib/llhttp/wasm_build_env.txt @@ -1,12 +1,12 @@ -> undici@6.21.2 prebuild:wasm +> undici@6.22.0 prebuild:wasm > node build/wasm.js --prebuild > docker build --platform=linux/aarch64 -t llhttp_wasm_builder -f /Users/matteo/repos/node/deps/undici/src/build/Dockerfile /Users/matteo/repos/node/deps/undici/src -> undici@6.21.2 build:wasm +> undici@6.22.0 build:wasm > node build/wasm.js --docker > docker run --rm -t --platform=linux/aarch64 --mount type=bind,source=/Users/matteo/repos/node/deps/undici/src/lib/llhttp,target=/home/node/undici/lib/llhttp llhttp_wasm_builder node build/wasm.js diff --git a/deps/undici/src/lib/mock/mock-errors.js b/deps/undici/src/lib/mock/mock-errors.js index 5442c0e8d2c20c..3de5603c8a90e2 100644 --- a/deps/undici/src/lib/mock/mock-errors.js +++ b/deps/undici/src/lib/mock/mock-errors.js @@ -2,6 +2,11 @@ const { UndiciError } = require('../core/errors') +const kMockNotMatchedError = Symbol.for('undici.error.UND_MOCK_ERR_MOCK_NOT_MATCHED') + +/** + * The request does not match any registered mock dispatches. + */ class MockNotMatchedError extends UndiciError { constructor (message) { super(message) @@ -10,6 +15,12 @@ class MockNotMatchedError extends UndiciError { this.message = message || 'The request does not match any registered mock dispatches' this.code = 'UND_MOCK_ERR_MOCK_NOT_MATCHED' } + + static [Symbol.hasInstance] (instance) { + return instance && instance[kMockNotMatchedError] === true + } + + [kMockNotMatchedError] = true } module.exports = { diff --git a/deps/undici/src/lib/web/fetch/body.js b/deps/undici/src/lib/web/fetch/body.js index aa6e2973532eb4..b1c553d4e0ff75 100644 --- a/deps/undici/src/lib/web/fetch/body.js +++ b/deps/undici/src/lib/web/fetch/body.js @@ -162,7 +162,10 @@ function extractBody (object, keepalive = false) { } } - const chunk = textEncoder.encode(`--${boundary}--`) + // CRLF is appended to the body to function with legacy servers and match other implementations. + // https://github.com/curl/curl/blob/3434c6b46e682452973972e8313613dfa58cd690/lib/mime.c#L1029-L1030 + // https://github.com/form-data/form-data/issues/63 + const chunk = textEncoder.encode(`--${boundary}--\r\n`) blobParts.push(chunk) length += chunk.byteLength if (hasUnknownSizeValue) { @@ -293,10 +296,6 @@ function cloneBody (instance, body) { // 1. Let « out1, out2 » be the result of teeing body’s stream. const [out1, out2] = body.stream.tee() - if (hasFinalizationRegistry) { - streamRegistry.register(instance, new WeakRef(out1)) - } - // 2. Set body’s stream to out1. body.stream = out1 diff --git a/deps/undici/src/lib/web/fetch/response.js b/deps/undici/src/lib/web/fetch/response.js index 3b6af35fbed0cf..3abaa8bd6d5ef4 100644 --- a/deps/undici/src/lib/web/fetch/response.js +++ b/deps/undici/src/lib/web/fetch/response.js @@ -240,6 +240,11 @@ class Response { // 2. Let clonedResponse be the result of cloning this’s response. const clonedResponse = cloneResponse(this[kState]) + // Note: To re-register because of a new stream. + if (hasFinalizationRegistry && this[kState].body?.stream) { + streamRegistry.register(this, new WeakRef(this[kState].body.stream)) + } + // 3. Return the result of creating a Response object, given // clonedResponse, this’s headers’s guard, and this’s relevant Realm. return fromInnerResponse(clonedResponse, getHeadersGuard(this[kHeaders])) diff --git a/deps/undici/src/package.json b/deps/undici/src/package.json index d7fab14768ad0f..d6c7a3339e8dd6 100644 --- a/deps/undici/src/package.json +++ b/deps/undici/src/package.json @@ -1,6 +1,6 @@ { "name": "undici", - "version": "6.21.2", + "version": "6.22.0", "description": "An HTTP/1.1 client, written from scratch for Node.js", "homepage": "https://undici.nodejs.org", "bugs": { diff --git a/deps/undici/src/types/proxy-agent.d.ts b/deps/undici/src/types/proxy-agent.d.ts index 32e3acbdaad499..27e237c6e3b0c7 100644 --- a/deps/undici/src/types/proxy-agent.d.ts +++ b/deps/undici/src/types/proxy-agent.d.ts @@ -24,5 +24,6 @@ declare namespace ProxyAgent { requestTls?: buildConnector.BuildOptions; proxyTls?: buildConnector.BuildOptions; clientFactory?(origin: URL, opts: object): Dispatcher; + proxyTunnel?: boolean; } } diff --git a/deps/undici/undici.js b/deps/undici/undici.js index d65ffba0ff6c1c..3dca9ec26ad290 100644 --- a/deps/undici/undici.js +++ b/deps/undici/undici.js @@ -10,6 +10,7 @@ var __commonJS = (cb, mod) => function __require() { var require_errors = __commonJS({ "lib/core/errors.js"(exports2, module2) { "use strict"; + var kUndiciError = Symbol.for("undici.error.UND_ERR"); var UndiciError = class extends Error { static { __name(this, "UndiciError"); @@ -19,7 +20,12 @@ var require_errors = __commonJS({ this.name = "UndiciError"; this.code = "UND_ERR"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kUndiciError] === true; + } + [kUndiciError] = true; }; + var kConnectTimeoutError = Symbol.for("undici.error.UND_ERR_CONNECT_TIMEOUT"); var ConnectTimeoutError = class extends UndiciError { static { __name(this, "ConnectTimeoutError"); @@ -30,7 +36,12 @@ var require_errors = __commonJS({ this.message = message || "Connect Timeout Error"; this.code = "UND_ERR_CONNECT_TIMEOUT"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kConnectTimeoutError] === true; + } + [kConnectTimeoutError] = true; }; + var kHeadersTimeoutError = Symbol.for("undici.error.UND_ERR_HEADERS_TIMEOUT"); var HeadersTimeoutError = class extends UndiciError { static { __name(this, "HeadersTimeoutError"); @@ -41,7 +52,12 @@ var require_errors = __commonJS({ this.message = message || "Headers Timeout Error"; this.code = "UND_ERR_HEADERS_TIMEOUT"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kHeadersTimeoutError] === true; + } + [kHeadersTimeoutError] = true; }; + var kHeadersOverflowError = Symbol.for("undici.error.UND_ERR_HEADERS_OVERFLOW"); var HeadersOverflowError = class extends UndiciError { static { __name(this, "HeadersOverflowError"); @@ -52,7 +68,12 @@ var require_errors = __commonJS({ this.message = message || "Headers Overflow Error"; this.code = "UND_ERR_HEADERS_OVERFLOW"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kHeadersOverflowError] === true; + } + [kHeadersOverflowError] = true; }; + var kBodyTimeoutError = Symbol.for("undici.error.UND_ERR_BODY_TIMEOUT"); var BodyTimeoutError = class extends UndiciError { static { __name(this, "BodyTimeoutError"); @@ -63,7 +84,12 @@ var require_errors = __commonJS({ this.message = message || "Body Timeout Error"; this.code = "UND_ERR_BODY_TIMEOUT"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kBodyTimeoutError] === true; + } + [kBodyTimeoutError] = true; }; + var kResponseStatusCodeError = Symbol.for("undici.error.UND_ERR_RESPONSE_STATUS_CODE"); var ResponseStatusCodeError = class extends UndiciError { static { __name(this, "ResponseStatusCodeError"); @@ -78,7 +104,12 @@ var require_errors = __commonJS({ this.statusCode = statusCode; this.headers = headers; } + static [Symbol.hasInstance](instance) { + return instance && instance[kResponseStatusCodeError] === true; + } + [kResponseStatusCodeError] = true; }; + var kInvalidArgumentError = Symbol.for("undici.error.UND_ERR_INVALID_ARG"); var InvalidArgumentError = class extends UndiciError { static { __name(this, "InvalidArgumentError"); @@ -89,7 +120,12 @@ var require_errors = __commonJS({ this.message = message || "Invalid Argument Error"; this.code = "UND_ERR_INVALID_ARG"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kInvalidArgumentError] === true; + } + [kInvalidArgumentError] = true; }; + var kInvalidReturnValueError = Symbol.for("undici.error.UND_ERR_INVALID_RETURN_VALUE"); var InvalidReturnValueError = class extends UndiciError { static { __name(this, "InvalidReturnValueError"); @@ -100,7 +136,12 @@ var require_errors = __commonJS({ this.message = message || "Invalid Return Value Error"; this.code = "UND_ERR_INVALID_RETURN_VALUE"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kInvalidReturnValueError] === true; + } + [kInvalidReturnValueError] = true; }; + var kAbortError = Symbol.for("undici.error.UND_ERR_ABORT"); var AbortError = class extends UndiciError { static { __name(this, "AbortError"); @@ -109,8 +150,14 @@ var require_errors = __commonJS({ super(message); this.name = "AbortError"; this.message = message || "The operation was aborted"; + this.code = "UND_ERR_ABORT"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kAbortError] === true; + } + [kAbortError] = true; }; + var kRequestAbortedError = Symbol.for("undici.error.UND_ERR_ABORTED"); var RequestAbortedError = class extends AbortError { static { __name(this, "RequestAbortedError"); @@ -121,7 +168,12 @@ var require_errors = __commonJS({ this.message = message || "Request aborted"; this.code = "UND_ERR_ABORTED"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kRequestAbortedError] === true; + } + [kRequestAbortedError] = true; }; + var kInformationalError = Symbol.for("undici.error.UND_ERR_INFO"); var InformationalError = class extends UndiciError { static { __name(this, "InformationalError"); @@ -132,7 +184,12 @@ var require_errors = __commonJS({ this.message = message || "Request information"; this.code = "UND_ERR_INFO"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kInformationalError] === true; + } + [kInformationalError] = true; }; + var kRequestContentLengthMismatchError = Symbol.for("undici.error.UND_ERR_REQ_CONTENT_LENGTH_MISMATCH"); var RequestContentLengthMismatchError = class extends UndiciError { static { __name(this, "RequestContentLengthMismatchError"); @@ -143,7 +200,12 @@ var require_errors = __commonJS({ this.message = message || "Request body length does not match content-length header"; this.code = "UND_ERR_REQ_CONTENT_LENGTH_MISMATCH"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kRequestContentLengthMismatchError] === true; + } + [kRequestContentLengthMismatchError] = true; }; + var kResponseContentLengthMismatchError = Symbol.for("undici.error.UND_ERR_RES_CONTENT_LENGTH_MISMATCH"); var ResponseContentLengthMismatchError = class extends UndiciError { static { __name(this, "ResponseContentLengthMismatchError"); @@ -154,7 +216,12 @@ var require_errors = __commonJS({ this.message = message || "Response body length does not match content-length header"; this.code = "UND_ERR_RES_CONTENT_LENGTH_MISMATCH"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kResponseContentLengthMismatchError] === true; + } + [kResponseContentLengthMismatchError] = true; }; + var kClientDestroyedError = Symbol.for("undici.error.UND_ERR_DESTROYED"); var ClientDestroyedError = class extends UndiciError { static { __name(this, "ClientDestroyedError"); @@ -165,7 +232,12 @@ var require_errors = __commonJS({ this.message = message || "The client is destroyed"; this.code = "UND_ERR_DESTROYED"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kClientDestroyedError] === true; + } + [kClientDestroyedError] = true; }; + var kClientClosedError = Symbol.for("undici.error.UND_ERR_CLOSED"); var ClientClosedError = class extends UndiciError { static { __name(this, "ClientClosedError"); @@ -176,7 +248,12 @@ var require_errors = __commonJS({ this.message = message || "The client is closed"; this.code = "UND_ERR_CLOSED"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kClientClosedError] === true; + } + [kClientClosedError] = true; }; + var kSocketError = Symbol.for("undici.error.UND_ERR_SOCKET"); var SocketError = class extends UndiciError { static { __name(this, "SocketError"); @@ -188,7 +265,12 @@ var require_errors = __commonJS({ this.code = "UND_ERR_SOCKET"; this.socket = socket; } + static [Symbol.hasInstance](instance) { + return instance && instance[kSocketError] === true; + } + [kSocketError] = true; }; + var kNotSupportedError = Symbol.for("undici.error.UND_ERR_NOT_SUPPORTED"); var NotSupportedError = class extends UndiciError { static { __name(this, "NotSupportedError"); @@ -199,7 +281,12 @@ var require_errors = __commonJS({ this.message = message || "Not supported error"; this.code = "UND_ERR_NOT_SUPPORTED"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kNotSupportedError] === true; + } + [kNotSupportedError] = true; }; + var kBalancedPoolMissingUpstreamError = Symbol.for("undici.error.UND_ERR_BPL_MISSING_UPSTREAM"); var BalancedPoolMissingUpstreamError = class extends UndiciError { static { __name(this, "BalancedPoolMissingUpstreamError"); @@ -210,7 +297,12 @@ var require_errors = __commonJS({ this.message = message || "No upstream has been added to the BalancedPool"; this.code = "UND_ERR_BPL_MISSING_UPSTREAM"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kBalancedPoolMissingUpstreamError] === true; + } + [kBalancedPoolMissingUpstreamError] = true; }; + var kHTTPParserError = Symbol.for("undici.error.UND_ERR_HTTP_PARSER"); var HTTPParserError = class extends Error { static { __name(this, "HTTPParserError"); @@ -221,7 +313,12 @@ var require_errors = __commonJS({ this.code = code ? `HPE_${code}` : void 0; this.data = data ? data.toString() : void 0; } + static [Symbol.hasInstance](instance) { + return instance && instance[kHTTPParserError] === true; + } + [kHTTPParserError] = true; }; + var kResponseExceededMaxSizeError = Symbol.for("undici.error.UND_ERR_RES_EXCEEDED_MAX_SIZE"); var ResponseExceededMaxSizeError = class extends UndiciError { static { __name(this, "ResponseExceededMaxSizeError"); @@ -232,7 +329,12 @@ var require_errors = __commonJS({ this.message = message || "Response content exceeded max size"; this.code = "UND_ERR_RES_EXCEEDED_MAX_SIZE"; } + static [Symbol.hasInstance](instance) { + return instance && instance[kResponseExceededMaxSizeError] === true; + } + [kResponseExceededMaxSizeError] = true; }; + var kRequestRetryError = Symbol.for("undici.error.UND_ERR_REQ_RETRY"); var RequestRetryError = class extends UndiciError { static { __name(this, "RequestRetryError"); @@ -246,7 +348,12 @@ var require_errors = __commonJS({ this.data = data; this.headers = headers; } + static [Symbol.hasInstance](instance) { + return instance && instance[kRequestRetryError] === true; + } + [kRequestRetryError] = true; }; + var kResponseError = Symbol.for("undici.error.UND_ERR_RESPONSE"); var ResponseError = class extends UndiciError { static { __name(this, "ResponseError"); @@ -260,7 +367,12 @@ var require_errors = __commonJS({ this.data = data; this.headers = headers; } + static [Symbol.hasInstance](instance) { + return instance && instance[kResponseError] === true; + } + [kResponseError] = true; }; + var kSecureProxyConnectionError = Symbol.for("undici.error.UND_ERR_PRX_TLS"); var SecureProxyConnectionError = class extends UndiciError { static { __name(this, "SecureProxyConnectionError"); @@ -272,6 +384,10 @@ var require_errors = __commonJS({ this.code = "UND_ERR_PRX_TLS"; this.cause = cause; } + static [Symbol.hasInstance](instance) { + return instance && instance[kSecureProxyConnectionError] === true; + } + [kSecureProxyConnectionError] = true; }; module2.exports = { AbortError, @@ -379,7 +495,7 @@ var require_dispatcher = __commonJS({ "lib/dispatcher/dispatcher.js"(exports2, module2) { "use strict"; var EventEmitter = require("node:events"); - var Dispatcher = class extends EventEmitter { + var Dispatcher2 = class extends EventEmitter { static { __name(this, "Dispatcher"); } @@ -410,7 +526,7 @@ var require_dispatcher = __commonJS({ return new ComposedDispatcher(this, dispatch); } }; - var ComposedDispatcher = class extends Dispatcher { + var ComposedDispatcher = class extends Dispatcher2 { static { __name(this, "ComposedDispatcher"); } @@ -431,7 +547,7 @@ var require_dispatcher = __commonJS({ return this.#dispatcher.destroy(...args); } }; - module2.exports = Dispatcher; + module2.exports = Dispatcher2; } }); @@ -439,7 +555,7 @@ var require_dispatcher = __commonJS({ var require_dispatcher_base = __commonJS({ "lib/dispatcher/dispatcher-base.js"(exports2, module2) { "use strict"; - var Dispatcher = require_dispatcher(); + var Dispatcher2 = require_dispatcher(); var { ClientDestroyedError, ClientClosedError, @@ -449,7 +565,7 @@ var require_dispatcher_base = __commonJS({ var kOnDestroyed = Symbol("onDestroyed"); var kOnClosed = Symbol("onClosed"); var kInterceptedDispatch = Symbol("Intercepted Dispatch"); - var DispatcherBase = class extends Dispatcher { + var DispatcherBase = class extends Dispatcher2 { static { __name(this, "DispatcherBase"); } @@ -5543,7 +5659,8 @@ Content-Type: ${value.type || "application/octet-stream"}\r } } } - const chunk = textEncoder.encode(`--${boundary}--`); + const chunk = textEncoder.encode(`--${boundary}--\r +`); blobParts.push(chunk); length += chunk.byteLength; if (hasUnknownSizeValue) { @@ -5623,9 +5740,6 @@ Content-Type: ${value.type || "application/octet-stream"}\r __name(safelyExtractBody, "safelyExtractBody"); function cloneBody(instance, body) { const [out1, out2] = body.stream.tee(); - if (hasFinalizationRegistry) { - streamRegistry.register(instance, new WeakRef(out1)); - } body.stream = out1; return { stream: out2, @@ -8287,19 +8401,21 @@ var require_global2 = __commonJS({ var require_proxy_agent = __commonJS({ "lib/dispatcher/proxy-agent.js"(exports2, module2) { "use strict"; - var { kProxy, kClose, kDestroy, kInterceptors } = require_symbols(); + var { kProxy, kClose, kDestroy, kDispatch, kInterceptors } = require_symbols(); var { URL: URL2 } = require("node:url"); var Agent = require_agent(); var Pool = require_pool(); var DispatcherBase = require_dispatcher_base(); var { InvalidArgumentError, RequestAbortedError, SecureProxyConnectionError } = require_errors(); var buildConnector = require_connect(); + var Client = require_client(); var kAgent = Symbol("proxy agent"); var kClient = Symbol("proxy client"); var kProxyHeaders = Symbol("proxy headers"); var kRequestTls = Symbol("request tls settings"); var kProxyTls = Symbol("proxy tls settings"); var kConnectEndpoint = Symbol("connect endpoint function"); + var kTunnelProxy = Symbol("tunnel proxy"); function defaultProtocolPort(protocol) { return protocol === "https:" ? 443 : 80; } @@ -8310,6 +8426,62 @@ var require_proxy_agent = __commonJS({ __name(defaultFactory, "defaultFactory"); var noop = /* @__PURE__ */ __name(() => { }, "noop"); + function defaultAgentFactory(origin, opts) { + if (opts.connections === 1) { + return new Client(origin, opts); + } + return new Pool(origin, opts); + } + __name(defaultAgentFactory, "defaultAgentFactory"); + var Http1ProxyWrapper = class extends DispatcherBase { + static { + __name(this, "Http1ProxyWrapper"); + } + #client; + constructor(proxyUrl, { headers = {}, connect, factory }) { + super(); + if (!proxyUrl) { + throw new InvalidArgumentError("Proxy URL is mandatory"); + } + this[kProxyHeaders] = headers; + if (factory) { + this.#client = factory(proxyUrl, { connect }); + } else { + this.#client = new Client(proxyUrl, { connect }); + } + } + [kDispatch](opts, handler) { + const onHeaders = handler.onHeaders; + handler.onHeaders = function(statusCode, data, resume) { + if (statusCode === 407) { + if (typeof handler.onError === "function") { + handler.onError(new InvalidArgumentError("Proxy Authentication Required (407)")); + } + return; + } + if (onHeaders) + onHeaders.call(this, statusCode, data, resume); + }; + const { + origin, + path = "/", + headers = {} + } = opts; + opts.path = origin + path; + if (!("host" in headers) && !("Host" in headers)) { + const { host } = new URL2(origin); + headers.host = host; + } + opts.headers = { ...this[kProxyHeaders], ...headers }; + return this.#client[kDispatch](opts, handler); + } + async [kClose]() { + return this.#client.close(); + } + async [kDestroy](err) { + return this.#client.destroy(err); + } + }; var ProxyAgent = class extends DispatcherBase { static { __name(this, "ProxyAgent"); @@ -8323,6 +8495,7 @@ var require_proxy_agent = __commonJS({ if (typeof clientFactory !== "function") { throw new InvalidArgumentError("Proxy opts.clientFactory must be a function."); } + const { proxyTunnel = true } = opts; const url = this.#getUrl(opts); const { href, origin, port, protocol, username, password, hostname: proxyHostname } = url; this[kProxy] = { uri: href, protocol }; @@ -8330,6 +8503,7 @@ var require_proxy_agent = __commonJS({ this[kRequestTls] = opts.requestTls; this[kProxyTls] = opts.proxyTls; this[kProxyHeaders] = opts.headers || {}; + this[kTunnelProxy] = proxyTunnel; if (opts.auth && opts.token) { throw new InvalidArgumentError("opts.auth cannot be used in combination with opts.token"); } else if (opts.auth) { @@ -8341,9 +8515,22 @@ var require_proxy_agent = __commonJS({ } const connect = buildConnector({ ...opts.proxyTls }); this[kConnectEndpoint] = buildConnector({ ...opts.requestTls }); + const agentFactory = opts.factory || defaultAgentFactory; + const factory = /* @__PURE__ */ __name((origin2, options) => { + const { protocol: protocol2 } = new URL2(origin2); + if (!this[kTunnelProxy] && protocol2 === "http:" && this[kProxy].protocol === "http:") { + return new Http1ProxyWrapper(this[kProxy].uri, { + headers: this[kProxyHeaders], + connect, + factory: agentFactory + }); + } + return agentFactory(origin2, options); + }, "factory"); this[kClient] = clientFactory(url, { connect }); this[kAgent] = new Agent({ ...opts, + factory, connect: async (opts2, callback) => { let requestedPath = opts2.host; if (!opts2.port) { @@ -9195,6 +9382,9 @@ var require_response = __commonJS({ }); } const clonedResponse = cloneResponse(this[kState]); + if (hasFinalizationRegistry && this[kState].body?.stream) { + streamRegistry.register(this, new WeakRef(this[kState].body.stream)); + } return fromInnerResponse(clonedResponse, getHeadersGuard(this[kHeaders])); } [nodeUtil.inspect.custom](depth, options) { @@ -13500,6 +13690,1206 @@ var require_eventsource = __commonJS({ } }); +// lib/api/readable.js +var require_readable = __commonJS({ + "lib/api/readable.js"(exports2, module2) { + "use strict"; + var assert = require("node:assert"); + var { Readable } = require("node:stream"); + var { RequestAbortedError, NotSupportedError, InvalidArgumentError, AbortError } = require_errors(); + var util = require_util(); + var { ReadableStreamFrom } = require_util(); + var kConsume = Symbol("kConsume"); + var kReading = Symbol("kReading"); + var kBody = Symbol("kBody"); + var kAbort = Symbol("kAbort"); + var kContentType = Symbol("kContentType"); + var kContentLength = Symbol("kContentLength"); + var noop = /* @__PURE__ */ __name(() => { + }, "noop"); + var BodyReadable = class extends Readable { + static { + __name(this, "BodyReadable"); + } + constructor({ + resume, + abort, + contentType = "", + contentLength, + highWaterMark = 64 * 1024 + // Same as nodejs fs streams. + }) { + super({ + autoDestroy: true, + read: resume, + highWaterMark + }); + this._readableState.dataEmitted = false; + this[kAbort] = abort; + this[kConsume] = null; + this[kBody] = null; + this[kContentType] = contentType; + this[kContentLength] = contentLength; + this[kReading] = false; + } + destroy(err) { + if (!err && !this._readableState.endEmitted) { + err = new RequestAbortedError(); + } + if (err) { + this[kAbort](); + } + return super.destroy(err); + } + _destroy(err, callback) { + if (!this[kReading]) { + setImmediate(() => { + callback(err); + }); + } else { + callback(err); + } + } + on(ev, ...args) { + if (ev === "data" || ev === "readable") { + this[kReading] = true; + } + return super.on(ev, ...args); + } + addListener(ev, ...args) { + return this.on(ev, ...args); + } + off(ev, ...args) { + const ret = super.off(ev, ...args); + if (ev === "data" || ev === "readable") { + this[kReading] = this.listenerCount("data") > 0 || this.listenerCount("readable") > 0; + } + return ret; + } + removeListener(ev, ...args) { + return this.off(ev, ...args); + } + push(chunk) { + if (this[kConsume] && chunk !== null) { + consumePush(this[kConsume], chunk); + return this[kReading] ? super.push(chunk) : true; + } + return super.push(chunk); + } + // https://fetch.spec.whatwg.org/#dom-body-text + async text() { + return consume(this, "text"); + } + // https://fetch.spec.whatwg.org/#dom-body-json + async json() { + return consume(this, "json"); + } + // https://fetch.spec.whatwg.org/#dom-body-blob + async blob() { + return consume(this, "blob"); + } + // https://fetch.spec.whatwg.org/#dom-body-bytes + async bytes() { + return consume(this, "bytes"); + } + // https://fetch.spec.whatwg.org/#dom-body-arraybuffer + async arrayBuffer() { + return consume(this, "arrayBuffer"); + } + // https://fetch.spec.whatwg.org/#dom-body-formdata + async formData() { + throw new NotSupportedError(); + } + // https://fetch.spec.whatwg.org/#dom-body-bodyused + get bodyUsed() { + return util.isDisturbed(this); + } + // https://fetch.spec.whatwg.org/#dom-body-body + get body() { + if (!this[kBody]) { + this[kBody] = ReadableStreamFrom(this); + if (this[kConsume]) { + this[kBody].getReader(); + assert(this[kBody].locked); + } + } + return this[kBody]; + } + async dump(opts) { + let limit = Number.isFinite(opts?.limit) ? opts.limit : 128 * 1024; + const signal = opts?.signal; + if (signal != null && (typeof signal !== "object" || !("aborted" in signal))) { + throw new InvalidArgumentError("signal must be an AbortSignal"); + } + signal?.throwIfAborted(); + if (this._readableState.closeEmitted) { + return null; + } + return await new Promise((resolve, reject) => { + if (this[kContentLength] > limit) { + this.destroy(new AbortError()); + } + const onAbort = /* @__PURE__ */ __name(() => { + this.destroy(signal.reason ?? new AbortError()); + }, "onAbort"); + signal?.addEventListener("abort", onAbort); + this.on("close", function() { + signal?.removeEventListener("abort", onAbort); + if (signal?.aborted) { + reject(signal.reason ?? new AbortError()); + } else { + resolve(null); + } + }).on("error", noop).on("data", function(chunk) { + limit -= chunk.length; + if (limit <= 0) { + this.destroy(); + } + }).resume(); + }); + } + }; + function isLocked(self) { + return self[kBody] && self[kBody].locked === true || self[kConsume]; + } + __name(isLocked, "isLocked"); + function isUnusable(self) { + return util.isDisturbed(self) || isLocked(self); + } + __name(isUnusable, "isUnusable"); + async function consume(stream, type) { + assert(!stream[kConsume]); + return new Promise((resolve, reject) => { + if (isUnusable(stream)) { + const rState = stream._readableState; + if (rState.destroyed && rState.closeEmitted === false) { + stream.on("error", (err) => { + reject(err); + }).on("close", () => { + reject(new TypeError("unusable")); + }); + } else { + reject(rState.errored ?? new TypeError("unusable")); + } + } else { + queueMicrotask(() => { + stream[kConsume] = { + type, + stream, + resolve, + reject, + length: 0, + body: [] + }; + stream.on("error", function(err) { + consumeFinish(this[kConsume], err); + }).on("close", function() { + if (this[kConsume].body !== null) { + consumeFinish(this[kConsume], new RequestAbortedError()); + } + }); + consumeStart(stream[kConsume]); + }); + } + }); + } + __name(consume, "consume"); + function consumeStart(consume2) { + if (consume2.body === null) { + return; + } + const { _readableState: state } = consume2.stream; + if (state.bufferIndex) { + const start = state.bufferIndex; + const end = state.buffer.length; + for (let n = start; n < end; n++) { + consumePush(consume2, state.buffer[n]); + } + } else { + for (const chunk of state.buffer) { + consumePush(consume2, chunk); + } + } + if (state.endEmitted) { + consumeEnd(this[kConsume]); + } else { + consume2.stream.on("end", function() { + consumeEnd(this[kConsume]); + }); + } + consume2.stream.resume(); + while (consume2.stream.read() != null) { + } + } + __name(consumeStart, "consumeStart"); + function chunksDecode(chunks, length) { + if (chunks.length === 0 || length === 0) { + return ""; + } + const buffer = chunks.length === 1 ? chunks[0] : Buffer.concat(chunks, length); + const bufferLength = buffer.length; + const start = bufferLength > 2 && buffer[0] === 239 && buffer[1] === 187 && buffer[2] === 191 ? 3 : 0; + return buffer.utf8Slice(start, bufferLength); + } + __name(chunksDecode, "chunksDecode"); + function chunksConcat(chunks, length) { + if (chunks.length === 0 || length === 0) { + return new Uint8Array(0); + } + if (chunks.length === 1) { + return new Uint8Array(chunks[0]); + } + const buffer = new Uint8Array(Buffer.allocUnsafeSlow(length).buffer); + let offset = 0; + for (let i = 0; i < chunks.length; ++i) { + const chunk = chunks[i]; + buffer.set(chunk, offset); + offset += chunk.length; + } + return buffer; + } + __name(chunksConcat, "chunksConcat"); + function consumeEnd(consume2) { + const { type, body, resolve, stream, length } = consume2; + try { + if (type === "text") { + resolve(chunksDecode(body, length)); + } else if (type === "json") { + resolve(JSON.parse(chunksDecode(body, length))); + } else if (type === "arrayBuffer") { + resolve(chunksConcat(body, length).buffer); + } else if (type === "blob") { + resolve(new Blob(body, { type: stream[kContentType] })); + } else if (type === "bytes") { + resolve(chunksConcat(body, length)); + } + consumeFinish(consume2); + } catch (err) { + stream.destroy(err); + } + } + __name(consumeEnd, "consumeEnd"); + function consumePush(consume2, chunk) { + consume2.length += chunk.length; + consume2.body.push(chunk); + } + __name(consumePush, "consumePush"); + function consumeFinish(consume2, err) { + if (consume2.body === null) { + return; + } + if (err) { + consume2.reject(err); + } else { + consume2.resolve(); + } + consume2.type = null; + consume2.stream = null; + consume2.resolve = null; + consume2.reject = null; + consume2.length = 0; + consume2.body = null; + } + __name(consumeFinish, "consumeFinish"); + module2.exports = { Readable: BodyReadable, chunksDecode }; + } +}); + +// lib/api/util.js +var require_util5 = __commonJS({ + "lib/api/util.js"(exports2, module2) { + var assert = require("node:assert"); + var { + ResponseStatusCodeError + } = require_errors(); + var { chunksDecode } = require_readable(); + var CHUNK_LIMIT = 128 * 1024; + async function getResolveErrorBodyCallback({ callback, body, contentType, statusCode, statusMessage, headers }) { + assert(body); + let chunks = []; + let length = 0; + try { + for await (const chunk of body) { + chunks.push(chunk); + length += chunk.length; + if (length > CHUNK_LIMIT) { + chunks = []; + length = 0; + break; + } + } + } catch { + chunks = []; + length = 0; + } + const message = `Response status code ${statusCode}${statusMessage ? `: ${statusMessage}` : ""}`; + if (statusCode === 204 || !contentType || !length) { + queueMicrotask(() => callback(new ResponseStatusCodeError(message, statusCode, headers))); + return; + } + const stackTraceLimit = Error.stackTraceLimit; + Error.stackTraceLimit = 0; + let payload; + try { + if (isContentTypeApplicationJson(contentType)) { + payload = JSON.parse(chunksDecode(chunks, length)); + } else if (isContentTypeText(contentType)) { + payload = chunksDecode(chunks, length); + } + } catch { + } finally { + Error.stackTraceLimit = stackTraceLimit; + } + queueMicrotask(() => callback(new ResponseStatusCodeError(message, statusCode, headers, payload))); + } + __name(getResolveErrorBodyCallback, "getResolveErrorBodyCallback"); + var isContentTypeApplicationJson = /* @__PURE__ */ __name((contentType) => { + return contentType.length > 15 && contentType[11] === "/" && contentType[0] === "a" && contentType[1] === "p" && contentType[2] === "p" && contentType[3] === "l" && contentType[4] === "i" && contentType[5] === "c" && contentType[6] === "a" && contentType[7] === "t" && contentType[8] === "i" && contentType[9] === "o" && contentType[10] === "n" && contentType[12] === "j" && contentType[13] === "s" && contentType[14] === "o" && contentType[15] === "n"; + }, "isContentTypeApplicationJson"); + var isContentTypeText = /* @__PURE__ */ __name((contentType) => { + return contentType.length > 4 && contentType[4] === "/" && contentType[0] === "t" && contentType[1] === "e" && contentType[2] === "x" && contentType[3] === "t"; + }, "isContentTypeText"); + module2.exports = { + getResolveErrorBodyCallback, + isContentTypeApplicationJson, + isContentTypeText + }; + } +}); + +// lib/api/api-request.js +var require_api_request = __commonJS({ + "lib/api/api-request.js"(exports2, module2) { + "use strict"; + var assert = require("node:assert"); + var { Readable } = require_readable(); + var { InvalidArgumentError, RequestAbortedError } = require_errors(); + var util = require_util(); + var { getResolveErrorBodyCallback } = require_util5(); + var { AsyncResource } = require("node:async_hooks"); + var RequestHandler = class extends AsyncResource { + static { + __name(this, "RequestHandler"); + } + constructor(opts, callback) { + if (!opts || typeof opts !== "object") { + throw new InvalidArgumentError("invalid opts"); + } + const { signal, method, opaque, body, onInfo, responseHeaders, throwOnError, highWaterMark } = opts; + try { + if (typeof callback !== "function") { + throw new InvalidArgumentError("invalid callback"); + } + if (highWaterMark && (typeof highWaterMark !== "number" || highWaterMark < 0)) { + throw new InvalidArgumentError("invalid highWaterMark"); + } + if (signal && typeof signal.on !== "function" && typeof signal.addEventListener !== "function") { + throw new InvalidArgumentError("signal must be an EventEmitter or EventTarget"); + } + if (method === "CONNECT") { + throw new InvalidArgumentError("invalid method"); + } + if (onInfo && typeof onInfo !== "function") { + throw new InvalidArgumentError("invalid onInfo callback"); + } + super("UNDICI_REQUEST"); + } catch (err) { + if (util.isStream(body)) { + util.destroy(body.on("error", util.nop), err); + } + throw err; + } + this.method = method; + this.responseHeaders = responseHeaders || null; + this.opaque = opaque || null; + this.callback = callback; + this.res = null; + this.abort = null; + this.body = body; + this.trailers = {}; + this.context = null; + this.onInfo = onInfo || null; + this.throwOnError = throwOnError; + this.highWaterMark = highWaterMark; + this.signal = signal; + this.reason = null; + this.removeAbortListener = null; + if (util.isStream(body)) { + body.on("error", (err) => { + this.onError(err); + }); + } + if (this.signal) { + if (this.signal.aborted) { + this.reason = this.signal.reason ?? new RequestAbortedError(); + } else { + this.removeAbortListener = util.addAbortListener(this.signal, () => { + this.reason = this.signal.reason ?? new RequestAbortedError(); + if (this.res) { + util.destroy(this.res.on("error", util.nop), this.reason); + } else if (this.abort) { + this.abort(this.reason); + } + if (this.removeAbortListener) { + this.res?.off("close", this.removeAbortListener); + this.removeAbortListener(); + this.removeAbortListener = null; + } + }); + } + } + } + onConnect(abort, context) { + if (this.reason) { + abort(this.reason); + return; + } + assert(this.callback); + this.abort = abort; + this.context = context; + } + onHeaders(statusCode, rawHeaders, resume, statusMessage) { + const { callback, opaque, abort, context, responseHeaders, highWaterMark } = this; + const headers = responseHeaders === "raw" ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders); + if (statusCode < 200) { + if (this.onInfo) { + this.onInfo({ statusCode, headers }); + } + return; + } + const parsedHeaders = responseHeaders === "raw" ? util.parseHeaders(rawHeaders) : headers; + const contentType = parsedHeaders["content-type"]; + const contentLength = parsedHeaders["content-length"]; + const res = new Readable({ + resume, + abort, + contentType, + contentLength: this.method !== "HEAD" && contentLength ? Number(contentLength) : null, + highWaterMark + }); + if (this.removeAbortListener) { + res.on("close", this.removeAbortListener); + } + this.callback = null; + this.res = res; + if (callback !== null) { + if (this.throwOnError && statusCode >= 400) { + this.runInAsyncScope( + getResolveErrorBodyCallback, + null, + { callback, body: res, contentType, statusCode, statusMessage, headers } + ); + } else { + this.runInAsyncScope(callback, null, null, { + statusCode, + headers, + trailers: this.trailers, + opaque, + body: res, + context + }); + } + } + } + onData(chunk) { + return this.res.push(chunk); + } + onComplete(trailers) { + util.parseHeaders(trailers, this.trailers); + this.res.push(null); + } + onError(err) { + const { res, callback, body, opaque } = this; + if (callback) { + this.callback = null; + queueMicrotask(() => { + this.runInAsyncScope(callback, null, err, { opaque }); + }); + } + if (res) { + this.res = null; + queueMicrotask(() => { + util.destroy(res, err); + }); + } + if (body) { + this.body = null; + util.destroy(body, err); + } + if (this.removeAbortListener) { + res?.off("close", this.removeAbortListener); + this.removeAbortListener(); + this.removeAbortListener = null; + } + } + }; + function request(opts, callback) { + if (callback === void 0) { + return new Promise((resolve, reject) => { + request.call(this, opts, (err, data) => { + return err ? reject(err) : resolve(data); + }); + }); + } + try { + this.dispatch(opts, new RequestHandler(opts, callback)); + } catch (err) { + if (typeof callback !== "function") { + throw err; + } + const opaque = opts?.opaque; + queueMicrotask(() => callback(err, { opaque })); + } + } + __name(request, "request"); + module2.exports = request; + module2.exports.RequestHandler = RequestHandler; + } +}); + +// lib/api/abort-signal.js +var require_abort_signal = __commonJS({ + "lib/api/abort-signal.js"(exports2, module2) { + var { addAbortListener } = require_util(); + var { RequestAbortedError } = require_errors(); + var kListener = Symbol("kListener"); + var kSignal = Symbol("kSignal"); + function abort(self) { + if (self.abort) { + self.abort(self[kSignal]?.reason); + } else { + self.reason = self[kSignal]?.reason ?? new RequestAbortedError(); + } + removeSignal(self); + } + __name(abort, "abort"); + function addSignal(self, signal) { + self.reason = null; + self[kSignal] = null; + self[kListener] = null; + if (!signal) { + return; + } + if (signal.aborted) { + abort(self); + return; + } + self[kSignal] = signal; + self[kListener] = () => { + abort(self); + }; + addAbortListener(self[kSignal], self[kListener]); + } + __name(addSignal, "addSignal"); + function removeSignal(self) { + if (!self[kSignal]) { + return; + } + if ("removeEventListener" in self[kSignal]) { + self[kSignal].removeEventListener("abort", self[kListener]); + } else { + self[kSignal].removeListener("abort", self[kListener]); + } + self[kSignal] = null; + self[kListener] = null; + } + __name(removeSignal, "removeSignal"); + module2.exports = { + addSignal, + removeSignal + }; + } +}); + +// lib/api/api-stream.js +var require_api_stream = __commonJS({ + "lib/api/api-stream.js"(exports2, module2) { + "use strict"; + var assert = require("node:assert"); + var { finished, PassThrough } = require("node:stream"); + var { InvalidArgumentError, InvalidReturnValueError } = require_errors(); + var util = require_util(); + var { getResolveErrorBodyCallback } = require_util5(); + var { AsyncResource } = require("node:async_hooks"); + var { addSignal, removeSignal } = require_abort_signal(); + var StreamHandler = class extends AsyncResource { + static { + __name(this, "StreamHandler"); + } + constructor(opts, factory, callback) { + if (!opts || typeof opts !== "object") { + throw new InvalidArgumentError("invalid opts"); + } + const { signal, method, opaque, body, onInfo, responseHeaders, throwOnError } = opts; + try { + if (typeof callback !== "function") { + throw new InvalidArgumentError("invalid callback"); + } + if (typeof factory !== "function") { + throw new InvalidArgumentError("invalid factory"); + } + if (signal && typeof signal.on !== "function" && typeof signal.addEventListener !== "function") { + throw new InvalidArgumentError("signal must be an EventEmitter or EventTarget"); + } + if (method === "CONNECT") { + throw new InvalidArgumentError("invalid method"); + } + if (onInfo && typeof onInfo !== "function") { + throw new InvalidArgumentError("invalid onInfo callback"); + } + super("UNDICI_STREAM"); + } catch (err) { + if (util.isStream(body)) { + util.destroy(body.on("error", util.nop), err); + } + throw err; + } + this.responseHeaders = responseHeaders || null; + this.opaque = opaque || null; + this.factory = factory; + this.callback = callback; + this.res = null; + this.abort = null; + this.context = null; + this.trailers = null; + this.body = body; + this.onInfo = onInfo || null; + this.throwOnError = throwOnError || false; + if (util.isStream(body)) { + body.on("error", (err) => { + this.onError(err); + }); + } + addSignal(this, signal); + } + onConnect(abort, context) { + if (this.reason) { + abort(this.reason); + return; + } + assert(this.callback); + this.abort = abort; + this.context = context; + } + onHeaders(statusCode, rawHeaders, resume, statusMessage) { + const { factory, opaque, context, callback, responseHeaders } = this; + const headers = responseHeaders === "raw" ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders); + if (statusCode < 200) { + if (this.onInfo) { + this.onInfo({ statusCode, headers }); + } + return; + } + this.factory = null; + let res; + if (this.throwOnError && statusCode >= 400) { + const parsedHeaders = responseHeaders === "raw" ? util.parseHeaders(rawHeaders) : headers; + const contentType = parsedHeaders["content-type"]; + res = new PassThrough(); + this.callback = null; + this.runInAsyncScope( + getResolveErrorBodyCallback, + null, + { callback, body: res, contentType, statusCode, statusMessage, headers } + ); + } else { + if (factory === null) { + return; + } + res = this.runInAsyncScope(factory, null, { + statusCode, + headers, + opaque, + context + }); + if (!res || typeof res.write !== "function" || typeof res.end !== "function" || typeof res.on !== "function") { + throw new InvalidReturnValueError("expected Writable"); + } + finished(res, { readable: false }, (err) => { + const { callback: callback2, res: res2, opaque: opaque2, trailers, abort } = this; + this.res = null; + if (err || !res2.readable) { + util.destroy(res2, err); + } + this.callback = null; + this.runInAsyncScope(callback2, null, err || null, { opaque: opaque2, trailers }); + if (err) { + abort(); + } + }); + } + res.on("drain", resume); + this.res = res; + const needDrain = res.writableNeedDrain !== void 0 ? res.writableNeedDrain : res._writableState?.needDrain; + return needDrain !== true; + } + onData(chunk) { + const { res } = this; + return res ? res.write(chunk) : true; + } + onComplete(trailers) { + const { res } = this; + removeSignal(this); + if (!res) { + return; + } + this.trailers = util.parseHeaders(trailers); + res.end(); + } + onError(err) { + const { res, callback, opaque, body } = this; + removeSignal(this); + this.factory = null; + if (res) { + this.res = null; + util.destroy(res, err); + } else if (callback) { + this.callback = null; + queueMicrotask(() => { + this.runInAsyncScope(callback, null, err, { opaque }); + }); + } + if (body) { + this.body = null; + util.destroy(body, err); + } + } + }; + function stream(opts, factory, callback) { + if (callback === void 0) { + return new Promise((resolve, reject) => { + stream.call(this, opts, factory, (err, data) => { + return err ? reject(err) : resolve(data); + }); + }); + } + try { + this.dispatch(opts, new StreamHandler(opts, factory, callback)); + } catch (err) { + if (typeof callback !== "function") { + throw err; + } + const opaque = opts?.opaque; + queueMicrotask(() => callback(err, { opaque })); + } + } + __name(stream, "stream"); + module2.exports = stream; + } +}); + +// lib/api/api-pipeline.js +var require_api_pipeline = __commonJS({ + "lib/api/api-pipeline.js"(exports2, module2) { + "use strict"; + var { + Readable, + Duplex, + PassThrough + } = require("node:stream"); + var { + InvalidArgumentError, + InvalidReturnValueError, + RequestAbortedError + } = require_errors(); + var util = require_util(); + var { AsyncResource } = require("node:async_hooks"); + var { addSignal, removeSignal } = require_abort_signal(); + var assert = require("node:assert"); + var kResume = Symbol("resume"); + var PipelineRequest = class extends Readable { + static { + __name(this, "PipelineRequest"); + } + constructor() { + super({ autoDestroy: true }); + this[kResume] = null; + } + _read() { + const { [kResume]: resume } = this; + if (resume) { + this[kResume] = null; + resume(); + } + } + _destroy(err, callback) { + this._read(); + callback(err); + } + }; + var PipelineResponse = class extends Readable { + static { + __name(this, "PipelineResponse"); + } + constructor(resume) { + super({ autoDestroy: true }); + this[kResume] = resume; + } + _read() { + this[kResume](); + } + _destroy(err, callback) { + if (!err && !this._readableState.endEmitted) { + err = new RequestAbortedError(); + } + callback(err); + } + }; + var PipelineHandler = class extends AsyncResource { + static { + __name(this, "PipelineHandler"); + } + constructor(opts, handler) { + if (!opts || typeof opts !== "object") { + throw new InvalidArgumentError("invalid opts"); + } + if (typeof handler !== "function") { + throw new InvalidArgumentError("invalid handler"); + } + const { signal, method, opaque, onInfo, responseHeaders } = opts; + if (signal && typeof signal.on !== "function" && typeof signal.addEventListener !== "function") { + throw new InvalidArgumentError("signal must be an EventEmitter or EventTarget"); + } + if (method === "CONNECT") { + throw new InvalidArgumentError("invalid method"); + } + if (onInfo && typeof onInfo !== "function") { + throw new InvalidArgumentError("invalid onInfo callback"); + } + super("UNDICI_PIPELINE"); + this.opaque = opaque || null; + this.responseHeaders = responseHeaders || null; + this.handler = handler; + this.abort = null; + this.context = null; + this.onInfo = onInfo || null; + this.req = new PipelineRequest().on("error", util.nop); + this.ret = new Duplex({ + readableObjectMode: opts.objectMode, + autoDestroy: true, + read: () => { + const { body } = this; + if (body?.resume) { + body.resume(); + } + }, + write: (chunk, encoding, callback) => { + const { req } = this; + if (req.push(chunk, encoding) || req._readableState.destroyed) { + callback(); + } else { + req[kResume] = callback; + } + }, + destroy: (err, callback) => { + const { body, req, res, ret, abort } = this; + if (!err && !ret._readableState.endEmitted) { + err = new RequestAbortedError(); + } + if (abort && err) { + abort(); + } + util.destroy(body, err); + util.destroy(req, err); + util.destroy(res, err); + removeSignal(this); + callback(err); + } + }).on("prefinish", () => { + const { req } = this; + req.push(null); + }); + this.res = null; + addSignal(this, signal); + } + onConnect(abort, context) { + const { ret, res } = this; + if (this.reason) { + abort(this.reason); + return; + } + assert(!res, "pipeline cannot be retried"); + assert(!ret.destroyed); + this.abort = abort; + this.context = context; + } + onHeaders(statusCode, rawHeaders, resume) { + const { opaque, handler, context } = this; + if (statusCode < 200) { + if (this.onInfo) { + const headers = this.responseHeaders === "raw" ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders); + this.onInfo({ statusCode, headers }); + } + return; + } + this.res = new PipelineResponse(resume); + let body; + try { + this.handler = null; + const headers = this.responseHeaders === "raw" ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders); + body = this.runInAsyncScope(handler, null, { + statusCode, + headers, + opaque, + body: this.res, + context + }); + } catch (err) { + this.res.on("error", util.nop); + throw err; + } + if (!body || typeof body.on !== "function") { + throw new InvalidReturnValueError("expected Readable"); + } + body.on("data", (chunk) => { + const { ret, body: body2 } = this; + if (!ret.push(chunk) && body2.pause) { + body2.pause(); + } + }).on("error", (err) => { + const { ret } = this; + util.destroy(ret, err); + }).on("end", () => { + const { ret } = this; + ret.push(null); + }).on("close", () => { + const { ret } = this; + if (!ret._readableState.ended) { + util.destroy(ret, new RequestAbortedError()); + } + }); + this.body = body; + } + onData(chunk) { + const { res } = this; + return res.push(chunk); + } + onComplete(trailers) { + const { res } = this; + res.push(null); + } + onError(err) { + const { ret } = this; + this.handler = null; + util.destroy(ret, err); + } + }; + function pipeline(opts, handler) { + try { + const pipelineHandler = new PipelineHandler(opts, handler); + this.dispatch({ ...opts, body: pipelineHandler.req }, pipelineHandler); + return pipelineHandler.ret; + } catch (err) { + return new PassThrough().destroy(err); + } + } + __name(pipeline, "pipeline"); + module2.exports = pipeline; + } +}); + +// lib/api/api-upgrade.js +var require_api_upgrade = __commonJS({ + "lib/api/api-upgrade.js"(exports2, module2) { + "use strict"; + var { InvalidArgumentError, SocketError } = require_errors(); + var { AsyncResource } = require("node:async_hooks"); + var util = require_util(); + var { addSignal, removeSignal } = require_abort_signal(); + var assert = require("node:assert"); + var UpgradeHandler = class extends AsyncResource { + static { + __name(this, "UpgradeHandler"); + } + constructor(opts, callback) { + if (!opts || typeof opts !== "object") { + throw new InvalidArgumentError("invalid opts"); + } + if (typeof callback !== "function") { + throw new InvalidArgumentError("invalid callback"); + } + const { signal, opaque, responseHeaders } = opts; + if (signal && typeof signal.on !== "function" && typeof signal.addEventListener !== "function") { + throw new InvalidArgumentError("signal must be an EventEmitter or EventTarget"); + } + super("UNDICI_UPGRADE"); + this.responseHeaders = responseHeaders || null; + this.opaque = opaque || null; + this.callback = callback; + this.abort = null; + this.context = null; + addSignal(this, signal); + } + onConnect(abort, context) { + if (this.reason) { + abort(this.reason); + return; + } + assert(this.callback); + this.abort = abort; + this.context = null; + } + onHeaders() { + throw new SocketError("bad upgrade", null); + } + onUpgrade(statusCode, rawHeaders, socket) { + assert(statusCode === 101); + const { callback, opaque, context } = this; + removeSignal(this); + this.callback = null; + const headers = this.responseHeaders === "raw" ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders); + this.runInAsyncScope(callback, null, null, { + headers, + socket, + opaque, + context + }); + } + onError(err) { + const { callback, opaque } = this; + removeSignal(this); + if (callback) { + this.callback = null; + queueMicrotask(() => { + this.runInAsyncScope(callback, null, err, { opaque }); + }); + } + } + }; + function upgrade(opts, callback) { + if (callback === void 0) { + return new Promise((resolve, reject) => { + upgrade.call(this, opts, (err, data) => { + return err ? reject(err) : resolve(data); + }); + }); + } + try { + const upgradeHandler = new UpgradeHandler(opts, callback); + this.dispatch({ + ...opts, + method: opts.method || "GET", + upgrade: opts.protocol || "Websocket" + }, upgradeHandler); + } catch (err) { + if (typeof callback !== "function") { + throw err; + } + const opaque = opts?.opaque; + queueMicrotask(() => callback(err, { opaque })); + } + } + __name(upgrade, "upgrade"); + module2.exports = upgrade; + } +}); + +// lib/api/api-connect.js +var require_api_connect = __commonJS({ + "lib/api/api-connect.js"(exports2, module2) { + "use strict"; + var assert = require("node:assert"); + var { AsyncResource } = require("node:async_hooks"); + var { InvalidArgumentError, SocketError } = require_errors(); + var util = require_util(); + var { addSignal, removeSignal } = require_abort_signal(); + var ConnectHandler = class extends AsyncResource { + static { + __name(this, "ConnectHandler"); + } + constructor(opts, callback) { + if (!opts || typeof opts !== "object") { + throw new InvalidArgumentError("invalid opts"); + } + if (typeof callback !== "function") { + throw new InvalidArgumentError("invalid callback"); + } + const { signal, opaque, responseHeaders } = opts; + if (signal && typeof signal.on !== "function" && typeof signal.addEventListener !== "function") { + throw new InvalidArgumentError("signal must be an EventEmitter or EventTarget"); + } + super("UNDICI_CONNECT"); + this.opaque = opaque || null; + this.responseHeaders = responseHeaders || null; + this.callback = callback; + this.abort = null; + addSignal(this, signal); + } + onConnect(abort, context) { + if (this.reason) { + abort(this.reason); + return; + } + assert(this.callback); + this.abort = abort; + this.context = context; + } + onHeaders() { + throw new SocketError("bad connect", null); + } + onUpgrade(statusCode, rawHeaders, socket) { + const { callback, opaque, context } = this; + removeSignal(this); + this.callback = null; + let headers = rawHeaders; + if (headers != null) { + headers = this.responseHeaders === "raw" ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders); + } + this.runInAsyncScope(callback, null, null, { + statusCode, + headers, + socket, + opaque, + context + }); + } + onError(err) { + const { callback, opaque } = this; + removeSignal(this); + if (callback) { + this.callback = null; + queueMicrotask(() => { + this.runInAsyncScope(callback, null, err, { opaque }); + }); + } + } + }; + function connect(opts, callback) { + if (callback === void 0) { + return new Promise((resolve, reject) => { + connect.call(this, opts, (err, data) => { + return err ? reject(err) : resolve(data); + }); + }); + } + try { + const connectHandler = new ConnectHandler(opts, callback); + this.dispatch({ ...opts, method: "CONNECT" }, connectHandler); + } catch (err) { + if (typeof callback !== "function") { + throw err; + } + const opaque = opts?.opaque; + queueMicrotask(() => callback(err, { opaque })); + } + } + __name(connect, "connect"); + module2.exports = connect; + } +}); + +// lib/api/index.js +var require_api = __commonJS({ + "lib/api/index.js"(exports2, module2) { + "use strict"; + module2.exports.request = require_api_request(); + module2.exports.stream = require_api_stream(); + module2.exports.pipeline = require_api_pipeline(); + module2.exports.upgrade = require_api_upgrade(); + module2.exports.connect = require_api_connect(); + } +}); + // index-fetch.js var { getGlobalDispatcher, setGlobalDispatcher } = require_global2(); var EnvHttpProxyAgent = require_env_http_proxy_agent(); @@ -13523,6 +14913,9 @@ module.exports.ErrorEvent = ErrorEvent; module.exports.MessageEvent = MessageEvent; module.exports.createFastMessageEvent = createFastMessageEvent; module.exports.EventSource = require_eventsource().EventSource; +var api = require_api(); +var Dispatcher = require_dispatcher(); +Object.assign(Dispatcher.prototype, api); module.exports.EnvHttpProxyAgent = EnvHttpProxyAgent; module.exports.getGlobalDispatcher = getGlobalDispatcher; module.exports.setGlobalDispatcher = setGlobalDispatcher; diff --git a/src/undici_version.h b/src/undici_version.h index e47161c2a854a0..cf8bc91018d08d 100644 --- a/src/undici_version.h +++ b/src/undici_version.h @@ -2,5 +2,5 @@ // Refer to tools/dep_updaters/update-undici.sh #ifndef SRC_UNDICI_VERSION_H_ #define SRC_UNDICI_VERSION_H_ -#define UNDICI_VERSION "6.21.2" +#define UNDICI_VERSION "6.22.0" #endif // SRC_UNDICI_VERSION_H_