@wirecatch/cli 0.1.0 → 0.2.0
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/README.md +15 -1
- package/dist/wirecatch.mjs +1347 -668
- package/package.json +6 -1
package/dist/wirecatch.mjs
CHANGED
|
@@ -1423,14 +1423,14 @@ var require_errors = __commonJS({
|
|
|
1423
1423
|
};
|
|
1424
1424
|
var kRequestRetryError = /* @__PURE__ */ Symbol.for("undici.error.UND_ERR_REQ_RETRY");
|
|
1425
1425
|
var RequestRetryError = class extends UndiciError {
|
|
1426
|
-
constructor(message, code, { headers, data }) {
|
|
1426
|
+
constructor(message, code, { headers: headers2, data }) {
|
|
1427
1427
|
super(message);
|
|
1428
1428
|
this.name = "RequestRetryError";
|
|
1429
1429
|
this.message = message || "Request retry error";
|
|
1430
1430
|
this.code = "UND_ERR_REQ_RETRY";
|
|
1431
1431
|
this.statusCode = code;
|
|
1432
1432
|
this.data = data;
|
|
1433
|
-
this.headers =
|
|
1433
|
+
this.headers = headers2;
|
|
1434
1434
|
}
|
|
1435
1435
|
static [Symbol.hasInstance](instance) {
|
|
1436
1436
|
return instance && instance[kRequestRetryError] === true;
|
|
@@ -1441,14 +1441,14 @@ var require_errors = __commonJS({
|
|
|
1441
1441
|
};
|
|
1442
1442
|
var kResponseError = /* @__PURE__ */ Symbol.for("undici.error.UND_ERR_RESPONSE");
|
|
1443
1443
|
var ResponseError = class extends UndiciError {
|
|
1444
|
-
constructor(message, code, { headers, body }) {
|
|
1444
|
+
constructor(message, code, { headers: headers2, body }) {
|
|
1445
1445
|
super(message);
|
|
1446
1446
|
this.name = "ResponseError";
|
|
1447
1447
|
this.message = message || "Response error";
|
|
1448
1448
|
this.code = "UND_ERR_RESPONSE";
|
|
1449
1449
|
this.statusCode = code;
|
|
1450
1450
|
this.body = body;
|
|
1451
|
-
this.headers =
|
|
1451
|
+
this.headers = headers2;
|
|
1452
1452
|
}
|
|
1453
1453
|
static [Symbol.hasInstance](instance) {
|
|
1454
1454
|
return instance && instance[kResponseError] === true;
|
|
@@ -1649,10 +1649,10 @@ var require_constants = __commonJS({
|
|
|
1649
1649
|
Object.setPrototypeOf(headerNameLowerCasedRecord, null);
|
|
1650
1650
|
var wellknownHeaderNameBuffers = {};
|
|
1651
1651
|
Object.setPrototypeOf(wellknownHeaderNameBuffers, null);
|
|
1652
|
-
function getHeaderNameAsBuffer(
|
|
1653
|
-
let buffer = wellknownHeaderNameBuffers[
|
|
1652
|
+
function getHeaderNameAsBuffer(header2) {
|
|
1653
|
+
let buffer = wellknownHeaderNameBuffers[header2];
|
|
1654
1654
|
if (buffer === void 0) {
|
|
1655
|
-
buffer = Buffer.from(
|
|
1655
|
+
buffer = Buffer.from(header2);
|
|
1656
1656
|
}
|
|
1657
1657
|
return buffer;
|
|
1658
1658
|
}
|
|
@@ -2032,14 +2032,14 @@ var require_util = __commonJS({
|
|
|
2032
2032
|
function bufferToLowerCasedHeaderName(value) {
|
|
2033
2033
|
return tree.lookup(value) ?? value.toString("latin1").toLowerCase();
|
|
2034
2034
|
}
|
|
2035
|
-
function parseHeaders(
|
|
2035
|
+
function parseHeaders(headers2, obj) {
|
|
2036
2036
|
if (obj === void 0) obj = {};
|
|
2037
|
-
for (let i = 0; i <
|
|
2038
|
-
const key = headerNameToString(
|
|
2037
|
+
for (let i = 0; i < headers2.length; i += 2) {
|
|
2038
|
+
const key = headerNameToString(headers2[i]);
|
|
2039
2039
|
let val = obj[key];
|
|
2040
2040
|
if (val !== void 0) {
|
|
2041
2041
|
if (!Object.hasOwn(obj, key)) {
|
|
2042
|
-
const headersValue = typeof
|
|
2042
|
+
const headersValue = typeof headers2[i + 1] === "string" ? headers2[i + 1] : Array.isArray(headers2[i + 1]) ? headers2[i + 1].map((x) => x.toString("latin1")) : headers2[i + 1].toString("latin1");
|
|
2043
2043
|
if (key === "__proto__") {
|
|
2044
2044
|
Object.defineProperty(obj, key, {
|
|
2045
2045
|
value: headersValue,
|
|
@@ -2055,23 +2055,23 @@ var require_util = __commonJS({
|
|
|
2055
2055
|
val = [val];
|
|
2056
2056
|
obj[key] = val;
|
|
2057
2057
|
}
|
|
2058
|
-
val.push(
|
|
2058
|
+
val.push(headers2[i + 1].toString("latin1"));
|
|
2059
2059
|
}
|
|
2060
2060
|
} else {
|
|
2061
|
-
const headersValue = typeof
|
|
2061
|
+
const headersValue = typeof headers2[i + 1] === "string" ? headers2[i + 1] : Array.isArray(headers2[i + 1]) ? headers2[i + 1].map((x) => x.toString("latin1")) : headers2[i + 1].toString("latin1");
|
|
2062
2062
|
obj[key] = headersValue;
|
|
2063
2063
|
}
|
|
2064
2064
|
}
|
|
2065
2065
|
return obj;
|
|
2066
2066
|
}
|
|
2067
|
-
function parseRawHeaders(
|
|
2068
|
-
const headersLength =
|
|
2067
|
+
function parseRawHeaders(headers2) {
|
|
2068
|
+
const headersLength = headers2.length;
|
|
2069
2069
|
const ret = new Array(headersLength);
|
|
2070
2070
|
let key;
|
|
2071
2071
|
let val;
|
|
2072
2072
|
for (let n = 0; n < headersLength; n += 2) {
|
|
2073
|
-
key =
|
|
2074
|
-
val =
|
|
2073
|
+
key = headers2[n];
|
|
2074
|
+
val = headers2[n + 1];
|
|
2075
2075
|
typeof key !== "string" && (key = key.toString());
|
|
2076
2076
|
typeof val !== "string" && (val = val.toString("latin1"));
|
|
2077
2077
|
ret[n] = key;
|
|
@@ -2079,9 +2079,9 @@ var require_util = __commonJS({
|
|
|
2079
2079
|
}
|
|
2080
2080
|
return ret;
|
|
2081
2081
|
}
|
|
2082
|
-
function toRawHeaders(
|
|
2082
|
+
function toRawHeaders(headers2) {
|
|
2083
2083
|
const rawHeaders = [];
|
|
2084
|
-
for (const [name, value] of Object.entries(
|
|
2084
|
+
for (const [name, value] of Object.entries(headers2)) {
|
|
2085
2085
|
if (Array.isArray(value)) {
|
|
2086
2086
|
for (const entry of value) {
|
|
2087
2087
|
rawHeaders.push(Buffer.from(name, "latin1"), Buffer.from(`${entry}`, "latin1"));
|
|
@@ -2092,11 +2092,11 @@ var require_util = __commonJS({
|
|
|
2092
2092
|
}
|
|
2093
2093
|
return rawHeaders;
|
|
2094
2094
|
}
|
|
2095
|
-
function encodeRawHeaders(
|
|
2096
|
-
if (!Array.isArray(
|
|
2095
|
+
function encodeRawHeaders(headers2) {
|
|
2096
|
+
if (!Array.isArray(headers2)) {
|
|
2097
2097
|
throw new TypeError("expected headers to be an array");
|
|
2098
2098
|
}
|
|
2099
|
-
return
|
|
2099
|
+
return headers2.map((x) => Buffer.from(x));
|
|
2100
2100
|
}
|
|
2101
2101
|
function isBuffer(buffer) {
|
|
2102
2102
|
return buffer instanceof Uint8Array || Buffer.isBuffer(buffer);
|
|
@@ -2943,7 +2943,7 @@ var require_request = __commonJS({
|
|
|
2943
2943
|
path,
|
|
2944
2944
|
method,
|
|
2945
2945
|
body,
|
|
2946
|
-
headers,
|
|
2946
|
+
headers: headers2,
|
|
2947
2947
|
query,
|
|
2948
2948
|
idempotent,
|
|
2949
2949
|
blocking,
|
|
@@ -3047,28 +3047,28 @@ var require_request = __commonJS({
|
|
|
3047
3047
|
this.contentType = null;
|
|
3048
3048
|
this.headers = [];
|
|
3049
3049
|
this.expectContinue = expectContinue != null ? expectContinue : false;
|
|
3050
|
-
if (Array.isArray(
|
|
3051
|
-
if (
|
|
3050
|
+
if (Array.isArray(headers2)) {
|
|
3051
|
+
if (headers2.length % 2 !== 0) {
|
|
3052
3052
|
throw new InvalidArgumentError("headers array must be even");
|
|
3053
3053
|
}
|
|
3054
|
-
for (let i = 0; i <
|
|
3055
|
-
processHeader(this,
|
|
3054
|
+
for (let i = 0; i < headers2.length; i += 2) {
|
|
3055
|
+
processHeader(this, headers2[i], headers2[i + 1]);
|
|
3056
3056
|
}
|
|
3057
|
-
} else if (
|
|
3058
|
-
if (hasSafeIterator(
|
|
3059
|
-
for (const
|
|
3060
|
-
if (!Array.isArray(
|
|
3057
|
+
} else if (headers2 && typeof headers2 === "object") {
|
|
3058
|
+
if (hasSafeIterator(headers2)) {
|
|
3059
|
+
for (const header2 of headers2) {
|
|
3060
|
+
if (!Array.isArray(header2) || header2.length !== 2) {
|
|
3061
3061
|
throw new InvalidArgumentError("headers must be in key-value pair format");
|
|
3062
3062
|
}
|
|
3063
|
-
processHeader(this,
|
|
3063
|
+
processHeader(this, header2[0], header2[1]);
|
|
3064
3064
|
}
|
|
3065
3065
|
} else {
|
|
3066
|
-
const keys = Object.keys(
|
|
3066
|
+
const keys = Object.keys(headers2);
|
|
3067
3067
|
for (let i = 0; i < keys.length; ++i) {
|
|
3068
|
-
processHeader(this, keys[i],
|
|
3068
|
+
processHeader(this, keys[i], headers2[keys[i]]);
|
|
3069
3069
|
}
|
|
3070
3070
|
}
|
|
3071
|
-
} else if (
|
|
3071
|
+
} else if (headers2 != null) {
|
|
3072
3072
|
throw new InvalidArgumentError("headers must be an object or an array");
|
|
3073
3073
|
}
|
|
3074
3074
|
assertRequestHandler(handler, method, upgrade);
|
|
@@ -3115,14 +3115,14 @@ var require_request = __commonJS({
|
|
|
3115
3115
|
onResponseStarted() {
|
|
3116
3116
|
return this[kHandler].onResponseStarted?.();
|
|
3117
3117
|
}
|
|
3118
|
-
onHeaders(statusCode,
|
|
3118
|
+
onHeaders(statusCode, headers2, resume, statusText) {
|
|
3119
3119
|
assert(!this.aborted);
|
|
3120
3120
|
assert(!this.completed);
|
|
3121
3121
|
if (channels.headers.hasSubscribers) {
|
|
3122
|
-
channels.headers.publish({ request: this, response: { statusCode, headers, statusText } });
|
|
3122
|
+
channels.headers.publish({ request: this, response: { statusCode, headers: headers2, statusText } });
|
|
3123
3123
|
}
|
|
3124
3124
|
try {
|
|
3125
|
-
return this[kHandler].onHeaders(statusCode,
|
|
3125
|
+
return this[kHandler].onHeaders(statusCode, headers2, resume, statusText);
|
|
3126
3126
|
} catch (err) {
|
|
3127
3127
|
this.abort(err);
|
|
3128
3128
|
}
|
|
@@ -3146,14 +3146,14 @@ var require_request = __commonJS({
|
|
|
3146
3146
|
* @param {import('node:stream').Duplex} socket
|
|
3147
3147
|
* @param {string} [statusText]
|
|
3148
3148
|
*/
|
|
3149
|
-
onUpgrade(statusCode,
|
|
3149
|
+
onUpgrade(statusCode, headers2, socket, statusText = "") {
|
|
3150
3150
|
this.onFinally();
|
|
3151
3151
|
assert(!this.aborted);
|
|
3152
3152
|
assert(!this.completed);
|
|
3153
3153
|
if (channels.headers.hasSubscribers) {
|
|
3154
|
-
channels.headers.publish({ request: this, response: { statusCode, headers, statusText } });
|
|
3154
|
+
channels.headers.publish({ request: this, response: { statusCode, headers: headers2, statusText } });
|
|
3155
3155
|
}
|
|
3156
|
-
const result = this[kHandler].onUpgrade(statusCode,
|
|
3156
|
+
const result = this[kHandler].onUpgrade(statusCode, headers2, socket);
|
|
3157
3157
|
if (!this.aborted) {
|
|
3158
3158
|
this.completed = true;
|
|
3159
3159
|
if (channels.trailers.hasSubscribers) {
|
|
@@ -3335,16 +3335,16 @@ var require_wrap_handler = __commonJS({
|
|
|
3335
3335
|
onRequestStart(controller, context) {
|
|
3336
3336
|
this.#handler.onConnect?.((reason) => controller.abort(reason), context);
|
|
3337
3337
|
}
|
|
3338
|
-
onRequestUpgrade(controller, statusCode,
|
|
3338
|
+
onRequestUpgrade(controller, statusCode, headers2, socket) {
|
|
3339
3339
|
const rawHeaders = [];
|
|
3340
|
-
for (const [key, val] of Object.entries(
|
|
3340
|
+
for (const [key, val] of Object.entries(headers2)) {
|
|
3341
3341
|
rawHeaders.push(Buffer.from(key, "latin1"), toRawHeaderValue(val));
|
|
3342
3342
|
}
|
|
3343
3343
|
this.#handler.onUpgrade?.(statusCode, rawHeaders, socket);
|
|
3344
3344
|
}
|
|
3345
|
-
onResponseStart(controller, statusCode,
|
|
3345
|
+
onResponseStart(controller, statusCode, headers2, statusMessage) {
|
|
3346
3346
|
const rawHeaders = [];
|
|
3347
|
-
for (const [key, val] of Object.entries(
|
|
3347
|
+
for (const [key, val] of Object.entries(headers2)) {
|
|
3348
3348
|
rawHeaders.push(Buffer.from(key, "latin1"), toRawHeaderValue(val));
|
|
3349
3349
|
}
|
|
3350
3350
|
if (this.#handler.onHeaders?.(statusCode, rawHeaders, () => controller.resume(), statusMessage) === false) {
|
|
@@ -3568,9 +3568,9 @@ var require_dispatcher_base = __commonJS({
|
|
|
3568
3568
|
}
|
|
3569
3569
|
close(callback) {
|
|
3570
3570
|
if (callback === void 0) {
|
|
3571
|
-
return new Promise((
|
|
3571
|
+
return new Promise((resolve4, reject) => {
|
|
3572
3572
|
this.close((err, data) => {
|
|
3573
|
-
return err ? reject(err) :
|
|
3573
|
+
return err ? reject(err) : resolve4(data);
|
|
3574
3574
|
});
|
|
3575
3575
|
});
|
|
3576
3576
|
}
|
|
@@ -3608,9 +3608,9 @@ var require_dispatcher_base = __commonJS({
|
|
|
3608
3608
|
err = null;
|
|
3609
3609
|
}
|
|
3610
3610
|
if (callback === void 0) {
|
|
3611
|
-
return new Promise((
|
|
3611
|
+
return new Promise((resolve4, reject) => {
|
|
3612
3612
|
this.destroy(err, (err2, data) => {
|
|
3613
|
-
return err2 ? reject(err2) :
|
|
3613
|
+
return err2 ? reject(err2) : resolve4(data);
|
|
3614
3614
|
});
|
|
3615
3615
|
});
|
|
3616
3616
|
}
|
|
@@ -5957,9 +5957,9 @@ var require_util2 = __commonJS({
|
|
|
5957
5957
|
return "success";
|
|
5958
5958
|
}
|
|
5959
5959
|
function appendFetchMetadata(httpRequest) {
|
|
5960
|
-
let
|
|
5961
|
-
|
|
5962
|
-
httpRequest.headersList.set("sec-fetch-mode",
|
|
5960
|
+
let header2 = null;
|
|
5961
|
+
header2 = httpRequest.mode;
|
|
5962
|
+
httpRequest.headersList.set("sec-fetch-mode", header2, true);
|
|
5963
5963
|
}
|
|
5964
5964
|
function appendRequestOriginHeader(request2) {
|
|
5965
5965
|
let serializedOrigin = request2.origin;
|
|
@@ -6476,11 +6476,11 @@ var require_util2 = __commonJS({
|
|
|
6476
6476
|
function createInflate(zlibOptions) {
|
|
6477
6477
|
return new InflateStream(zlibOptions);
|
|
6478
6478
|
}
|
|
6479
|
-
function extractMimeType(
|
|
6479
|
+
function extractMimeType(headers2) {
|
|
6480
6480
|
let charset = null;
|
|
6481
6481
|
let essence = null;
|
|
6482
6482
|
let mimeType2 = null;
|
|
6483
|
-
const values = getDecodeSplit("content-type",
|
|
6483
|
+
const values = getDecodeSplit("content-type", headers2);
|
|
6484
6484
|
if (values === null) {
|
|
6485
6485
|
return "failure";
|
|
6486
6486
|
}
|
|
@@ -7116,8 +7116,8 @@ var require_promise = __commonJS({
|
|
|
7116
7116
|
function createDeferredPromise() {
|
|
7117
7117
|
let res;
|
|
7118
7118
|
let rej;
|
|
7119
|
-
const promise = new Promise((
|
|
7120
|
-
res =
|
|
7119
|
+
const promise = new Promise((resolve4, reject) => {
|
|
7120
|
+
res = resolve4;
|
|
7121
7121
|
rej = reject;
|
|
7122
7122
|
});
|
|
7123
7123
|
return { promise, resolve: res, reject: rej };
|
|
@@ -7393,8 +7393,8 @@ Content-Type: ${value.type || "application/octet-stream"}\r
|
|
|
7393
7393
|
return body != null && (body.stream.locked || util.isDisturbed(body.stream));
|
|
7394
7394
|
}
|
|
7395
7395
|
function bodyMimeType(requestOrResponse) {
|
|
7396
|
-
const
|
|
7397
|
-
const mimeType2 = extractMimeType(
|
|
7396
|
+
const headers2 = requestOrResponse.headersList;
|
|
7397
|
+
const mimeType2 = extractMimeType(headers2);
|
|
7398
7398
|
if (mimeType2 === "failure") {
|
|
7399
7399
|
return null;
|
|
7400
7400
|
}
|
|
@@ -7838,12 +7838,12 @@ var require_client_h1 = __commonJS({
|
|
|
7838
7838
|
* @param {Buffer} head
|
|
7839
7839
|
*/
|
|
7840
7840
|
onUpgrade(head) {
|
|
7841
|
-
const { upgrade, client, socket, headers, statusCode, statusText } = this;
|
|
7841
|
+
const { upgrade, client, socket, headers: headers2, statusCode, statusText } = this;
|
|
7842
7842
|
assert(upgrade);
|
|
7843
7843
|
assert(client[kSocket] === socket);
|
|
7844
7844
|
assert(!socket.destroyed);
|
|
7845
7845
|
assert(!this.paused);
|
|
7846
|
-
assert((
|
|
7846
|
+
assert((headers2.length & 1) === 0);
|
|
7847
7847
|
const request2 = client[kQueue][client[kRunningIdx]];
|
|
7848
7848
|
assert(request2);
|
|
7849
7849
|
assert(request2.upgrade || request2.method === "CONNECT");
|
|
@@ -7863,7 +7863,7 @@ var require_client_h1 = __commonJS({
|
|
|
7863
7863
|
client[kQueue][client[kRunningIdx]++] = null;
|
|
7864
7864
|
client.emit("disconnect", client[kUrl], [client], new InformationalError("upgrade"));
|
|
7865
7865
|
try {
|
|
7866
|
-
request2.onUpgrade(statusCode,
|
|
7866
|
+
request2.onUpgrade(statusCode, headers2, socket, statusText);
|
|
7867
7867
|
} catch (err) {
|
|
7868
7868
|
util.errorRequest(client, request2, err);
|
|
7869
7869
|
util.destroy(socket, err);
|
|
@@ -7877,7 +7877,7 @@ var require_client_h1 = __commonJS({
|
|
|
7877
7877
|
* @returns {number}
|
|
7878
7878
|
*/
|
|
7879
7879
|
onHeadersComplete(statusCode, upgrade, shouldKeepAlive) {
|
|
7880
|
-
const { client, socket, headers, statusText } = this;
|
|
7880
|
+
const { client, socket, headers: headers2, statusText } = this;
|
|
7881
7881
|
if (socket.destroyed) {
|
|
7882
7882
|
return -1;
|
|
7883
7883
|
}
|
|
@@ -7942,7 +7942,7 @@ var require_client_h1 = __commonJS({
|
|
|
7942
7942
|
} else {
|
|
7943
7943
|
socket[kReset] = true;
|
|
7944
7944
|
}
|
|
7945
|
-
const pause = request2.onHeaders(statusCode,
|
|
7945
|
+
const pause = request2.onHeaders(statusCode, headers2, this.resume, statusText) === false;
|
|
7946
7946
|
if (request2.aborted) {
|
|
7947
7947
|
return -1;
|
|
7948
7948
|
}
|
|
@@ -7990,7 +7990,7 @@ var require_client_h1 = __commonJS({
|
|
|
7990
7990
|
* @returns {number}
|
|
7991
7991
|
*/
|
|
7992
7992
|
onMessageComplete() {
|
|
7993
|
-
const { client, socket, statusCode, upgrade, headers, contentLength, bytesRead, shouldKeepAlive } = this;
|
|
7993
|
+
const { client, socket, statusCode, upgrade, headers: headers2, contentLength, bytesRead, shouldKeepAlive } = this;
|
|
7994
7994
|
if (socket.destroyed && (!statusCode || shouldKeepAlive)) {
|
|
7995
7995
|
return -1;
|
|
7996
7996
|
}
|
|
@@ -8016,7 +8016,7 @@ var require_client_h1 = __commonJS({
|
|
|
8016
8016
|
util.destroy(socket, new ResponseContentLengthMismatchError());
|
|
8017
8017
|
return -1;
|
|
8018
8018
|
}
|
|
8019
|
-
request2.onComplete(
|
|
8019
|
+
request2.onComplete(headers2);
|
|
8020
8020
|
client[kQueue][client[kRunningIdx]++] = null;
|
|
8021
8021
|
socket[kSocketUsed] = client[kPending] === 0;
|
|
8022
8022
|
if (socket[kWriting]) {
|
|
@@ -8281,7 +8281,7 @@ var require_client_h1 = __commonJS({
|
|
|
8281
8281
|
}
|
|
8282
8282
|
function writeH1(client, request2) {
|
|
8283
8283
|
const { method, path, host, upgrade, blocking, reset } = request2;
|
|
8284
|
-
let { body, headers, contentLength } = request2;
|
|
8284
|
+
let { body, headers: headers2, contentLength } = request2;
|
|
8285
8285
|
const expectsPayload = method === "PUT" || method === "POST" || method === "PATCH" || method === "QUERY" || method === "PROPFIND" || method === "PROPPATCH";
|
|
8286
8286
|
if (util.isFormDataLike(body)) {
|
|
8287
8287
|
if (!extractBody) {
|
|
@@ -8289,7 +8289,7 @@ var require_client_h1 = __commonJS({
|
|
|
8289
8289
|
}
|
|
8290
8290
|
const [bodyStream, contentType] = extractBody(body);
|
|
8291
8291
|
if (request2.contentType == null) {
|
|
8292
|
-
|
|
8292
|
+
headers2.push("content-type", contentType);
|
|
8293
8293
|
}
|
|
8294
8294
|
body = bodyStream.stream;
|
|
8295
8295
|
contentLength = bodyStream.length;
|
|
@@ -8301,7 +8301,7 @@ var require_client_h1 = __commonJS({
|
|
|
8301
8301
|
util.errorRequest(client, request2, new InvalidArgumentError("invalid content-type header"));
|
|
8302
8302
|
return false;
|
|
8303
8303
|
}
|
|
8304
|
-
|
|
8304
|
+
headers2.push("content-type", contentTypeValue);
|
|
8305
8305
|
}
|
|
8306
8306
|
}
|
|
8307
8307
|
if (body && typeof body.read === "function") {
|
|
@@ -8356,64 +8356,64 @@ var require_client_h1 = __commonJS({
|
|
|
8356
8356
|
socket[kBlocking] = true;
|
|
8357
8357
|
}
|
|
8358
8358
|
setTypeOfService(socket, request2);
|
|
8359
|
-
let
|
|
8359
|
+
let header2 = `${method} ${path} HTTP/1.1\r
|
|
8360
8360
|
`;
|
|
8361
8361
|
if (typeof host === "string") {
|
|
8362
|
-
|
|
8362
|
+
header2 += `host: ${host}\r
|
|
8363
8363
|
`;
|
|
8364
8364
|
} else {
|
|
8365
|
-
|
|
8365
|
+
header2 += client[kHostHeader];
|
|
8366
8366
|
}
|
|
8367
8367
|
if (upgrade) {
|
|
8368
|
-
|
|
8368
|
+
header2 += `connection: upgrade\r
|
|
8369
8369
|
upgrade: ${upgrade}\r
|
|
8370
8370
|
`;
|
|
8371
8371
|
} else if (client[kPipelining] && !socket[kReset]) {
|
|
8372
|
-
|
|
8372
|
+
header2 += "connection: keep-alive\r\n";
|
|
8373
8373
|
} else {
|
|
8374
|
-
|
|
8374
|
+
header2 += "connection: close\r\n";
|
|
8375
8375
|
}
|
|
8376
|
-
if (Array.isArray(
|
|
8377
|
-
for (let n = 0; n <
|
|
8378
|
-
const key =
|
|
8379
|
-
const val =
|
|
8376
|
+
if (Array.isArray(headers2)) {
|
|
8377
|
+
for (let n = 0; n < headers2.length; n += 2) {
|
|
8378
|
+
const key = headers2[n + 0];
|
|
8379
|
+
const val = headers2[n + 1];
|
|
8380
8380
|
if (Array.isArray(val)) {
|
|
8381
8381
|
for (let i = 0; i < val.length; i++) {
|
|
8382
|
-
|
|
8382
|
+
header2 += `${key}: ${val[i]}\r
|
|
8383
8383
|
`;
|
|
8384
8384
|
}
|
|
8385
8385
|
} else {
|
|
8386
|
-
|
|
8386
|
+
header2 += `${key}: ${val}\r
|
|
8387
8387
|
`;
|
|
8388
8388
|
}
|
|
8389
8389
|
}
|
|
8390
8390
|
}
|
|
8391
8391
|
if (channels.sendHeaders.hasSubscribers) {
|
|
8392
|
-
channels.sendHeaders.publish({ request: request2, headers:
|
|
8392
|
+
channels.sendHeaders.publish({ request: request2, headers: header2, socket });
|
|
8393
8393
|
}
|
|
8394
8394
|
if (!body || bodyLength === 0) {
|
|
8395
|
-
writeBuffer(abort, null, client, request2, socket, contentLength,
|
|
8395
|
+
writeBuffer(abort, null, client, request2, socket, contentLength, header2, expectsPayload);
|
|
8396
8396
|
} else if (util.isBuffer(body)) {
|
|
8397
|
-
writeBuffer(abort, body, client, request2, socket, contentLength,
|
|
8397
|
+
writeBuffer(abort, body, client, request2, socket, contentLength, header2, expectsPayload);
|
|
8398
8398
|
} else if (util.isBlobLike(body)) {
|
|
8399
8399
|
if (typeof body.stream === "function") {
|
|
8400
|
-
writeIterable(abort, body.stream(), client, request2, socket, contentLength,
|
|
8400
|
+
writeIterable(abort, body.stream(), client, request2, socket, contentLength, header2, expectsPayload);
|
|
8401
8401
|
} else {
|
|
8402
|
-
writeBlob(abort, body, client, request2, socket, contentLength,
|
|
8402
|
+
writeBlob(abort, body, client, request2, socket, contentLength, header2, expectsPayload);
|
|
8403
8403
|
}
|
|
8404
8404
|
} else if (util.isStream(body)) {
|
|
8405
|
-
writeStream(abort, body, client, request2, socket, contentLength,
|
|
8405
|
+
writeStream(abort, body, client, request2, socket, contentLength, header2, expectsPayload);
|
|
8406
8406
|
} else if (util.isIterable(body)) {
|
|
8407
|
-
writeIterable(abort, body, client, request2, socket, contentLength,
|
|
8407
|
+
writeIterable(abort, body, client, request2, socket, contentLength, header2, expectsPayload);
|
|
8408
8408
|
} else {
|
|
8409
8409
|
assert(false);
|
|
8410
8410
|
}
|
|
8411
8411
|
return true;
|
|
8412
8412
|
}
|
|
8413
|
-
function writeStream(abort, body, client, request2, socket, contentLength,
|
|
8413
|
+
function writeStream(abort, body, client, request2, socket, contentLength, header2, expectsPayload) {
|
|
8414
8414
|
assert(contentLength !== 0 || client[kRunning] === 0, "stream body cannot be pipelined");
|
|
8415
8415
|
let finished = false;
|
|
8416
|
-
const writer = new AsyncWriter({ abort, socket, request: request2, contentLength, client, expectsPayload, header });
|
|
8416
|
+
const writer = new AsyncWriter({ abort, socket, request: request2, contentLength, client, expectsPayload, header: header2 });
|
|
8417
8417
|
const onData = function(chunk) {
|
|
8418
8418
|
if (finished) {
|
|
8419
8419
|
return;
|
|
@@ -8479,22 +8479,22 @@ upgrade: ${upgrade}\r
|
|
|
8479
8479
|
setImmediate(onClose);
|
|
8480
8480
|
}
|
|
8481
8481
|
}
|
|
8482
|
-
function writeBuffer(abort, body, client, request2, socket, contentLength,
|
|
8482
|
+
function writeBuffer(abort, body, client, request2, socket, contentLength, header2, expectsPayload) {
|
|
8483
8483
|
try {
|
|
8484
8484
|
if (!body) {
|
|
8485
8485
|
if (contentLength === 0) {
|
|
8486
|
-
socket.write(`${
|
|
8486
|
+
socket.write(`${header2}content-length: 0\r
|
|
8487
8487
|
\r
|
|
8488
8488
|
`, "latin1");
|
|
8489
8489
|
} else {
|
|
8490
8490
|
assert(contentLength === null, "no body must not have content length");
|
|
8491
|
-
socket.write(`${
|
|
8491
|
+
socket.write(`${header2}\r
|
|
8492
8492
|
`, "latin1");
|
|
8493
8493
|
}
|
|
8494
8494
|
} else if (util.isBuffer(body)) {
|
|
8495
8495
|
assert(contentLength === body.byteLength, "buffer body must have content length");
|
|
8496
8496
|
socket.cork();
|
|
8497
|
-
socket.write(`${
|
|
8497
|
+
socket.write(`${header2}content-length: ${contentLength}\r
|
|
8498
8498
|
\r
|
|
8499
8499
|
`, "latin1");
|
|
8500
8500
|
socket.write(body);
|
|
@@ -8510,7 +8510,7 @@ upgrade: ${upgrade}\r
|
|
|
8510
8510
|
abort(err);
|
|
8511
8511
|
}
|
|
8512
8512
|
}
|
|
8513
|
-
async function writeBlob(abort, body, client, request2, socket, contentLength,
|
|
8513
|
+
async function writeBlob(abort, body, client, request2, socket, contentLength, header2, expectsPayload) {
|
|
8514
8514
|
assert(contentLength === body.size, "blob body must have content length");
|
|
8515
8515
|
try {
|
|
8516
8516
|
if (contentLength != null && contentLength !== body.size) {
|
|
@@ -8518,7 +8518,7 @@ upgrade: ${upgrade}\r
|
|
|
8518
8518
|
}
|
|
8519
8519
|
const buffer = Buffer.from(await body.arrayBuffer());
|
|
8520
8520
|
socket.cork();
|
|
8521
|
-
socket.write(`${
|
|
8521
|
+
socket.write(`${header2}content-length: ${contentLength}\r
|
|
8522
8522
|
\r
|
|
8523
8523
|
`, "latin1");
|
|
8524
8524
|
socket.write(buffer);
|
|
@@ -8533,7 +8533,7 @@ upgrade: ${upgrade}\r
|
|
|
8533
8533
|
abort(err);
|
|
8534
8534
|
}
|
|
8535
8535
|
}
|
|
8536
|
-
async function writeIterable(abort, body, client, request2, socket, contentLength,
|
|
8536
|
+
async function writeIterable(abort, body, client, request2, socket, contentLength, header2, expectsPayload) {
|
|
8537
8537
|
assert(contentLength !== 0 || client[kRunning] === 0, "iterator body cannot be pipelined");
|
|
8538
8538
|
let callback = null;
|
|
8539
8539
|
function onDrain() {
|
|
@@ -8543,16 +8543,16 @@ upgrade: ${upgrade}\r
|
|
|
8543
8543
|
cb();
|
|
8544
8544
|
}
|
|
8545
8545
|
}
|
|
8546
|
-
const waitForDrain = () => new Promise((
|
|
8546
|
+
const waitForDrain = () => new Promise((resolve4, reject) => {
|
|
8547
8547
|
assert(callback === null);
|
|
8548
8548
|
if (socket[kError]) {
|
|
8549
8549
|
reject(socket[kError]);
|
|
8550
8550
|
} else {
|
|
8551
|
-
callback =
|
|
8551
|
+
callback = resolve4;
|
|
8552
8552
|
}
|
|
8553
8553
|
});
|
|
8554
8554
|
socket.on("close", onDrain).on("drain", onDrain);
|
|
8555
|
-
const writer = new AsyncWriter({ abort, socket, request: request2, contentLength, client, expectsPayload, header });
|
|
8555
|
+
const writer = new AsyncWriter({ abort, socket, request: request2, contentLength, client, expectsPayload, header: header2 });
|
|
8556
8556
|
try {
|
|
8557
8557
|
for await (const chunk of body) {
|
|
8558
8558
|
if (socket[kError]) {
|
|
@@ -8581,14 +8581,14 @@ upgrade: ${upgrade}\r
|
|
|
8581
8581
|
* @param {boolean} arg.expectsPayload
|
|
8582
8582
|
* @param {string} arg.header
|
|
8583
8583
|
*/
|
|
8584
|
-
constructor({ abort, socket, request: request2, contentLength, client, expectsPayload, header }) {
|
|
8584
|
+
constructor({ abort, socket, request: request2, contentLength, client, expectsPayload, header: header2 }) {
|
|
8585
8585
|
this.socket = socket;
|
|
8586
8586
|
this.request = request2;
|
|
8587
8587
|
this.contentLength = contentLength;
|
|
8588
8588
|
this.client = client;
|
|
8589
8589
|
this.bytesWritten = 0;
|
|
8590
8590
|
this.expectsPayload = expectsPayload;
|
|
8591
|
-
this.header =
|
|
8591
|
+
this.header = header2;
|
|
8592
8592
|
this.abort = abort;
|
|
8593
8593
|
socket[kWriting] = true;
|
|
8594
8594
|
}
|
|
@@ -8597,7 +8597,7 @@ upgrade: ${upgrade}\r
|
|
|
8597
8597
|
* @returns
|
|
8598
8598
|
*/
|
|
8599
8599
|
write(chunk) {
|
|
8600
|
-
const { socket, request: request2, contentLength, client, bytesWritten, expectsPayload, header } = this;
|
|
8600
|
+
const { socket, request: request2, contentLength, client, bytesWritten, expectsPayload, header: header2 } = this;
|
|
8601
8601
|
if (socket[kError]) {
|
|
8602
8602
|
throw socket[kError];
|
|
8603
8603
|
}
|
|
@@ -8620,10 +8620,10 @@ upgrade: ${upgrade}\r
|
|
|
8620
8620
|
socket[kReset] = true;
|
|
8621
8621
|
}
|
|
8622
8622
|
if (contentLength === null) {
|
|
8623
|
-
socket.write(`${
|
|
8623
|
+
socket.write(`${header2}transfer-encoding: chunked\r
|
|
8624
8624
|
`, "latin1");
|
|
8625
8625
|
} else {
|
|
8626
|
-
socket.write(`${
|
|
8626
|
+
socket.write(`${header2}content-length: ${contentLength}\r
|
|
8627
8627
|
\r
|
|
8628
8628
|
`, "latin1");
|
|
8629
8629
|
}
|
|
@@ -8650,7 +8650,7 @@ ${len.toString(16)}\r
|
|
|
8650
8650
|
* @returns {void}
|
|
8651
8651
|
*/
|
|
8652
8652
|
end() {
|
|
8653
|
-
const { socket, contentLength, client, bytesWritten, expectsPayload, header, request: request2 } = this;
|
|
8653
|
+
const { socket, contentLength, client, bytesWritten, expectsPayload, header: header2, request: request2 } = this;
|
|
8654
8654
|
request2.onRequestSent();
|
|
8655
8655
|
socket[kWriting] = false;
|
|
8656
8656
|
if (socket[kError]) {
|
|
@@ -8661,11 +8661,11 @@ ${len.toString(16)}\r
|
|
|
8661
8661
|
}
|
|
8662
8662
|
if (bytesWritten === 0) {
|
|
8663
8663
|
if (expectsPayload) {
|
|
8664
|
-
socket.write(`${
|
|
8664
|
+
socket.write(`${header2}content-length: 0\r
|
|
8665
8665
|
\r
|
|
8666
8666
|
`, "latin1");
|
|
8667
8667
|
} else {
|
|
8668
|
-
socket.write(`${
|
|
8668
|
+
socket.write(`${header2}\r
|
|
8669
8669
|
`, "latin1");
|
|
8670
8670
|
}
|
|
8671
8671
|
} else if (contentLength === null) {
|
|
@@ -8770,9 +8770,9 @@ var require_client_h2 = __commonJS({
|
|
|
8770
8770
|
NGHTTP2_CANCEL
|
|
8771
8771
|
}
|
|
8772
8772
|
} = http2;
|
|
8773
|
-
function parseH2Headers(
|
|
8773
|
+
function parseH2Headers(headers2) {
|
|
8774
8774
|
const result = [];
|
|
8775
|
-
for (const [name, value] of Object.entries(
|
|
8775
|
+
for (const [name, value] of Object.entries(headers2)) {
|
|
8776
8776
|
if (Array.isArray(value)) {
|
|
8777
8777
|
for (const subvalue of value) {
|
|
8778
8778
|
result.push(Buffer.from(name), Buffer.from(subvalue));
|
|
@@ -9039,36 +9039,36 @@ var require_client_h2 = __commonJS({
|
|
|
9039
9039
|
util.errorRequest(client, request2, new InvalidArgumentError(`Custom upgrade "${upgrade}" not supported over HTTP/2`));
|
|
9040
9040
|
return false;
|
|
9041
9041
|
}
|
|
9042
|
-
const
|
|
9042
|
+
const headers2 = {};
|
|
9043
9043
|
for (let n = 0; n < reqHeaders.length; n += 2) {
|
|
9044
9044
|
const key = reqHeaders[n + 0];
|
|
9045
9045
|
const val = reqHeaders[n + 1];
|
|
9046
9046
|
if (key === "cookie") {
|
|
9047
|
-
if (
|
|
9048
|
-
|
|
9047
|
+
if (headers2[key] != null) {
|
|
9048
|
+
headers2[key] = Array.isArray(headers2[key]) ? (headers2[key].push(val), headers2[key]) : [headers2[key], val];
|
|
9049
9049
|
} else {
|
|
9050
|
-
|
|
9050
|
+
headers2[key] = val;
|
|
9051
9051
|
}
|
|
9052
9052
|
continue;
|
|
9053
9053
|
}
|
|
9054
9054
|
if (Array.isArray(val)) {
|
|
9055
9055
|
for (let i = 0; i < val.length; i++) {
|
|
9056
|
-
if (
|
|
9057
|
-
|
|
9056
|
+
if (headers2[key]) {
|
|
9057
|
+
headers2[key] += `, ${val[i]}`;
|
|
9058
9058
|
} else {
|
|
9059
|
-
|
|
9059
|
+
headers2[key] = val[i];
|
|
9060
9060
|
}
|
|
9061
9061
|
}
|
|
9062
|
-
} else if (
|
|
9063
|
-
|
|
9062
|
+
} else if (headers2[key]) {
|
|
9063
|
+
headers2[key] += `, ${val}`;
|
|
9064
9064
|
} else {
|
|
9065
|
-
|
|
9065
|
+
headers2[key] = val;
|
|
9066
9066
|
}
|
|
9067
9067
|
}
|
|
9068
9068
|
let stream = null;
|
|
9069
9069
|
const { hostname, port } = client[kUrl];
|
|
9070
|
-
|
|
9071
|
-
|
|
9070
|
+
headers2[HTTP2_HEADER_AUTHORITY] = host || `${hostname}${port ? `:${port}` : ""}`;
|
|
9071
|
+
headers2[HTTP2_HEADER_METHOD] = method;
|
|
9072
9072
|
const abort = (err) => {
|
|
9073
9073
|
if (request2.aborted || request2.completed) {
|
|
9074
9074
|
return;
|
|
@@ -9100,19 +9100,19 @@ var require_client_h2 = __commonJS({
|
|
|
9100
9100
|
session.unref();
|
|
9101
9101
|
return false;
|
|
9102
9102
|
}
|
|
9103
|
-
|
|
9104
|
-
|
|
9105
|
-
|
|
9103
|
+
headers2[HTTP2_HEADER_METHOD] = "CONNECT";
|
|
9104
|
+
headers2[HTTP2_HEADER_PROTOCOL] = "websocket";
|
|
9105
|
+
headers2[HTTP2_HEADER_PATH] = path;
|
|
9106
9106
|
if (protocol === "ws:" || protocol === "wss:") {
|
|
9107
|
-
|
|
9107
|
+
headers2[HTTP2_HEADER_SCHEME] = protocol === "ws:" ? "http" : "https";
|
|
9108
9108
|
} else {
|
|
9109
|
-
|
|
9109
|
+
headers2[HTTP2_HEADER_SCHEME] = protocol === "http:" ? "http" : "https";
|
|
9110
9110
|
}
|
|
9111
|
-
stream = session.request(
|
|
9111
|
+
stream = session.request(headers2, { endStream: false, signal });
|
|
9112
9112
|
stream[kHTTP2Stream] = true;
|
|
9113
9113
|
++session[kOpenStreams];
|
|
9114
|
-
stream.once("response", (
|
|
9115
|
-
const { [HTTP2_HEADER_STATUS]: statusCode, ...realHeaders } =
|
|
9114
|
+
stream.once("response", (headers3, _flags) => {
|
|
9115
|
+
const { [HTTP2_HEADER_STATUS]: statusCode, ...realHeaders } = headers3;
|
|
9116
9116
|
try {
|
|
9117
9117
|
request2.onUpgrade(statusCode, parseH2Headers(realHeaders), stream);
|
|
9118
9118
|
} catch (err) {
|
|
@@ -9133,11 +9133,11 @@ var require_client_h2 = __commonJS({
|
|
|
9133
9133
|
stream.setTimeout(headersTimeout);
|
|
9134
9134
|
return true;
|
|
9135
9135
|
}
|
|
9136
|
-
stream = session.request(
|
|
9136
|
+
stream = session.request(headers2, { endStream: false, signal });
|
|
9137
9137
|
stream[kHTTP2Stream] = true;
|
|
9138
9138
|
++session[kOpenStreams];
|
|
9139
|
-
stream.on("response", (
|
|
9140
|
-
const { [HTTP2_HEADER_STATUS]: statusCode, ...realHeaders } =
|
|
9139
|
+
stream.on("response", (headers3) => {
|
|
9140
|
+
const { [HTTP2_HEADER_STATUS]: statusCode, ...realHeaders } = headers3;
|
|
9141
9141
|
try {
|
|
9142
9142
|
request2.onUpgrade(statusCode, parseH2Headers(realHeaders), stream);
|
|
9143
9143
|
} catch (err) {
|
|
@@ -9154,8 +9154,8 @@ var require_client_h2 = __commonJS({
|
|
|
9154
9154
|
stream.setTimeout(headersTimeout);
|
|
9155
9155
|
return true;
|
|
9156
9156
|
}
|
|
9157
|
-
|
|
9158
|
-
|
|
9157
|
+
headers2[HTTP2_HEADER_PATH] = path;
|
|
9158
|
+
headers2[HTTP2_HEADER_SCHEME] = protocol === "http:" ? "http" : "https";
|
|
9159
9159
|
const expectsPayload = method === "PUT" || method === "POST" || method === "PATCH";
|
|
9160
9160
|
if (body && typeof body.read === "function") {
|
|
9161
9161
|
body.read(0);
|
|
@@ -9164,7 +9164,7 @@ var require_client_h2 = __commonJS({
|
|
|
9164
9164
|
if (util.isFormDataLike(body)) {
|
|
9165
9165
|
extractBody ??= require_body().extractBody;
|
|
9166
9166
|
const [bodyStream, contentType] = extractBody(body);
|
|
9167
|
-
|
|
9167
|
+
headers2["content-type"] = contentType;
|
|
9168
9168
|
body = bodyStream.stream;
|
|
9169
9169
|
contentLength = bodyStream.length;
|
|
9170
9170
|
}
|
|
@@ -9183,25 +9183,25 @@ var require_client_h2 = __commonJS({
|
|
|
9183
9183
|
}
|
|
9184
9184
|
if (contentLength != null) {
|
|
9185
9185
|
assert(body || contentLength === 0, "no body must not have content length");
|
|
9186
|
-
|
|
9186
|
+
headers2[HTTP2_HEADER_CONTENT_LENGTH] = `${contentLength}`;
|
|
9187
9187
|
}
|
|
9188
9188
|
session.ref();
|
|
9189
9189
|
if (channels.sendHeaders.hasSubscribers) {
|
|
9190
|
-
let
|
|
9191
|
-
for (const key in
|
|
9192
|
-
|
|
9190
|
+
let header2 = "";
|
|
9191
|
+
for (const key in headers2) {
|
|
9192
|
+
header2 += `${key}: ${headers2[key]}\r
|
|
9193
9193
|
`;
|
|
9194
9194
|
}
|
|
9195
|
-
channels.sendHeaders.publish({ request: request2, headers:
|
|
9195
|
+
channels.sendHeaders.publish({ request: request2, headers: header2, socket: session[kSocket] });
|
|
9196
9196
|
}
|
|
9197
9197
|
const shouldEndStream = method === "GET" || method === "HEAD" || body === null;
|
|
9198
9198
|
if (expectContinue) {
|
|
9199
|
-
|
|
9200
|
-
stream = session.request(
|
|
9199
|
+
headers2[HTTP2_HEADER_EXPECT] = "100-continue";
|
|
9200
|
+
stream = session.request(headers2, { endStream: shouldEndStream, signal });
|
|
9201
9201
|
stream[kHTTP2Stream] = true;
|
|
9202
9202
|
stream.once("continue", writeBodyH2);
|
|
9203
9203
|
} else {
|
|
9204
|
-
stream = session.request(
|
|
9204
|
+
stream = session.request(headers2, {
|
|
9205
9205
|
endStream: shouldEndStream,
|
|
9206
9206
|
signal
|
|
9207
9207
|
});
|
|
@@ -9211,8 +9211,8 @@ var require_client_h2 = __commonJS({
|
|
|
9211
9211
|
++session[kOpenStreams];
|
|
9212
9212
|
stream.setTimeout(headersTimeout);
|
|
9213
9213
|
let responseReceived = false;
|
|
9214
|
-
stream.once("response", (
|
|
9215
|
-
const { [HTTP2_HEADER_STATUS]: statusCode, ...realHeaders } =
|
|
9214
|
+
stream.once("response", (headers3) => {
|
|
9215
|
+
const { [HTTP2_HEADER_STATUS]: statusCode, ...realHeaders } = headers3;
|
|
9216
9216
|
request2.onResponseStarted();
|
|
9217
9217
|
responseReceived = true;
|
|
9218
9218
|
stream.setTimeout(bodyTimeout);
|
|
@@ -9432,12 +9432,12 @@ var require_client_h2 = __commonJS({
|
|
|
9432
9432
|
cb();
|
|
9433
9433
|
}
|
|
9434
9434
|
}
|
|
9435
|
-
const waitForDrain = () => new Promise((
|
|
9435
|
+
const waitForDrain = () => new Promise((resolve4, reject) => {
|
|
9436
9436
|
assert(callback === null);
|
|
9437
9437
|
if (socket[kError]) {
|
|
9438
9438
|
reject(socket[kError]);
|
|
9439
9439
|
} else {
|
|
9440
|
-
callback =
|
|
9440
|
+
callback = resolve4;
|
|
9441
9441
|
}
|
|
9442
9442
|
});
|
|
9443
9443
|
h2stream.on("close", onDrain).on("drain", onDrain);
|
|
@@ -9754,16 +9754,16 @@ var require_client = __commonJS({
|
|
|
9754
9754
|
return this[kNeedDrain] < 2;
|
|
9755
9755
|
}
|
|
9756
9756
|
[kClose]() {
|
|
9757
|
-
return new Promise((
|
|
9757
|
+
return new Promise((resolve4) => {
|
|
9758
9758
|
if (this[kSize]) {
|
|
9759
|
-
this[kClosedResolve] =
|
|
9759
|
+
this[kClosedResolve] = resolve4;
|
|
9760
9760
|
} else {
|
|
9761
|
-
|
|
9761
|
+
resolve4(null);
|
|
9762
9762
|
}
|
|
9763
9763
|
});
|
|
9764
9764
|
}
|
|
9765
9765
|
[kDestroy](err) {
|
|
9766
|
-
return new Promise((
|
|
9766
|
+
return new Promise((resolve4) => {
|
|
9767
9767
|
const requests = this[kQueue].splice(this[kPendingIdx]);
|
|
9768
9768
|
for (let i = 0; i < requests.length; i++) {
|
|
9769
9769
|
const request2 = requests[i];
|
|
@@ -9776,7 +9776,7 @@ var require_client = __commonJS({
|
|
|
9776
9776
|
this[kClosedResolve]();
|
|
9777
9777
|
this[kClosedResolve] = null;
|
|
9778
9778
|
}
|
|
9779
|
-
|
|
9779
|
+
resolve4(null);
|
|
9780
9780
|
};
|
|
9781
9781
|
if (this[kHTTPContext]) {
|
|
9782
9782
|
this[kHTTPContext].destroy(err, callback);
|
|
@@ -10183,8 +10183,8 @@ var require_pool_base = __commonJS({
|
|
|
10183
10183
|
}
|
|
10184
10184
|
return Promise.all(closeAll);
|
|
10185
10185
|
} else {
|
|
10186
|
-
return new Promise((
|
|
10187
|
-
this[kClosedResolve] =
|
|
10186
|
+
return new Promise((resolve4) => {
|
|
10187
|
+
this[kClosedResolve] = resolve4;
|
|
10188
10188
|
});
|
|
10189
10189
|
}
|
|
10190
10190
|
}
|
|
@@ -11306,7 +11306,7 @@ var require_socks5_proxy_agent = __commonJS({
|
|
|
11306
11306
|
const proxyHost = this[kProxyUrl].hostname;
|
|
11307
11307
|
const proxyPort = parseInt(this[kProxyUrl].port) || 1080;
|
|
11308
11308
|
debug("creating SOCKS5 connection to", proxyHost, proxyPort);
|
|
11309
|
-
const socket = await new Promise((
|
|
11309
|
+
const socket = await new Promise((resolve4, reject) => {
|
|
11310
11310
|
this[kConnector]({
|
|
11311
11311
|
hostname: proxyHost,
|
|
11312
11312
|
host: proxyHost,
|
|
@@ -11316,7 +11316,7 @@ var require_socks5_proxy_agent = __commonJS({
|
|
|
11316
11316
|
if (err) {
|
|
11317
11317
|
reject(err);
|
|
11318
11318
|
} else {
|
|
11319
|
-
|
|
11319
|
+
resolve4(socket2);
|
|
11320
11320
|
}
|
|
11321
11321
|
});
|
|
11322
11322
|
});
|
|
@@ -11326,14 +11326,14 @@ var require_socks5_proxy_agent = __commonJS({
|
|
|
11326
11326
|
socket.destroy();
|
|
11327
11327
|
});
|
|
11328
11328
|
await socks5Client.handshake();
|
|
11329
|
-
await new Promise((
|
|
11329
|
+
await new Promise((resolve4, reject) => {
|
|
11330
11330
|
const timeout = setTimeout(() => {
|
|
11331
11331
|
reject(new Error("SOCKS5 authentication timeout"));
|
|
11332
11332
|
}, 5e3);
|
|
11333
11333
|
const onAuthenticated = () => {
|
|
11334
11334
|
clearTimeout(timeout);
|
|
11335
11335
|
socks5Client.removeListener("error", onError);
|
|
11336
|
-
|
|
11336
|
+
resolve4();
|
|
11337
11337
|
};
|
|
11338
11338
|
const onError = (err) => {
|
|
11339
11339
|
clearTimeout(timeout);
|
|
@@ -11342,14 +11342,14 @@ var require_socks5_proxy_agent = __commonJS({
|
|
|
11342
11342
|
};
|
|
11343
11343
|
if (socks5Client.state === STATES.AUTHENTICATED) {
|
|
11344
11344
|
clearTimeout(timeout);
|
|
11345
|
-
|
|
11345
|
+
resolve4();
|
|
11346
11346
|
} else {
|
|
11347
11347
|
socks5Client.once("authenticated", onAuthenticated);
|
|
11348
11348
|
socks5Client.once("error", onError);
|
|
11349
11349
|
}
|
|
11350
11350
|
});
|
|
11351
11351
|
await socks5Client.connect(targetHost, targetPort);
|
|
11352
|
-
await new Promise((
|
|
11352
|
+
await new Promise((resolve4, reject) => {
|
|
11353
11353
|
const timeout = setTimeout(() => {
|
|
11354
11354
|
reject(new Error("SOCKS5 connection timeout"));
|
|
11355
11355
|
}, 5e3);
|
|
@@ -11357,7 +11357,7 @@ var require_socks5_proxy_agent = __commonJS({
|
|
|
11357
11357
|
debug("SOCKS5 tunnel established to", targetHost, targetPort, "via", info);
|
|
11358
11358
|
clearTimeout(timeout);
|
|
11359
11359
|
socks5Client.removeListener("error", onError);
|
|
11360
|
-
|
|
11360
|
+
resolve4();
|
|
11361
11361
|
};
|
|
11362
11362
|
const onError = (err) => {
|
|
11363
11363
|
clearTimeout(timeout);
|
|
@@ -11400,8 +11400,8 @@ var require_socks5_proxy_agent = __commonJS({
|
|
|
11400
11400
|
socket,
|
|
11401
11401
|
servername: this[kRequestTls]?.servername || targetHost
|
|
11402
11402
|
});
|
|
11403
|
-
await new Promise((
|
|
11404
|
-
finalSocket.once("secureConnect",
|
|
11403
|
+
await new Promise((resolve4, reject) => {
|
|
11404
|
+
finalSocket.once("secureConnect", resolve4);
|
|
11405
11405
|
finalSocket.once("error", reject);
|
|
11406
11406
|
});
|
|
11407
11407
|
}
|
|
@@ -11485,12 +11485,12 @@ var require_proxy_agent = __commonJS({
|
|
|
11485
11485
|
}
|
|
11486
11486
|
var Http1ProxyWrapper = class extends DispatcherBase {
|
|
11487
11487
|
#client;
|
|
11488
|
-
constructor(proxyUrl, { headers = {}, connect, factory }) {
|
|
11488
|
+
constructor(proxyUrl, { headers: headers2 = {}, connect, factory }) {
|
|
11489
11489
|
if (!proxyUrl) {
|
|
11490
11490
|
throw new InvalidArgumentError("Proxy URL is mandatory");
|
|
11491
11491
|
}
|
|
11492
11492
|
super();
|
|
11493
|
-
this[kProxyHeaders] =
|
|
11493
|
+
this[kProxyHeaders] = headers2;
|
|
11494
11494
|
if (factory) {
|
|
11495
11495
|
this.#client = factory(proxyUrl, { connect });
|
|
11496
11496
|
} else {
|
|
@@ -11511,14 +11511,14 @@ var require_proxy_agent = __commonJS({
|
|
|
11511
11511
|
const {
|
|
11512
11512
|
origin,
|
|
11513
11513
|
path = "/",
|
|
11514
|
-
headers = {}
|
|
11514
|
+
headers: headers2 = {}
|
|
11515
11515
|
} = opts;
|
|
11516
11516
|
opts.path = origin + path;
|
|
11517
|
-
if (!("host" in
|
|
11517
|
+
if (!("host" in headers2) && !("Host" in headers2)) {
|
|
11518
11518
|
const { host } = new URL(origin);
|
|
11519
|
-
|
|
11519
|
+
headers2.host = host;
|
|
11520
11520
|
}
|
|
11521
|
-
opts.headers = { ...this[kProxyHeaders], ...
|
|
11521
|
+
opts.headers = { ...this[kProxyHeaders], ...headers2 };
|
|
11522
11522
|
return this.#client[kDispatch](opts, handler);
|
|
11523
11523
|
}
|
|
11524
11524
|
[kClose]() {
|
|
@@ -11644,16 +11644,16 @@ var require_proxy_agent = __commonJS({
|
|
|
11644
11644
|
});
|
|
11645
11645
|
}
|
|
11646
11646
|
dispatch(opts, handler) {
|
|
11647
|
-
const
|
|
11648
|
-
throwIfProxyAuthIsSent(
|
|
11649
|
-
if (
|
|
11647
|
+
const headers2 = buildHeaders(opts.headers);
|
|
11648
|
+
throwIfProxyAuthIsSent(headers2);
|
|
11649
|
+
if (headers2 && !("host" in headers2) && !("Host" in headers2)) {
|
|
11650
11650
|
const { host } = new URL(opts.origin);
|
|
11651
|
-
|
|
11651
|
+
headers2.host = host;
|
|
11652
11652
|
}
|
|
11653
11653
|
return this[kAgent].dispatch(
|
|
11654
11654
|
{
|
|
11655
11655
|
...opts,
|
|
11656
|
-
headers
|
|
11656
|
+
headers: headers2
|
|
11657
11657
|
},
|
|
11658
11658
|
handler
|
|
11659
11659
|
);
|
|
@@ -11686,18 +11686,18 @@ var require_proxy_agent = __commonJS({
|
|
|
11686
11686
|
return Promise.all(promises);
|
|
11687
11687
|
}
|
|
11688
11688
|
};
|
|
11689
|
-
function buildHeaders(
|
|
11690
|
-
if (Array.isArray(
|
|
11689
|
+
function buildHeaders(headers2) {
|
|
11690
|
+
if (Array.isArray(headers2)) {
|
|
11691
11691
|
const headersPair = {};
|
|
11692
|
-
for (let i = 0; i <
|
|
11693
|
-
headersPair[
|
|
11692
|
+
for (let i = 0; i < headers2.length; i += 2) {
|
|
11693
|
+
headersPair[headers2[i]] = headers2[i + 1];
|
|
11694
11694
|
}
|
|
11695
11695
|
return headersPair;
|
|
11696
11696
|
}
|
|
11697
|
-
return
|
|
11697
|
+
return headers2;
|
|
11698
11698
|
}
|
|
11699
|
-
function throwIfProxyAuthIsSent(
|
|
11700
|
-
const existProxyAuth =
|
|
11699
|
+
function throwIfProxyAuthIsSent(headers2) {
|
|
11700
|
+
const existProxyAuth = headers2 && Object.keys(headers2).find((key) => key.toLowerCase() === "proxy-authorization");
|
|
11701
11701
|
if (existProxyAuth) {
|
|
11702
11702
|
throw new InvalidArgumentError("Proxy-Authorization should be sent in ProxyAgent constructor");
|
|
11703
11703
|
}
|
|
@@ -11846,8 +11846,8 @@ var require_retry_handler = __commonJS({
|
|
|
11846
11846
|
const retryTime = new Date(retryAfter).getTime();
|
|
11847
11847
|
return isNaN(retryTime) ? 0 : retryTime - Date.now();
|
|
11848
11848
|
}
|
|
11849
|
-
function validatePartialResponseContentLength(
|
|
11850
|
-
const contentLength =
|
|
11849
|
+
function validatePartialResponseContentLength(headers2, range, statusCode, retryCount) {
|
|
11850
|
+
const contentLength = headers2["content-length"];
|
|
11851
11851
|
if (contentLength == null) {
|
|
11852
11852
|
return;
|
|
11853
11853
|
}
|
|
@@ -11858,7 +11858,7 @@ var require_retry_handler = __commonJS({
|
|
|
11858
11858
|
const expectedLength = range.end - range.start + 1;
|
|
11859
11859
|
if (!Number.isFinite(length) || length !== expectedLength) {
|
|
11860
11860
|
throw new RequestRetryError("Content-Length mismatch", statusCode, {
|
|
11861
|
-
headers,
|
|
11861
|
+
headers: headers2,
|
|
11862
11862
|
data: { count: retryCount }
|
|
11863
11863
|
});
|
|
11864
11864
|
}
|
|
@@ -11968,15 +11968,15 @@ var require_retry_handler = __commonJS({
|
|
|
11968
11968
|
this.etag = null;
|
|
11969
11969
|
this.controllerProxy = new RetryController();
|
|
11970
11970
|
}
|
|
11971
|
-
onResponseStartWithRetry(controller, statusCode,
|
|
11971
|
+
onResponseStartWithRetry(controller, statusCode, headers2, statusMessage, err) {
|
|
11972
11972
|
if (this.retryOpts.throwOnError) {
|
|
11973
11973
|
if (this.retryOpts.statusCodes.includes(statusCode) === false) {
|
|
11974
11974
|
if (this.headersSent) {
|
|
11975
11975
|
this.handler.onResponseError?.(this.controllerProxy, err);
|
|
11976
11976
|
} else {
|
|
11977
11977
|
this.headersSent = true;
|
|
11978
|
-
this.checkpointResponseEnd(
|
|
11979
|
-
this.handler.onResponseStart?.(this.controllerProxy, statusCode,
|
|
11978
|
+
this.checkpointResponseEnd(headers2);
|
|
11979
|
+
this.handler.onResponseStart?.(this.controllerProxy, statusCode, headers2, statusMessage);
|
|
11980
11980
|
}
|
|
11981
11981
|
} else {
|
|
11982
11982
|
this.error = err;
|
|
@@ -11985,8 +11985,8 @@ var require_retry_handler = __commonJS({
|
|
|
11985
11985
|
}
|
|
11986
11986
|
if (isDisturbed(this.opts.body)) {
|
|
11987
11987
|
this.headersSent = true;
|
|
11988
|
-
this.checkpointResponseEnd(
|
|
11989
|
-
this.handler.onResponseStart?.(this.controllerProxy, statusCode,
|
|
11988
|
+
this.checkpointResponseEnd(headers2);
|
|
11989
|
+
this.handler.onResponseStart?.(this.controllerProxy, statusCode, headers2, statusMessage);
|
|
11990
11990
|
return;
|
|
11991
11991
|
}
|
|
11992
11992
|
function shouldRetry(passedErr) {
|
|
@@ -11995,8 +11995,8 @@ var require_retry_handler = __commonJS({
|
|
|
11995
11995
|
this.handler.onResponseError?.(this.controllerProxy, passedErr);
|
|
11996
11996
|
} else {
|
|
11997
11997
|
this.headersSent = true;
|
|
11998
|
-
this.checkpointResponseEnd(
|
|
11999
|
-
this.handler.onResponseStart?.(this.controllerProxy, statusCode,
|
|
11998
|
+
this.checkpointResponseEnd(headers2);
|
|
11999
|
+
this.handler.onResponseStart?.(this.controllerProxy, statusCode, headers2, statusMessage);
|
|
12000
12000
|
}
|
|
12001
12001
|
controller.resume();
|
|
12002
12002
|
return;
|
|
@@ -12014,9 +12014,9 @@ var require_retry_handler = __commonJS({
|
|
|
12014
12014
|
shouldRetry.bind(this)
|
|
12015
12015
|
);
|
|
12016
12016
|
}
|
|
12017
|
-
checkpointResponseEnd(
|
|
12017
|
+
checkpointResponseEnd(headers2) {
|
|
12018
12018
|
if (this.end == null && this.opts.method !== "HEAD") {
|
|
12019
|
-
const contentLength =
|
|
12019
|
+
const contentLength = headers2["content-length"];
|
|
12020
12020
|
this.end = contentLength != null ? Number(contentLength) - 1 : null;
|
|
12021
12021
|
assert(
|
|
12022
12022
|
this.end == null || Number.isFinite(this.end),
|
|
@@ -12031,11 +12031,11 @@ var require_retry_handler = __commonJS({
|
|
|
12031
12031
|
this.handler.onRequestStart?.(this.controllerProxy, context);
|
|
12032
12032
|
}
|
|
12033
12033
|
}
|
|
12034
|
-
onRequestUpgrade(_controller, statusCode,
|
|
12035
|
-
this.handler.onRequestUpgrade?.(this.controllerProxy, statusCode,
|
|
12034
|
+
onRequestUpgrade(_controller, statusCode, headers2, socket) {
|
|
12035
|
+
this.handler.onRequestUpgrade?.(this.controllerProxy, statusCode, headers2, socket);
|
|
12036
12036
|
}
|
|
12037
12037
|
static [kRetryHandlerDefaultRetry](err, { state, opts }, cb) {
|
|
12038
|
-
const { statusCode, code, headers } = err;
|
|
12038
|
+
const { statusCode, code, headers: headers2 } = err;
|
|
12039
12039
|
const { method, retryOptions } = opts;
|
|
12040
12040
|
const {
|
|
12041
12041
|
maxRetries,
|
|
@@ -12063,52 +12063,52 @@ var require_retry_handler = __commonJS({
|
|
|
12063
12063
|
cb(err);
|
|
12064
12064
|
return;
|
|
12065
12065
|
}
|
|
12066
|
-
let retryAfterHeader =
|
|
12066
|
+
let retryAfterHeader = headers2?.["retry-after"];
|
|
12067
12067
|
if (retryAfterHeader) {
|
|
12068
12068
|
retryAfterHeader = Number(retryAfterHeader);
|
|
12069
|
-
retryAfterHeader = Number.isNaN(retryAfterHeader) ? calculateRetryAfterHeader(
|
|
12069
|
+
retryAfterHeader = Number.isNaN(retryAfterHeader) ? calculateRetryAfterHeader(headers2["retry-after"]) : retryAfterHeader * 1e3;
|
|
12070
12070
|
}
|
|
12071
12071
|
const retryTimeout = retryAfterHeader > 0 ? Math.min(retryAfterHeader, maxTimeout) : Math.min(minTimeout * timeoutFactor ** (counter2 - 1), maxTimeout);
|
|
12072
12072
|
setTimeout(() => cb(null), retryTimeout);
|
|
12073
12073
|
}
|
|
12074
|
-
onResponseStart(controller, statusCode,
|
|
12074
|
+
onResponseStart(controller, statusCode, headers2, statusMessage) {
|
|
12075
12075
|
this.error = null;
|
|
12076
12076
|
this.retryCount += 1;
|
|
12077
12077
|
if (statusCode >= 300) {
|
|
12078
12078
|
const err = new RequestRetryError("Request failed", statusCode, {
|
|
12079
|
-
headers,
|
|
12079
|
+
headers: headers2,
|
|
12080
12080
|
data: {
|
|
12081
12081
|
count: this.retryCount
|
|
12082
12082
|
}
|
|
12083
12083
|
});
|
|
12084
|
-
this.onResponseStartWithRetry(controller, statusCode,
|
|
12084
|
+
this.onResponseStartWithRetry(controller, statusCode, headers2, statusMessage, err);
|
|
12085
12085
|
return;
|
|
12086
12086
|
}
|
|
12087
12087
|
if (this.headersSent) {
|
|
12088
12088
|
if (statusCode !== 206 && (this.start > 0 || statusCode !== 200)) {
|
|
12089
12089
|
throw new RequestRetryError("server does not support the range header and the payload was partially consumed", statusCode, {
|
|
12090
|
-
headers,
|
|
12090
|
+
headers: headers2,
|
|
12091
12091
|
data: { count: this.retryCount }
|
|
12092
12092
|
});
|
|
12093
12093
|
}
|
|
12094
|
-
const contentRange = parseRangeHeader(
|
|
12094
|
+
const contentRange = parseRangeHeader(headers2["content-range"]);
|
|
12095
12095
|
if (!contentRange) {
|
|
12096
12096
|
throw new RequestRetryError("Content-Range mismatch", statusCode, {
|
|
12097
|
-
headers,
|
|
12097
|
+
headers: headers2,
|
|
12098
12098
|
data: { count: this.retryCount }
|
|
12099
12099
|
});
|
|
12100
12100
|
}
|
|
12101
|
-
if (this.etag != null && this.etag !==
|
|
12101
|
+
if (this.etag != null && this.etag !== headers2.etag) {
|
|
12102
12102
|
throw new RequestRetryError("ETag mismatch", statusCode, {
|
|
12103
|
-
headers,
|
|
12103
|
+
headers: headers2,
|
|
12104
12104
|
data: { count: this.retryCount }
|
|
12105
12105
|
});
|
|
12106
12106
|
}
|
|
12107
|
-
validatePartialResponseContentLength(
|
|
12107
|
+
validatePartialResponseContentLength(headers2, contentRange, statusCode, this.retryCount);
|
|
12108
12108
|
const { start, size, end = size ? size - 1 : null } = contentRange;
|
|
12109
12109
|
if (this.start !== start || this.end != null && this.end !== end) {
|
|
12110
12110
|
throw new RequestRetryError("Content-Range mismatch", statusCode, {
|
|
12111
|
-
headers,
|
|
12111
|
+
headers: headers2,
|
|
12112
12112
|
data: { count: this.retryCount }
|
|
12113
12113
|
});
|
|
12114
12114
|
}
|
|
@@ -12116,18 +12116,18 @@ var require_retry_handler = __commonJS({
|
|
|
12116
12116
|
}
|
|
12117
12117
|
if (this.end == null) {
|
|
12118
12118
|
if (statusCode === 206) {
|
|
12119
|
-
const range = parseRangeHeader(
|
|
12119
|
+
const range = parseRangeHeader(headers2["content-range"]);
|
|
12120
12120
|
if (range == null) {
|
|
12121
12121
|
this.headersSent = true;
|
|
12122
12122
|
this.handler.onResponseStart?.(
|
|
12123
12123
|
this.controllerProxy,
|
|
12124
12124
|
statusCode,
|
|
12125
|
-
|
|
12125
|
+
headers2,
|
|
12126
12126
|
statusMessage
|
|
12127
12127
|
);
|
|
12128
12128
|
return;
|
|
12129
12129
|
}
|
|
12130
|
-
validatePartialResponseContentLength(
|
|
12130
|
+
validatePartialResponseContentLength(headers2, range, statusCode, this.retryCount);
|
|
12131
12131
|
const { start, size, end = size ? size - 1 : null } = range;
|
|
12132
12132
|
assert(
|
|
12133
12133
|
start != null && Number.isFinite(start),
|
|
@@ -12138,7 +12138,7 @@ var require_retry_handler = __commonJS({
|
|
|
12138
12138
|
this.end = end;
|
|
12139
12139
|
}
|
|
12140
12140
|
if (this.end == null) {
|
|
12141
|
-
const contentLength =
|
|
12141
|
+
const contentLength = headers2["content-length"];
|
|
12142
12142
|
this.end = contentLength != null ? Number(contentLength) - 1 : null;
|
|
12143
12143
|
}
|
|
12144
12144
|
assert(Number.isFinite(this.start));
|
|
@@ -12147,7 +12147,7 @@ var require_retry_handler = __commonJS({
|
|
|
12147
12147
|
"invalid content-length"
|
|
12148
12148
|
);
|
|
12149
12149
|
this.resume = true;
|
|
12150
|
-
this.etag =
|
|
12150
|
+
this.etag = headers2.etag != null ? headers2.etag : null;
|
|
12151
12151
|
if (this.etag != null && this.etag[0] === "W" && this.etag[1] === "/") {
|
|
12152
12152
|
this.etag = null;
|
|
12153
12153
|
}
|
|
@@ -12155,12 +12155,12 @@ var require_retry_handler = __commonJS({
|
|
|
12155
12155
|
this.handler.onResponseStart?.(
|
|
12156
12156
|
this.controllerProxy,
|
|
12157
12157
|
statusCode,
|
|
12158
|
-
|
|
12158
|
+
headers2,
|
|
12159
12159
|
statusMessage
|
|
12160
12160
|
);
|
|
12161
12161
|
} else {
|
|
12162
12162
|
throw new RequestRetryError("Request failed", statusCode, {
|
|
12163
|
-
headers,
|
|
12163
|
+
headers: headers2,
|
|
12164
12164
|
data: { count: this.retryCount }
|
|
12165
12165
|
});
|
|
12166
12166
|
}
|
|
@@ -12184,15 +12184,15 @@ var require_retry_handler = __commonJS({
|
|
|
12184
12184
|
}
|
|
12185
12185
|
retry() {
|
|
12186
12186
|
if (this.start !== 0) {
|
|
12187
|
-
const
|
|
12187
|
+
const headers2 = { range: `bytes=${this.start}-${this.end ?? ""}` };
|
|
12188
12188
|
if (this.etag != null) {
|
|
12189
|
-
|
|
12189
|
+
headers2["if-match"] = this.etag;
|
|
12190
12190
|
}
|
|
12191
12191
|
this.opts = {
|
|
12192
12192
|
...this.opts,
|
|
12193
12193
|
headers: {
|
|
12194
12194
|
...this.opts.headers,
|
|
12195
|
-
...
|
|
12195
|
+
...headers2
|
|
12196
12196
|
}
|
|
12197
12197
|
};
|
|
12198
12198
|
}
|
|
@@ -12534,7 +12534,7 @@ var require_readable = __commonJS({
|
|
|
12534
12534
|
if (this._readableState.closeEmitted) {
|
|
12535
12535
|
return Promise.resolve(null);
|
|
12536
12536
|
}
|
|
12537
|
-
return new Promise((
|
|
12537
|
+
return new Promise((resolve4, reject) => {
|
|
12538
12538
|
if (this[kContentLength] && this[kContentLength] > limit || this[kBytesRead] > limit) {
|
|
12539
12539
|
this.destroy(new AbortError());
|
|
12540
12540
|
}
|
|
@@ -12548,11 +12548,11 @@ var require_readable = __commonJS({
|
|
|
12548
12548
|
if (signal.aborted) {
|
|
12549
12549
|
reject(signal.reason ?? new AbortError());
|
|
12550
12550
|
} else {
|
|
12551
|
-
|
|
12551
|
+
resolve4(null);
|
|
12552
12552
|
}
|
|
12553
12553
|
});
|
|
12554
12554
|
} else {
|
|
12555
|
-
this.on("close",
|
|
12555
|
+
this.on("close", resolve4);
|
|
12556
12556
|
}
|
|
12557
12557
|
this.on("error", noop).on("data", () => {
|
|
12558
12558
|
if (this[kBytesRead] > limit) {
|
|
@@ -12580,7 +12580,7 @@ var require_readable = __commonJS({
|
|
|
12580
12580
|
}
|
|
12581
12581
|
function consume(stream, type) {
|
|
12582
12582
|
assert(!stream[kConsume]);
|
|
12583
|
-
return new Promise((
|
|
12583
|
+
return new Promise((resolve4, reject) => {
|
|
12584
12584
|
if (isUnusable(stream)) {
|
|
12585
12585
|
const rState = stream._readableState;
|
|
12586
12586
|
if (rState.destroyed && rState.closeEmitted === false) {
|
|
@@ -12595,7 +12595,7 @@ var require_readable = __commonJS({
|
|
|
12595
12595
|
stream[kConsume] = {
|
|
12596
12596
|
type,
|
|
12597
12597
|
stream,
|
|
12598
|
-
resolve:
|
|
12598
|
+
resolve: resolve4,
|
|
12599
12599
|
reject,
|
|
12600
12600
|
length: 0,
|
|
12601
12601
|
body: []
|
|
@@ -12669,18 +12669,18 @@ var require_readable = __commonJS({
|
|
|
12669
12669
|
return buffer;
|
|
12670
12670
|
}
|
|
12671
12671
|
function consumeEnd(consume2, encoding) {
|
|
12672
|
-
const { type, body, resolve:
|
|
12672
|
+
const { type, body, resolve: resolve4, stream, length } = consume2;
|
|
12673
12673
|
try {
|
|
12674
12674
|
if (type === "text") {
|
|
12675
|
-
|
|
12675
|
+
resolve4(chunksDecode(body, length, encoding));
|
|
12676
12676
|
} else if (type === "json") {
|
|
12677
|
-
|
|
12677
|
+
resolve4(JSON.parse(chunksDecode(body, length, encoding)));
|
|
12678
12678
|
} else if (type === "arrayBuffer") {
|
|
12679
|
-
|
|
12679
|
+
resolve4(chunksConcat(body, length).buffer);
|
|
12680
12680
|
} else if (type === "blob") {
|
|
12681
|
-
|
|
12681
|
+
resolve4(new Blob(body, { type: stream[kContentType] }));
|
|
12682
12682
|
} else if (type === "bytes") {
|
|
12683
|
-
|
|
12683
|
+
resolve4(chunksConcat(body, length));
|
|
12684
12684
|
}
|
|
12685
12685
|
consumeFinish(consume2);
|
|
12686
12686
|
} catch (err) {
|
|
@@ -12791,14 +12791,14 @@ var require_api_request = __commonJS({
|
|
|
12791
12791
|
}
|
|
12792
12792
|
onHeaders(statusCode, rawHeaders, resume, statusMessage) {
|
|
12793
12793
|
const { callback, opaque, abort, context, responseHeaders, highWaterMark } = this;
|
|
12794
|
-
const
|
|
12794
|
+
const headers2 = responseHeaders === "raw" ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders);
|
|
12795
12795
|
if (statusCode < 200) {
|
|
12796
12796
|
if (this.onInfo) {
|
|
12797
|
-
this.onInfo({ statusCode, headers });
|
|
12797
|
+
this.onInfo({ statusCode, headers: headers2 });
|
|
12798
12798
|
}
|
|
12799
12799
|
return;
|
|
12800
12800
|
}
|
|
12801
|
-
const parsedHeaders = responseHeaders === "raw" ? util.parseHeaders(rawHeaders) :
|
|
12801
|
+
const parsedHeaders = responseHeaders === "raw" ? util.parseHeaders(rawHeaders) : headers2;
|
|
12802
12802
|
const contentType = parsedHeaders["content-type"];
|
|
12803
12803
|
const contentLength = parsedHeaders["content-length"];
|
|
12804
12804
|
const res = new Readable({
|
|
@@ -12819,7 +12819,7 @@ var require_api_request = __commonJS({
|
|
|
12819
12819
|
this.runInAsyncScope(callback, null, null, {
|
|
12820
12820
|
statusCode,
|
|
12821
12821
|
statusText: statusMessage,
|
|
12822
|
-
headers,
|
|
12822
|
+
headers: headers2,
|
|
12823
12823
|
trailers: this.trailers,
|
|
12824
12824
|
opaque,
|
|
12825
12825
|
body: res,
|
|
@@ -12870,9 +12870,9 @@ var require_api_request = __commonJS({
|
|
|
12870
12870
|
};
|
|
12871
12871
|
function request2(opts, callback) {
|
|
12872
12872
|
if (callback === void 0) {
|
|
12873
|
-
return new Promise((
|
|
12873
|
+
return new Promise((resolve4, reject) => {
|
|
12874
12874
|
request2.call(this, opts, (err, data) => {
|
|
12875
|
-
return err ? reject(err) :
|
|
12875
|
+
return err ? reject(err) : resolve4(data);
|
|
12876
12876
|
});
|
|
12877
12877
|
});
|
|
12878
12878
|
}
|
|
@@ -13013,10 +13013,10 @@ var require_api_stream = __commonJS({
|
|
|
13013
13013
|
}
|
|
13014
13014
|
onHeaders(statusCode, rawHeaders, resume, statusMessage) {
|
|
13015
13015
|
const { factory, opaque, context, responseHeaders } = this;
|
|
13016
|
-
const
|
|
13016
|
+
const headers2 = responseHeaders === "raw" ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders);
|
|
13017
13017
|
if (statusCode < 200) {
|
|
13018
13018
|
if (this.onInfo) {
|
|
13019
|
-
this.onInfo({ statusCode, headers });
|
|
13019
|
+
this.onInfo({ statusCode, headers: headers2 });
|
|
13020
13020
|
}
|
|
13021
13021
|
return;
|
|
13022
13022
|
}
|
|
@@ -13026,7 +13026,7 @@ var require_api_stream = __commonJS({
|
|
|
13026
13026
|
}
|
|
13027
13027
|
const res = this.runInAsyncScope(factory, null, {
|
|
13028
13028
|
statusCode,
|
|
13029
|
-
headers,
|
|
13029
|
+
headers: headers2,
|
|
13030
13030
|
opaque,
|
|
13031
13031
|
context
|
|
13032
13032
|
});
|
|
@@ -13084,9 +13084,9 @@ var require_api_stream = __commonJS({
|
|
|
13084
13084
|
};
|
|
13085
13085
|
function stream(opts, factory, callback) {
|
|
13086
13086
|
if (callback === void 0) {
|
|
13087
|
-
return new Promise((
|
|
13087
|
+
return new Promise((resolve4, reject) => {
|
|
13088
13088
|
stream.call(this, opts, factory, (err, data) => {
|
|
13089
|
-
return err ? reject(err) :
|
|
13089
|
+
return err ? reject(err) : resolve4(data);
|
|
13090
13090
|
});
|
|
13091
13091
|
});
|
|
13092
13092
|
}
|
|
@@ -13236,8 +13236,8 @@ var require_api_pipeline = __commonJS({
|
|
|
13236
13236
|
const { opaque, handler, context } = this;
|
|
13237
13237
|
if (statusCode < 200) {
|
|
13238
13238
|
if (this.onInfo) {
|
|
13239
|
-
const
|
|
13240
|
-
this.onInfo({ statusCode, headers });
|
|
13239
|
+
const headers2 = this.responseHeaders === "raw" ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders);
|
|
13240
|
+
this.onInfo({ statusCode, headers: headers2 });
|
|
13241
13241
|
}
|
|
13242
13242
|
return;
|
|
13243
13243
|
}
|
|
@@ -13245,10 +13245,10 @@ var require_api_pipeline = __commonJS({
|
|
|
13245
13245
|
let body;
|
|
13246
13246
|
try {
|
|
13247
13247
|
this.handler = null;
|
|
13248
|
-
const
|
|
13248
|
+
const headers2 = this.responseHeaders === "raw" ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders);
|
|
13249
13249
|
body = this.runInAsyncScope(handler, null, {
|
|
13250
13250
|
statusCode,
|
|
13251
|
-
headers,
|
|
13251
|
+
headers: headers2,
|
|
13252
13252
|
opaque,
|
|
13253
13253
|
body: this.res,
|
|
13254
13254
|
context
|
|
@@ -13353,9 +13353,9 @@ var require_api_upgrade = __commonJS({
|
|
|
13353
13353
|
const { callback, opaque, context } = this;
|
|
13354
13354
|
removeSignal(this);
|
|
13355
13355
|
this.callback = null;
|
|
13356
|
-
const
|
|
13356
|
+
const headers2 = this.responseHeaders === "raw" ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders);
|
|
13357
13357
|
this.runInAsyncScope(callback, null, null, {
|
|
13358
|
-
headers,
|
|
13358
|
+
headers: headers2,
|
|
13359
13359
|
socket,
|
|
13360
13360
|
opaque,
|
|
13361
13361
|
context
|
|
@@ -13374,9 +13374,9 @@ var require_api_upgrade = __commonJS({
|
|
|
13374
13374
|
};
|
|
13375
13375
|
function upgrade(opts, callback) {
|
|
13376
13376
|
if (callback === void 0) {
|
|
13377
|
-
return new Promise((
|
|
13377
|
+
return new Promise((resolve4, reject) => {
|
|
13378
13378
|
upgrade.call(this, opts, (err, data) => {
|
|
13379
|
-
return err ? reject(err) :
|
|
13379
|
+
return err ? reject(err) : resolve4(data);
|
|
13380
13380
|
});
|
|
13381
13381
|
});
|
|
13382
13382
|
}
|
|
@@ -13444,13 +13444,13 @@ var require_api_connect = __commonJS({
|
|
|
13444
13444
|
const { callback, opaque, context } = this;
|
|
13445
13445
|
removeSignal(this);
|
|
13446
13446
|
this.callback = null;
|
|
13447
|
-
let
|
|
13448
|
-
if (
|
|
13449
|
-
|
|
13447
|
+
let headers2 = rawHeaders;
|
|
13448
|
+
if (headers2 != null) {
|
|
13449
|
+
headers2 = this.responseHeaders === "raw" ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders);
|
|
13450
13450
|
}
|
|
13451
13451
|
this.runInAsyncScope(callback, null, null, {
|
|
13452
13452
|
statusCode,
|
|
13453
|
-
headers,
|
|
13453
|
+
headers: headers2,
|
|
13454
13454
|
socket,
|
|
13455
13455
|
opaque,
|
|
13456
13456
|
context
|
|
@@ -13469,9 +13469,9 @@ var require_api_connect = __commonJS({
|
|
|
13469
13469
|
};
|
|
13470
13470
|
function connect(opts, callback) {
|
|
13471
13471
|
if (callback === void 0) {
|
|
13472
|
-
return new Promise((
|
|
13472
|
+
return new Promise((resolve4, reject) => {
|
|
13473
13473
|
connect.call(this, opts, (err, data) => {
|
|
13474
|
-
return err ? reject(err) :
|
|
13474
|
+
return err ? reject(err) : resolve4(data);
|
|
13475
13475
|
});
|
|
13476
13476
|
});
|
|
13477
13477
|
}
|
|
@@ -13599,50 +13599,50 @@ var require_mock_utils = __commonJS({
|
|
|
13599
13599
|
}
|
|
13600
13600
|
return false;
|
|
13601
13601
|
}
|
|
13602
|
-
function lowerCaseEntries(
|
|
13602
|
+
function lowerCaseEntries(headers2) {
|
|
13603
13603
|
return Object.fromEntries(
|
|
13604
|
-
Object.entries(
|
|
13604
|
+
Object.entries(headers2).map(([headerName, headerValue2]) => {
|
|
13605
13605
|
return [headerName.toLocaleLowerCase(), headerValue2];
|
|
13606
13606
|
})
|
|
13607
13607
|
);
|
|
13608
13608
|
}
|
|
13609
|
-
function getHeaderByName(
|
|
13610
|
-
if (Array.isArray(
|
|
13611
|
-
for (let i = 0; i <
|
|
13612
|
-
if (
|
|
13613
|
-
return
|
|
13609
|
+
function getHeaderByName(headers2, key) {
|
|
13610
|
+
if (Array.isArray(headers2)) {
|
|
13611
|
+
for (let i = 0; i < headers2.length; i += 2) {
|
|
13612
|
+
if (headers2[i].toLocaleLowerCase() === key.toLocaleLowerCase()) {
|
|
13613
|
+
return headers2[i + 1];
|
|
13614
13614
|
}
|
|
13615
13615
|
}
|
|
13616
13616
|
return void 0;
|
|
13617
|
-
} else if (typeof
|
|
13618
|
-
return
|
|
13617
|
+
} else if (typeof headers2.get === "function") {
|
|
13618
|
+
return headers2.get(key);
|
|
13619
13619
|
} else {
|
|
13620
|
-
return lowerCaseEntries(
|
|
13620
|
+
return lowerCaseEntries(headers2)[key.toLocaleLowerCase()];
|
|
13621
13621
|
}
|
|
13622
13622
|
}
|
|
13623
|
-
function buildHeadersFromArray(
|
|
13624
|
-
const clone =
|
|
13623
|
+
function buildHeadersFromArray(headers2) {
|
|
13624
|
+
const clone = headers2.slice();
|
|
13625
13625
|
const entries = [];
|
|
13626
13626
|
for (let index = 0; index < clone.length; index += 2) {
|
|
13627
13627
|
entries.push([clone[index], clone[index + 1]]);
|
|
13628
13628
|
}
|
|
13629
13629
|
return Object.fromEntries(entries);
|
|
13630
13630
|
}
|
|
13631
|
-
function matchHeaders(mockDispatch2,
|
|
13631
|
+
function matchHeaders(mockDispatch2, headers2) {
|
|
13632
13632
|
if (typeof mockDispatch2.headers === "function") {
|
|
13633
|
-
if (Array.isArray(
|
|
13634
|
-
|
|
13633
|
+
if (Array.isArray(headers2)) {
|
|
13634
|
+
headers2 = buildHeadersFromArray(headers2);
|
|
13635
13635
|
}
|
|
13636
|
-
return mockDispatch2.headers(
|
|
13636
|
+
return mockDispatch2.headers(headers2 ? lowerCaseEntries(headers2) : {});
|
|
13637
13637
|
}
|
|
13638
13638
|
if (typeof mockDispatch2.headers === "undefined") {
|
|
13639
13639
|
return true;
|
|
13640
13640
|
}
|
|
13641
|
-
if (typeof
|
|
13641
|
+
if (typeof headers2 !== "object" || typeof mockDispatch2.headers !== "object") {
|
|
13642
13642
|
return false;
|
|
13643
13643
|
}
|
|
13644
13644
|
for (const [matchHeaderName, matchHeaderValue] of Object.entries(mockDispatch2.headers)) {
|
|
13645
|
-
const headerValue2 = getHeaderByName(
|
|
13645
|
+
const headerValue2 = getHeaderByName(headers2, matchHeaderName);
|
|
13646
13646
|
if (!matchValue(matchHeaderValue, headerValue2)) {
|
|
13647
13647
|
return false;
|
|
13648
13648
|
}
|
|
@@ -13685,11 +13685,11 @@ var require_mock_utils = __commonJS({
|
|
|
13685
13685
|
qp.sort();
|
|
13686
13686
|
return [...pathSegments, qp.toString()].join("?");
|
|
13687
13687
|
}
|
|
13688
|
-
function matchKey(mockDispatch2, { path, method, body, headers }) {
|
|
13688
|
+
function matchKey(mockDispatch2, { path, method, body, headers: headers2 }) {
|
|
13689
13689
|
const pathMatch2 = matchValue(mockDispatch2.path, path);
|
|
13690
13690
|
const methodMatch = matchValue(mockDispatch2.method, method);
|
|
13691
13691
|
const bodyMatch = typeof mockDispatch2.body !== "undefined" ? matchValue(mockDispatch2.body, body) : true;
|
|
13692
|
-
const headersMatch = matchHeaders(mockDispatch2,
|
|
13692
|
+
const headersMatch = matchHeaders(mockDispatch2, headers2);
|
|
13693
13693
|
return pathMatch2 && methodMatch && bodyMatch && headersMatch;
|
|
13694
13694
|
}
|
|
13695
13695
|
function getResponseData(data) {
|
|
@@ -13727,8 +13727,8 @@ var require_mock_utils = __commonJS({
|
|
|
13727
13727
|
}
|
|
13728
13728
|
matchedMockDispatches = matchedMockDispatches.filter((mockDispatch2) => matchHeaders(mockDispatch2, key.headers));
|
|
13729
13729
|
if (matchedMockDispatches.length === 0) {
|
|
13730
|
-
const
|
|
13731
|
-
throw new MockNotMatchedError(`Mock dispatch not matched for headers '${
|
|
13730
|
+
const headers2 = typeof key.headers === "object" ? JSON.stringify(key.headers) : key.headers;
|
|
13731
|
+
throw new MockNotMatchedError(`Mock dispatch not matched for headers '${headers2}' on path '${resolvedPath}'`);
|
|
13732
13732
|
}
|
|
13733
13733
|
return matchedMockDispatches[0];
|
|
13734
13734
|
}
|
|
@@ -13761,12 +13761,12 @@ var require_mock_utils = __commonJS({
|
|
|
13761
13761
|
return path;
|
|
13762
13762
|
}
|
|
13763
13763
|
function buildKey(opts) {
|
|
13764
|
-
const { path, method, body, headers, query } = opts;
|
|
13764
|
+
const { path, method, body, headers: headers2, query } = opts;
|
|
13765
13765
|
return {
|
|
13766
13766
|
path,
|
|
13767
13767
|
method,
|
|
13768
13768
|
body,
|
|
13769
|
-
headers,
|
|
13769
|
+
headers: headers2,
|
|
13770
13770
|
query
|
|
13771
13771
|
};
|
|
13772
13772
|
}
|
|
@@ -13804,7 +13804,7 @@ var require_mock_utils = __commonJS({
|
|
|
13804
13804
|
if (mockDispatch2.data.callback) {
|
|
13805
13805
|
mockDispatch2.data = { ...mockDispatch2.data, ...mockDispatch2.data.callback(opts) };
|
|
13806
13806
|
}
|
|
13807
|
-
const { data: { statusCode, data, headers, trailers, error }, delay, persist } = mockDispatch2;
|
|
13807
|
+
const { data: { statusCode, data, headers: headers2, trailers, error }, delay, persist } = mockDispatch2;
|
|
13808
13808
|
const { timesInvoked, times } = mockDispatch2;
|
|
13809
13809
|
mockDispatch2.consumed = !persist && timesInvoked >= times;
|
|
13810
13810
|
mockDispatch2.pending = timesInvoked < times;
|
|
@@ -13848,7 +13848,7 @@ var require_mock_utils = __commonJS({
|
|
|
13848
13848
|
return;
|
|
13849
13849
|
}
|
|
13850
13850
|
const responseData = getResponseData(body);
|
|
13851
|
-
const responseHeaders = generateKeyValues(
|
|
13851
|
+
const responseHeaders = generateKeyValues(headers2);
|
|
13852
13852
|
const responseTrailers = generateKeyValues(trailers);
|
|
13853
13853
|
handler.onHeaders?.(statusCode, responseHeaders, resume, getStatusText(statusCode));
|
|
13854
13854
|
handler.onData?.(Buffer.from(responseData));
|
|
@@ -14023,9 +14023,9 @@ var require_mock_interceptor = __commonJS({
|
|
|
14023
14023
|
createMockScopeDispatchData({ statusCode, data, responseOptions }) {
|
|
14024
14024
|
const responseData = getResponseData(data);
|
|
14025
14025
|
const contentLength = this[kContentLength] ? { "content-length": responseData.length } : {};
|
|
14026
|
-
const
|
|
14026
|
+
const headers2 = { ...this[kDefaultHeaders], ...contentLength, ...responseOptions.headers };
|
|
14027
14027
|
const trailers = { ...this[kDefaultTrailers], ...responseOptions.trailers };
|
|
14028
|
-
return { statusCode, data, headers, trailers };
|
|
14028
|
+
return { statusCode, data, headers: headers2, trailers };
|
|
14029
14029
|
}
|
|
14030
14030
|
validateReplyParameters(replyParameters) {
|
|
14031
14031
|
if (typeof replyParameters.statusCode === "undefined") {
|
|
@@ -14077,11 +14077,11 @@ var require_mock_interceptor = __commonJS({
|
|
|
14077
14077
|
/**
|
|
14078
14078
|
* Set default reply headers on the interceptor for subsequent replies
|
|
14079
14079
|
*/
|
|
14080
|
-
defaultReplyHeaders(
|
|
14081
|
-
if (typeof
|
|
14080
|
+
defaultReplyHeaders(headers2) {
|
|
14081
|
+
if (typeof headers2 === "undefined") {
|
|
14082
14082
|
throw new InvalidArgumentError("headers must be defined");
|
|
14083
14083
|
}
|
|
14084
|
-
this[kDefaultHeaders] =
|
|
14084
|
+
this[kDefaultHeaders] = headers2;
|
|
14085
14085
|
return this;
|
|
14086
14086
|
}
|
|
14087
14087
|
/**
|
|
@@ -14663,15 +14663,15 @@ var require_snapshot_utils = __commonJS({
|
|
|
14663
14663
|
function createHeaderFilters(matchOptions = {}) {
|
|
14664
14664
|
const { ignoreHeaders = [], excludeHeaders = [], matchHeaders = [], caseSensitive = false } = matchOptions;
|
|
14665
14665
|
return {
|
|
14666
|
-
ignore: new Set(ignoreHeaders.map((
|
|
14667
|
-
exclude: new Set(excludeHeaders.map((
|
|
14668
|
-
match: new Set(matchHeaders.map((
|
|
14666
|
+
ignore: new Set(ignoreHeaders.map((header2) => caseSensitive ? header2 : header2.toLowerCase())),
|
|
14667
|
+
exclude: new Set(excludeHeaders.map((header2) => caseSensitive ? header2 : header2.toLowerCase())),
|
|
14668
|
+
match: new Set(matchHeaders.map((header2) => caseSensitive ? header2 : header2.toLowerCase()))
|
|
14669
14669
|
};
|
|
14670
14670
|
}
|
|
14671
14671
|
var crypto2 = runtimeFeatures.has("crypto") ? __require("node:crypto") : null;
|
|
14672
14672
|
var hashId = crypto2?.hash ? (value) => crypto2.hash("sha256", value, "base64url") : (value) => Buffer.from(value).toString("base64url");
|
|
14673
|
-
function isUndiciHeaders(
|
|
14674
|
-
return Array.isArray(
|
|
14673
|
+
function isUndiciHeaders(headers2) {
|
|
14674
|
+
return Array.isArray(headers2) && (headers2.length & 1) === 0;
|
|
14675
14675
|
}
|
|
14676
14676
|
function isUrlExcludedFactory(excludePatterns = []) {
|
|
14677
14677
|
if (excludePatterns.length === 0) {
|
|
@@ -14696,13 +14696,13 @@ var require_snapshot_utils = __commonJS({
|
|
|
14696
14696
|
return false;
|
|
14697
14697
|
};
|
|
14698
14698
|
}
|
|
14699
|
-
function normalizeHeaders(
|
|
14699
|
+
function normalizeHeaders(headers2) {
|
|
14700
14700
|
const normalizedHeaders = {};
|
|
14701
|
-
if (!
|
|
14702
|
-
if (isUndiciHeaders(
|
|
14703
|
-
for (let i = 0; i <
|
|
14704
|
-
const key =
|
|
14705
|
-
const value =
|
|
14701
|
+
if (!headers2) return normalizedHeaders;
|
|
14702
|
+
if (isUndiciHeaders(headers2)) {
|
|
14703
|
+
for (let i = 0; i < headers2.length; i += 2) {
|
|
14704
|
+
const key = headers2[i];
|
|
14705
|
+
const value = headers2[i + 1];
|
|
14706
14706
|
if (key && value !== void 0) {
|
|
14707
14707
|
const keyStr = Buffer.isBuffer(key) ? key.toString() : key;
|
|
14708
14708
|
const valueStr = Buffer.isBuffer(value) ? value.toString() : value;
|
|
@@ -14711,8 +14711,8 @@ var require_snapshot_utils = __commonJS({
|
|
|
14711
14711
|
}
|
|
14712
14712
|
return normalizedHeaders;
|
|
14713
14713
|
}
|
|
14714
|
-
if (
|
|
14715
|
-
for (const [key, value] of Object.entries(
|
|
14714
|
+
if (headers2 && typeof headers2 === "object") {
|
|
14715
|
+
for (const [key, value] of Object.entries(headers2)) {
|
|
14716
14716
|
if (key && typeof key === "string") {
|
|
14717
14717
|
normalizedHeaders[key.toLowerCase()] = Array.isArray(value) ? value.join(", ") : String(value);
|
|
14718
14718
|
}
|
|
@@ -14744,8 +14744,8 @@ var require_snapshot_utils = __commonJS({
|
|
|
14744
14744
|
var require_snapshot_recorder = __commonJS({
|
|
14745
14745
|
"../../node_modules/.pnpm/undici@7.30.2/node_modules/undici/lib/mock/snapshot-recorder.js"(exports, module) {
|
|
14746
14746
|
"use strict";
|
|
14747
|
-
var { writeFile:
|
|
14748
|
-
var { dirname:
|
|
14747
|
+
var { writeFile: writeFile3, readFile: readFile3, mkdir: mkdir3 } = __require("node:fs/promises");
|
|
14748
|
+
var { dirname: dirname3, resolve: resolve4 } = __require("node:path");
|
|
14749
14749
|
var { setTimeout: setTimeout2, clearTimeout: clearTimeout2 } = __require("node:timers");
|
|
14750
14750
|
var { InvalidArgumentError, UndiciError } = require_errors();
|
|
14751
14751
|
var { hashId, isUrlExcludedFactory, normalizeHeaders, createHeaderFilters } = require_snapshot_utils();
|
|
@@ -14762,14 +14762,14 @@ var require_snapshot_recorder = __commonJS({
|
|
|
14762
14762
|
body: matchOptions.matchBody !== false && opts.body ? String(opts.body) : ""
|
|
14763
14763
|
};
|
|
14764
14764
|
}
|
|
14765
|
-
function filterHeadersForMatching(
|
|
14766
|
-
if (!
|
|
14765
|
+
function filterHeadersForMatching(headers2, headerFilters, matchOptions = {}) {
|
|
14766
|
+
if (!headers2 || typeof headers2 !== "object") return {};
|
|
14767
14767
|
const {
|
|
14768
14768
|
caseSensitive = false
|
|
14769
14769
|
} = matchOptions;
|
|
14770
14770
|
const filtered = {};
|
|
14771
14771
|
const { ignore, exclude, match } = headerFilters;
|
|
14772
|
-
for (const [key, value] of Object.entries(
|
|
14772
|
+
for (const [key, value] of Object.entries(headers2)) {
|
|
14773
14773
|
const headerKey = caseSensitive ? key : key.toLowerCase();
|
|
14774
14774
|
if (exclude.has(headerKey)) continue;
|
|
14775
14775
|
if (ignore.has(headerKey)) continue;
|
|
@@ -14780,14 +14780,14 @@ var require_snapshot_recorder = __commonJS({
|
|
|
14780
14780
|
}
|
|
14781
14781
|
return filtered;
|
|
14782
14782
|
}
|
|
14783
|
-
function filterHeadersForStorage(
|
|
14784
|
-
if (!
|
|
14783
|
+
function filterHeadersForStorage(headers2, headerFilters, matchOptions = {}) {
|
|
14784
|
+
if (!headers2 || typeof headers2 !== "object") return {};
|
|
14785
14785
|
const {
|
|
14786
14786
|
caseSensitive = false
|
|
14787
14787
|
} = matchOptions;
|
|
14788
14788
|
const filtered = {};
|
|
14789
14789
|
const { exclude: excludeSet } = headerFilters;
|
|
14790
|
-
for (const [key, value] of Object.entries(
|
|
14790
|
+
for (const [key, value] of Object.entries(headers2)) {
|
|
14791
14791
|
const headerKey = caseSensitive ? key : key.toLowerCase();
|
|
14792
14792
|
if (excludeSet.has(headerKey)) continue;
|
|
14793
14793
|
filtered[headerKey] = value;
|
|
@@ -14946,7 +14946,7 @@ var require_snapshot_recorder = __commonJS({
|
|
|
14946
14946
|
throw new InvalidArgumentError("Snapshot path is required");
|
|
14947
14947
|
}
|
|
14948
14948
|
try {
|
|
14949
|
-
const data = await readFile3(
|
|
14949
|
+
const data = await readFile3(resolve4(path), "utf8");
|
|
14950
14950
|
const parsed = JSON.parse(data);
|
|
14951
14951
|
if (Array.isArray(parsed)) {
|
|
14952
14952
|
this.#snapshots.clear();
|
|
@@ -14975,13 +14975,13 @@ var require_snapshot_recorder = __commonJS({
|
|
|
14975
14975
|
if (!path) {
|
|
14976
14976
|
throw new InvalidArgumentError("Snapshot path is required");
|
|
14977
14977
|
}
|
|
14978
|
-
const resolvedPath =
|
|
14979
|
-
await
|
|
14978
|
+
const resolvedPath = resolve4(path);
|
|
14979
|
+
await mkdir3(dirname3(resolvedPath), { recursive: true });
|
|
14980
14980
|
const data = Array.from(this.#snapshots.entries()).map(([hash, snapshot]) => ({
|
|
14981
14981
|
hash,
|
|
14982
14982
|
snapshot
|
|
14983
14983
|
}));
|
|
14984
|
-
await
|
|
14984
|
+
await writeFile3(resolvedPath, JSON.stringify(data, null, 2), { flush: true });
|
|
14985
14985
|
}
|
|
14986
14986
|
/**
|
|
14987
14987
|
* Clears all recorded snapshots
|
|
@@ -15227,13 +15227,13 @@ var require_snapshot_agent = __commonJS({
|
|
|
15227
15227
|
onRequestStart(controller, context) {
|
|
15228
15228
|
return handler.onRequestStart(controller, { ...context, history: this.history });
|
|
15229
15229
|
},
|
|
15230
|
-
onRequestUpgrade(controller, statusCode,
|
|
15231
|
-
return handler.onRequestUpgrade(controller, statusCode,
|
|
15230
|
+
onRequestUpgrade(controller, statusCode, headers2, socket) {
|
|
15231
|
+
return handler.onRequestUpgrade(controller, statusCode, headers2, socket);
|
|
15232
15232
|
},
|
|
15233
|
-
onResponseStart(controller, statusCode,
|
|
15233
|
+
onResponseStart(controller, statusCode, headers2, statusMessage) {
|
|
15234
15234
|
responseData.statusCode = statusCode;
|
|
15235
|
-
responseData.headers =
|
|
15236
|
-
return handler.onResponseStart(controller, statusCode,
|
|
15235
|
+
responseData.headers = headers2;
|
|
15236
|
+
return handler.onResponseStart(controller, statusCode, headers2, statusMessage);
|
|
15237
15237
|
},
|
|
15238
15238
|
onResponseData(controller, chunk) {
|
|
15239
15239
|
responseData.body.push(chunk);
|
|
@@ -15581,10 +15581,10 @@ var require_redirect_handler = __commonJS({
|
|
|
15581
15581
|
onRequestStart(controller, context) {
|
|
15582
15582
|
this.handler.onRequestStart?.(controller, { ...context, history: this.history });
|
|
15583
15583
|
}
|
|
15584
|
-
onRequestUpgrade(controller, statusCode,
|
|
15585
|
-
this.handler.onRequestUpgrade?.(controller, statusCode,
|
|
15584
|
+
onRequestUpgrade(controller, statusCode, headers2, socket) {
|
|
15585
|
+
this.handler.onRequestUpgrade?.(controller, statusCode, headers2, socket);
|
|
15586
15586
|
}
|
|
15587
|
-
onResponseStart(controller, statusCode,
|
|
15587
|
+
onResponseStart(controller, statusCode, headers2, statusMessage) {
|
|
15588
15588
|
if (this.opts.throwOnMaxRedirect && this.history.length >= this.maxRedirections) {
|
|
15589
15589
|
throw new Error("max redirects");
|
|
15590
15590
|
}
|
|
@@ -15602,17 +15602,17 @@ var require_redirect_handler = __commonJS({
|
|
|
15602
15602
|
}
|
|
15603
15603
|
this.opts.body = null;
|
|
15604
15604
|
}
|
|
15605
|
-
this.location = this.history.length >= this.maxRedirections || util.isDisturbed(this.opts.body) || redirectableStatusCodes.indexOf(statusCode) === -1 ? null :
|
|
15605
|
+
this.location = this.history.length >= this.maxRedirections || util.isDisturbed(this.opts.body) || redirectableStatusCodes.indexOf(statusCode) === -1 ? null : headers2.location;
|
|
15606
15606
|
if (this.opts.origin) {
|
|
15607
15607
|
this.history.push(new URL(this.opts.path, this.opts.origin));
|
|
15608
15608
|
}
|
|
15609
15609
|
if (!this.location) {
|
|
15610
|
-
this.handler.onResponseStart?.(controller, statusCode,
|
|
15610
|
+
this.handler.onResponseStart?.(controller, statusCode, headers2, statusMessage);
|
|
15611
15611
|
return;
|
|
15612
15612
|
}
|
|
15613
15613
|
this.history[kRedirectCacheControl].push({
|
|
15614
15614
|
statusCode,
|
|
15615
|
-
headers: { ...
|
|
15615
|
+
headers: { ...headers2 },
|
|
15616
15616
|
receivedAt: Date.now()
|
|
15617
15617
|
});
|
|
15618
15618
|
const { origin, pathname, search } = util.parseURL(new URL(this.location, this.opts.origin && new URL(this.opts.path, this.opts.origin)));
|
|
@@ -15645,44 +15645,44 @@ var require_redirect_handler = __commonJS({
|
|
|
15645
15645
|
this.handler.onResponseError?.(controller, error);
|
|
15646
15646
|
}
|
|
15647
15647
|
};
|
|
15648
|
-
function shouldRemoveHeader(
|
|
15649
|
-
if (
|
|
15650
|
-
return util.headerNameToString(
|
|
15648
|
+
function shouldRemoveHeader(header2, removeContent, unknownOrigin) {
|
|
15649
|
+
if (header2.length === 4) {
|
|
15650
|
+
return util.headerNameToString(header2) === "host";
|
|
15651
15651
|
}
|
|
15652
|
-
if (removeContent && util.headerNameToString(
|
|
15652
|
+
if (removeContent && util.headerNameToString(header2).startsWith("content-")) {
|
|
15653
15653
|
return true;
|
|
15654
15654
|
}
|
|
15655
|
-
if (unknownOrigin && (
|
|
15656
|
-
const name = util.headerNameToString(
|
|
15655
|
+
if (unknownOrigin && (header2.length === 13 || header2.length === 6 || header2.length === 19)) {
|
|
15656
|
+
const name = util.headerNameToString(header2);
|
|
15657
15657
|
return name === "authorization" || name === "cookie" || name === "proxy-authorization";
|
|
15658
15658
|
}
|
|
15659
15659
|
return false;
|
|
15660
15660
|
}
|
|
15661
|
-
function cleanRequestHeaders(
|
|
15661
|
+
function cleanRequestHeaders(headers2, removeContent, unknownOrigin) {
|
|
15662
15662
|
const ret = [];
|
|
15663
|
-
if (Array.isArray(
|
|
15664
|
-
if (
|
|
15665
|
-
for (const [key, value] of
|
|
15663
|
+
if (Array.isArray(headers2)) {
|
|
15664
|
+
if (headers2.length > 0 && Array.isArray(headers2[0])) {
|
|
15665
|
+
for (const [key, value] of headers2) {
|
|
15666
15666
|
if (!shouldRemoveHeader(key, removeContent, unknownOrigin)) {
|
|
15667
15667
|
ret.push(key, value);
|
|
15668
15668
|
}
|
|
15669
15669
|
}
|
|
15670
15670
|
} else {
|
|
15671
|
-
for (let i = 0; i <
|
|
15672
|
-
if (!shouldRemoveHeader(
|
|
15673
|
-
ret.push(
|
|
15671
|
+
for (let i = 0; i < headers2.length; i += 2) {
|
|
15672
|
+
if (!shouldRemoveHeader(headers2[i], removeContent, unknownOrigin)) {
|
|
15673
|
+
ret.push(headers2[i], headers2[i + 1]);
|
|
15674
15674
|
}
|
|
15675
15675
|
}
|
|
15676
15676
|
}
|
|
15677
|
-
} else if (
|
|
15678
|
-
const entries = util.hasSafeIterator(
|
|
15677
|
+
} else if (headers2 && typeof headers2 === "object") {
|
|
15678
|
+
const entries = util.hasSafeIterator(headers2) ? headers2 : Object.entries(headers2);
|
|
15679
15679
|
for (const [key, value] of entries) {
|
|
15680
15680
|
if (!shouldRemoveHeader(key, removeContent, unknownOrigin)) {
|
|
15681
15681
|
ret.push(key, value);
|
|
15682
15682
|
}
|
|
15683
15683
|
}
|
|
15684
15684
|
} else {
|
|
15685
|
-
assert(
|
|
15685
|
+
assert(headers2 == null, "headers must be an object or an array");
|
|
15686
15686
|
}
|
|
15687
15687
|
return ret;
|
|
15688
15688
|
}
|
|
@@ -15738,12 +15738,12 @@ var require_response_error = __commonJS({
|
|
|
15738
15738
|
this.#body = "";
|
|
15739
15739
|
return super.onRequestStart(controller, context);
|
|
15740
15740
|
}
|
|
15741
|
-
onResponseStart(controller, statusCode,
|
|
15741
|
+
onResponseStart(controller, statusCode, headers2, statusMessage) {
|
|
15742
15742
|
this.#statusCode = statusCode;
|
|
15743
|
-
this.#headers =
|
|
15744
|
-
this.#contentType =
|
|
15743
|
+
this.#headers = headers2;
|
|
15744
|
+
this.#contentType = headers2["content-type"];
|
|
15745
15745
|
if (this.#statusCode < 400) {
|
|
15746
|
-
return super.onResponseStart(controller, statusCode,
|
|
15746
|
+
return super.onResponseStart(controller, statusCode, headers2, statusMessage);
|
|
15747
15747
|
}
|
|
15748
15748
|
if (this.#checkContentType("application/json") || this.#checkContentType("text/plain")) {
|
|
15749
15749
|
this.#decoder = new TextDecoder("utf-8");
|
|
@@ -15845,8 +15845,8 @@ var require_dump = __commonJS({
|
|
|
15845
15845
|
controller.abort = this.#abort.bind(this);
|
|
15846
15846
|
return super.onRequestStart(controller, context);
|
|
15847
15847
|
}
|
|
15848
|
-
onResponseStart(controller, statusCode,
|
|
15849
|
-
const contentLength =
|
|
15848
|
+
onResponseStart(controller, statusCode, headers2, statusMessage) {
|
|
15849
|
+
const contentLength = headers2["content-length"];
|
|
15850
15850
|
if (contentLength != null && contentLength > this.#maxSize) {
|
|
15851
15851
|
throw new RequestAbortedError(
|
|
15852
15852
|
`Response size (${contentLength}) larger than maxSize (${this.#maxSize})`
|
|
@@ -15855,7 +15855,7 @@ var require_dump = __commonJS({
|
|
|
15855
15855
|
if (this.aborted === true) {
|
|
15856
15856
|
return true;
|
|
15857
15857
|
}
|
|
15858
|
-
return super.onResponseStart(controller, statusCode,
|
|
15858
|
+
return super.onResponseStart(controller, statusCode, headers2, statusMessage);
|
|
15859
15859
|
}
|
|
15860
15860
|
onResponseError(controller, err) {
|
|
15861
15861
|
super.onResponseError(controller, this.aborted === true ? this.reason : err);
|
|
@@ -15904,62 +15904,62 @@ var require_dns = __commonJS({
|
|
|
15904
15904
|
var DecoratorHandler = require_decorator_handler();
|
|
15905
15905
|
var { InvalidArgumentError, InformationalError } = require_errors();
|
|
15906
15906
|
var maxInt = Math.pow(2, 31) - 1;
|
|
15907
|
-
function hasSafeIterator(
|
|
15908
|
-
const prototype = Object.getPrototypeOf(
|
|
15909
|
-
const ownIterator = Object.prototype.hasOwnProperty.call(
|
|
15910
|
-
return ownIterator || prototype != null && prototype !== Object.prototype && typeof
|
|
15907
|
+
function hasSafeIterator(headers2) {
|
|
15908
|
+
const prototype = Object.getPrototypeOf(headers2);
|
|
15909
|
+
const ownIterator = Object.prototype.hasOwnProperty.call(headers2, Symbol.iterator);
|
|
15910
|
+
return ownIterator || prototype != null && prototype !== Object.prototype && typeof headers2[Symbol.iterator] === "function";
|
|
15911
15911
|
}
|
|
15912
15912
|
function isHostHeader(key) {
|
|
15913
15913
|
return typeof key === "string" && key.toLowerCase() === "host";
|
|
15914
15914
|
}
|
|
15915
|
-
function normalizeHeaders(
|
|
15916
|
-
if (
|
|
15915
|
+
function normalizeHeaders(headers2) {
|
|
15916
|
+
if (headers2 == null) {
|
|
15917
15917
|
return null;
|
|
15918
15918
|
}
|
|
15919
|
-
if (Array.isArray(
|
|
15920
|
-
if (
|
|
15921
|
-
return
|
|
15919
|
+
if (Array.isArray(headers2)) {
|
|
15920
|
+
if (headers2.length === 0 || !Array.isArray(headers2[0])) {
|
|
15921
|
+
return headers2;
|
|
15922
15922
|
}
|
|
15923
15923
|
const normalized = [];
|
|
15924
|
-
for (const
|
|
15925
|
-
if (Array.isArray(
|
|
15926
|
-
normalized.push(
|
|
15924
|
+
for (const header2 of headers2) {
|
|
15925
|
+
if (Array.isArray(header2) && header2.length === 2) {
|
|
15926
|
+
normalized.push(header2[0], header2[1]);
|
|
15927
15927
|
} else {
|
|
15928
|
-
normalized.push(
|
|
15928
|
+
normalized.push(header2);
|
|
15929
15929
|
}
|
|
15930
15930
|
}
|
|
15931
15931
|
return normalized;
|
|
15932
15932
|
}
|
|
15933
|
-
if (typeof
|
|
15933
|
+
if (typeof headers2 === "object" && hasSafeIterator(headers2)) {
|
|
15934
15934
|
const normalized = [];
|
|
15935
|
-
for (const
|
|
15936
|
-
if (Array.isArray(
|
|
15937
|
-
normalized.push(
|
|
15935
|
+
for (const header2 of headers2) {
|
|
15936
|
+
if (Array.isArray(header2) && header2.length === 2) {
|
|
15937
|
+
normalized.push(header2[0], header2[1]);
|
|
15938
15938
|
} else {
|
|
15939
|
-
normalized.push(
|
|
15939
|
+
normalized.push(header2);
|
|
15940
15940
|
}
|
|
15941
15941
|
}
|
|
15942
15942
|
return normalized;
|
|
15943
15943
|
}
|
|
15944
|
-
return
|
|
15944
|
+
return headers2;
|
|
15945
15945
|
}
|
|
15946
|
-
function hasHostHeader(
|
|
15947
|
-
if (
|
|
15946
|
+
function hasHostHeader(headers2) {
|
|
15947
|
+
if (headers2 == null) {
|
|
15948
15948
|
return false;
|
|
15949
15949
|
}
|
|
15950
|
-
if (Array.isArray(
|
|
15951
|
-
if (
|
|
15950
|
+
if (Array.isArray(headers2)) {
|
|
15951
|
+
if (headers2.length === 0) {
|
|
15952
15952
|
return false;
|
|
15953
15953
|
}
|
|
15954
|
-
for (let i = 0; i <
|
|
15955
|
-
if (isHostHeader(
|
|
15954
|
+
for (let i = 0; i < headers2.length; i += 2) {
|
|
15955
|
+
if (isHostHeader(headers2[i])) {
|
|
15956
15956
|
return true;
|
|
15957
15957
|
}
|
|
15958
15958
|
}
|
|
15959
15959
|
return false;
|
|
15960
15960
|
}
|
|
15961
|
-
if (typeof
|
|
15962
|
-
for (const key in
|
|
15961
|
+
if (typeof headers2 === "object") {
|
|
15962
|
+
for (const key in headers2) {
|
|
15963
15963
|
if (isHostHeader(key)) {
|
|
15964
15964
|
return true;
|
|
15965
15965
|
}
|
|
@@ -15967,8 +15967,8 @@ var require_dns = __commonJS({
|
|
|
15967
15967
|
}
|
|
15968
15968
|
return false;
|
|
15969
15969
|
}
|
|
15970
|
-
function withHostHeader(host,
|
|
15971
|
-
const normalizedHeaders = normalizeHeaders(
|
|
15970
|
+
function withHostHeader(host, headers2) {
|
|
15971
|
+
const normalizedHeaders = normalizeHeaders(headers2);
|
|
15972
15972
|
if (hasHostHeader(normalizedHeaders)) {
|
|
15973
15973
|
return normalizedHeaders;
|
|
15974
15974
|
}
|
|
@@ -16471,24 +16471,24 @@ var require_cache = __commonJS({
|
|
|
16471
16471
|
headers: opts.headers
|
|
16472
16472
|
};
|
|
16473
16473
|
}
|
|
16474
|
-
function appendHeader(
|
|
16474
|
+
function appendHeader(headers2, key, val) {
|
|
16475
16475
|
const headerName = key.toLowerCase();
|
|
16476
|
-
const current =
|
|
16476
|
+
const current = headers2[headerName];
|
|
16477
16477
|
const values = Array.isArray(val) ? val : [val];
|
|
16478
16478
|
if (current === void 0) {
|
|
16479
|
-
|
|
16479
|
+
headers2[headerName] = Array.isArray(val) ? val.slice() : val;
|
|
16480
16480
|
} else if (Array.isArray(current)) {
|
|
16481
16481
|
current.push(...values);
|
|
16482
16482
|
} else {
|
|
16483
|
-
|
|
16483
|
+
headers2[headerName] = [current, ...values];
|
|
16484
16484
|
}
|
|
16485
16485
|
}
|
|
16486
16486
|
function normalizeHeaders(opts) {
|
|
16487
|
-
let
|
|
16487
|
+
let headers2;
|
|
16488
16488
|
if (opts.headers == null) {
|
|
16489
|
-
|
|
16489
|
+
headers2 = {};
|
|
16490
16490
|
} else if (typeof opts.headers === "object") {
|
|
16491
|
-
|
|
16491
|
+
headers2 = {};
|
|
16492
16492
|
if (hasSafeIterator(opts.headers)) {
|
|
16493
16493
|
if (Array.isArray(opts.headers)) {
|
|
16494
16494
|
if (Array.isArray(opts.headers[0])) {
|
|
@@ -16500,7 +16500,7 @@ var require_cache = __commonJS({
|
|
|
16500
16500
|
if (typeof key !== "string" || typeof val !== "string") {
|
|
16501
16501
|
throw new Error("opts.headers is not a valid header map");
|
|
16502
16502
|
}
|
|
16503
|
-
appendHeader(
|
|
16503
|
+
appendHeader(headers2, key, val);
|
|
16504
16504
|
}
|
|
16505
16505
|
} else {
|
|
16506
16506
|
if (opts.headers.length % 2 !== 0) {
|
|
@@ -16513,9 +16513,9 @@ var require_cache = __commonJS({
|
|
|
16513
16513
|
throw new Error("opts.headers is not a valid header map");
|
|
16514
16514
|
}
|
|
16515
16515
|
if (typeof val === "string") {
|
|
16516
|
-
appendHeader(
|
|
16516
|
+
appendHeader(headers2, key, val);
|
|
16517
16517
|
} else {
|
|
16518
|
-
appendHeader(
|
|
16518
|
+
appendHeader(headers2, key, val.map((item) => typeof item === "string" ? item : item.toString("latin1")));
|
|
16519
16519
|
}
|
|
16520
16520
|
}
|
|
16521
16521
|
}
|
|
@@ -16528,18 +16528,18 @@ var require_cache = __commonJS({
|
|
|
16528
16528
|
if (typeof key !== "string" || typeof val !== "string") {
|
|
16529
16529
|
throw new Error("opts.headers is not a valid header map");
|
|
16530
16530
|
}
|
|
16531
|
-
appendHeader(
|
|
16531
|
+
appendHeader(headers2, key, val);
|
|
16532
16532
|
}
|
|
16533
16533
|
}
|
|
16534
16534
|
} else {
|
|
16535
16535
|
for (const key of Object.keys(opts.headers)) {
|
|
16536
|
-
appendHeader(
|
|
16536
|
+
appendHeader(headers2, key, opts.headers[key]);
|
|
16537
16537
|
}
|
|
16538
16538
|
}
|
|
16539
16539
|
} else {
|
|
16540
16540
|
throw new Error("opts.headers is not an object");
|
|
16541
16541
|
}
|
|
16542
|
-
return
|
|
16542
|
+
return headers2;
|
|
16543
16543
|
}
|
|
16544
16544
|
function assertCacheKey(key) {
|
|
16545
16545
|
if (typeof key !== "object") {
|
|
@@ -16576,11 +16576,11 @@ var require_cache = __commonJS({
|
|
|
16576
16576
|
throw new TypeError(`expected value.etag to be string, got ${typeof value.etag}`);
|
|
16577
16577
|
}
|
|
16578
16578
|
}
|
|
16579
|
-
function parseCacheControlHeader(
|
|
16579
|
+
function parseCacheControlHeader(header2) {
|
|
16580
16580
|
const output = {};
|
|
16581
16581
|
const invalidNumericDirectives = /* @__PURE__ */ new Set();
|
|
16582
16582
|
const invalidNoArgumentDirectives = /* @__PURE__ */ new Set();
|
|
16583
|
-
const directives = splitCacheControlHeaderValue(Array.isArray(
|
|
16583
|
+
const directives = splitCacheControlHeaderValue(Array.isArray(header2) ? header2.join(",") : header2);
|
|
16584
16584
|
for (let i = 0; i < directives.length; i++) {
|
|
16585
16585
|
const directiveRecord = directives[i];
|
|
16586
16586
|
const directive = directiveRecord.value.toLowerCase();
|
|
@@ -16680,11 +16680,11 @@ var require_cache = __commonJS({
|
|
|
16680
16680
|
break;
|
|
16681
16681
|
}
|
|
16682
16682
|
i = lastQuotedPart;
|
|
16683
|
-
const
|
|
16683
|
+
const headers2 = fieldList.split(",");
|
|
16684
16684
|
let validFieldNames = true;
|
|
16685
|
-
for (let j = 0; j <
|
|
16686
|
-
|
|
16687
|
-
if (!isValidHTTPToken(
|
|
16685
|
+
for (let j = 0; j < headers2.length; j++) {
|
|
16686
|
+
headers2[j] = trimOWS(headers2[j]);
|
|
16687
|
+
if (!isValidHTTPToken(headers2[j])) {
|
|
16688
16688
|
validFieldNames = false;
|
|
16689
16689
|
}
|
|
16690
16690
|
}
|
|
@@ -16692,9 +16692,9 @@ var require_cache = __commonJS({
|
|
|
16692
16692
|
output[key] = true;
|
|
16693
16693
|
} else if (output[key] !== true) {
|
|
16694
16694
|
if (key in output) {
|
|
16695
|
-
output[key] = output[key].concat(
|
|
16695
|
+
output[key] = output[key].concat(headers2);
|
|
16696
16696
|
} else {
|
|
16697
|
-
output[key] =
|
|
16697
|
+
output[key] = headers2;
|
|
16698
16698
|
}
|
|
16699
16699
|
}
|
|
16700
16700
|
} else {
|
|
@@ -16759,24 +16759,24 @@ var require_cache = __commonJS({
|
|
|
16759
16759
|
}
|
|
16760
16760
|
return false;
|
|
16761
16761
|
}
|
|
16762
|
-
function parseVaryHeader(varyHeader,
|
|
16762
|
+
function parseVaryHeader(varyHeader, headers2) {
|
|
16763
16763
|
if (hasVaryStar(varyHeader)) {
|
|
16764
|
-
return
|
|
16764
|
+
return headers2;
|
|
16765
16765
|
}
|
|
16766
16766
|
const output = (
|
|
16767
16767
|
/** @type {Record<string, string | string[] | null>} */
|
|
16768
16768
|
{}
|
|
16769
16769
|
);
|
|
16770
16770
|
const varyingHeaders = splitVaryHeader(varyHeader);
|
|
16771
|
-
for (const
|
|
16772
|
-
const trimmedHeader = trimOWS(
|
|
16771
|
+
for (const header2 of varyingHeaders) {
|
|
16772
|
+
const trimmedHeader = trimOWS(header2).toLowerCase();
|
|
16773
16773
|
if (trimmedHeader.length === 0) {
|
|
16774
16774
|
continue;
|
|
16775
16775
|
}
|
|
16776
16776
|
if (!isValidHTTPToken(trimmedHeader)) {
|
|
16777
16777
|
return void 0;
|
|
16778
16778
|
}
|
|
16779
|
-
const headerValue2 =
|
|
16779
|
+
const headerValue2 = headers2[trimmedHeader];
|
|
16780
16780
|
output[trimmedHeader] = Array.isArray(headerValue2) ? headerValue2.slice() : headerValue2 ?? null;
|
|
16781
16781
|
}
|
|
16782
16782
|
return output;
|
|
@@ -16820,17 +16820,17 @@ var require_cache = __commonJS({
|
|
|
16820
16820
|
}
|
|
16821
16821
|
}
|
|
16822
16822
|
function makeDeduplicationKey(cacheKey, excludeHeaders) {
|
|
16823
|
-
const
|
|
16823
|
+
const headers2 = {};
|
|
16824
16824
|
if (cacheKey.headers) {
|
|
16825
16825
|
const sortedHeaders = Object.keys(cacheKey.headers).sort();
|
|
16826
|
-
for (const
|
|
16827
|
-
if (excludeHeaders?.has(
|
|
16826
|
+
for (const header2 of sortedHeaders) {
|
|
16827
|
+
if (excludeHeaders?.has(header2.toLowerCase())) {
|
|
16828
16828
|
continue;
|
|
16829
16829
|
}
|
|
16830
|
-
|
|
16830
|
+
headers2[header2] = cacheKey.headers[header2];
|
|
16831
16831
|
}
|
|
16832
16832
|
}
|
|
16833
|
-
return JSON.stringify([cacheKey.origin, cacheKey.method, cacheKey.path,
|
|
16833
|
+
return JSON.stringify([cacheKey.origin, cacheKey.method, cacheKey.path, headers2]);
|
|
16834
16834
|
}
|
|
16835
16835
|
module.exports = {
|
|
16836
16836
|
makeCacheKey,
|
|
@@ -17474,8 +17474,8 @@ var require_cache_handler = __commonJS({
|
|
|
17474
17474
|
deleteLocationTargets(store, cacheKey, resHeaders.location);
|
|
17475
17475
|
deleteLocationTargets(store, cacheKey, resHeaders["content-location"]);
|
|
17476
17476
|
}
|
|
17477
|
-
function requestCarriesCredentials(
|
|
17478
|
-
return
|
|
17477
|
+
function requestCarriesCredentials(headers2) {
|
|
17478
|
+
return headers2 != null && (Object.hasOwn(headers2, "authorization") || Object.hasOwn(headers2, "cookie") || Object.hasOwn(headers2, "proxy-authorization"));
|
|
17479
17479
|
}
|
|
17480
17480
|
var CacheHandler = class {
|
|
17481
17481
|
/**
|
|
@@ -17536,8 +17536,8 @@ var require_cache_handler = __commonJS({
|
|
|
17536
17536
|
this.#history = context?.history;
|
|
17537
17537
|
this.#handler.onRequestStart?.(controller, context);
|
|
17538
17538
|
}
|
|
17539
|
-
onRequestUpgrade(controller, statusCode,
|
|
17540
|
-
this.#handler.onRequestUpgrade?.(controller, statusCode,
|
|
17539
|
+
onRequestUpgrade(controller, statusCode, headers2, socket) {
|
|
17540
|
+
this.#handler.onRequestUpgrade?.(controller, statusCode, headers2, socket);
|
|
17541
17541
|
}
|
|
17542
17542
|
/**
|
|
17543
17543
|
* @param {import('../../types/dispatcher.d.ts').default.DispatchController} controller
|
|
@@ -18343,13 +18343,13 @@ var require_cache_revalidation_handler = __commonJS({
|
|
|
18343
18343
|
this.#successful = false;
|
|
18344
18344
|
this.#context = context;
|
|
18345
18345
|
}
|
|
18346
|
-
onRequestUpgrade(controller, statusCode,
|
|
18347
|
-
this.#handler.onRequestUpgrade?.(controller, statusCode,
|
|
18346
|
+
onRequestUpgrade(controller, statusCode, headers2, socket) {
|
|
18347
|
+
this.#handler.onRequestUpgrade?.(controller, statusCode, headers2, socket);
|
|
18348
18348
|
}
|
|
18349
|
-
onResponseStart(controller, statusCode,
|
|
18349
|
+
onResponseStart(controller, statusCode, headers2, statusMessage) {
|
|
18350
18350
|
assert(this.#callback != null);
|
|
18351
18351
|
this.#successful = statusCode === 304 || this.#allowErrorStatusCodes && statusCode >= 500 && statusCode <= 504;
|
|
18352
|
-
this.#callback(this.#successful, this.#context, statusCode,
|
|
18352
|
+
this.#callback(this.#successful, this.#context, statusCode, headers2);
|
|
18353
18353
|
this.#callback = null;
|
|
18354
18354
|
if (this.#successful) {
|
|
18355
18355
|
return true;
|
|
@@ -18358,7 +18358,7 @@ var require_cache_revalidation_handler = __commonJS({
|
|
|
18358
18358
|
this.#handler.onResponseStart?.(
|
|
18359
18359
|
controller,
|
|
18360
18360
|
statusCode,
|
|
18361
|
-
|
|
18361
|
+
headers2,
|
|
18362
18362
|
statusMessage
|
|
18363
18363
|
);
|
|
18364
18364
|
}
|
|
@@ -18440,8 +18440,8 @@ var require_cache2 = __commonJS({
|
|
|
18440
18440
|
}
|
|
18441
18441
|
return false;
|
|
18442
18442
|
}
|
|
18443
|
-
function hasPragmaNoCache(
|
|
18444
|
-
const pragma =
|
|
18443
|
+
function hasPragmaNoCache(headers2) {
|
|
18444
|
+
const pragma = headers2?.pragma;
|
|
18445
18445
|
if (!pragma) {
|
|
18446
18446
|
return false;
|
|
18447
18447
|
}
|
|
@@ -18460,14 +18460,14 @@ var require_cache2 = __commonJS({
|
|
|
18460
18460
|
}
|
|
18461
18461
|
return false;
|
|
18462
18462
|
}
|
|
18463
|
-
function needsRevalidation(result, cacheControlDirectives, { headers = {} }) {
|
|
18463
|
+
function needsRevalidation(result, cacheControlDirectives, { headers: headers2 = {} }) {
|
|
18464
18464
|
if (cacheControlDirectives?.["no-cache"]) {
|
|
18465
18465
|
return true;
|
|
18466
18466
|
}
|
|
18467
18467
|
if (result.cacheControlDirectives?.["no-cache"] && !Array.isArray(result.cacheControlDirectives["no-cache"])) {
|
|
18468
18468
|
return true;
|
|
18469
18469
|
}
|
|
18470
|
-
if (
|
|
18470
|
+
if (headers2["if-modified-since"] || headers2["if-none-match"]) {
|
|
18471
18471
|
return true;
|
|
18472
18472
|
}
|
|
18473
18473
|
return false;
|
|
@@ -18477,19 +18477,19 @@ var require_cache2 = __commonJS({
|
|
|
18477
18477
|
// s-maxage implies proxy-revalidate for shared caches.
|
|
18478
18478
|
result.cacheControlDirectives?.["s-maxage"] !== void 0);
|
|
18479
18479
|
}
|
|
18480
|
-
function revalidationResponseDisallowsCachedReuse(cacheType,
|
|
18481
|
-
if (
|
|
18480
|
+
function revalidationResponseDisallowsCachedReuse(cacheType, headers2) {
|
|
18481
|
+
if (headers2.vary && isInvalidOrWildcardVaryHeader(headers2.vary) || cacheType === "shared" && Object.hasOwn(headers2, "set-cookie")) {
|
|
18482
18482
|
return true;
|
|
18483
18483
|
}
|
|
18484
|
-
const cacheControl =
|
|
18484
|
+
const cacheControl = headers2["cache-control"];
|
|
18485
18485
|
if (!cacheControl) {
|
|
18486
18486
|
return false;
|
|
18487
18487
|
}
|
|
18488
18488
|
const cacheControlDirectives = parseCacheControlHeader(cacheControl);
|
|
18489
18489
|
return cacheControlDirectives["no-store"] === true || cacheType === "shared" && cacheControlDirectives.private === true;
|
|
18490
18490
|
}
|
|
18491
|
-
function revalidationResponseUpdatesCacheControl(
|
|
18492
|
-
return
|
|
18491
|
+
function revalidationResponseUpdatesCacheControl(headers2) {
|
|
18492
|
+
return headers2["cache-control"] !== void 0;
|
|
18493
18493
|
}
|
|
18494
18494
|
function revalidationResponseAddsVary(result, varyDirectives) {
|
|
18495
18495
|
if (!varyDirectives) {
|
|
@@ -18508,28 +18508,28 @@ var require_cache2 = __commonJS({
|
|
|
18508
18508
|
} catch {
|
|
18509
18509
|
}
|
|
18510
18510
|
}
|
|
18511
|
-
function getUsableLastModified(
|
|
18512
|
-
const lastModified =
|
|
18511
|
+
function getUsableLastModified(headers2) {
|
|
18512
|
+
const lastModified = headers2?.["last-modified"];
|
|
18513
18513
|
if (typeof lastModified === "string" && parseHttpDate(lastModified)) {
|
|
18514
18514
|
return lastModified;
|
|
18515
18515
|
}
|
|
18516
18516
|
}
|
|
18517
18517
|
function makeRevalidationHeaders(opts, result) {
|
|
18518
|
-
const
|
|
18518
|
+
const headers2 = {
|
|
18519
18519
|
...opts.headers,
|
|
18520
18520
|
"if-modified-since": getUsableLastModified(result.headers) ?? new Date(result.cachedAt).toUTCString()
|
|
18521
18521
|
};
|
|
18522
18522
|
if (result.etag) {
|
|
18523
|
-
|
|
18523
|
+
headers2["if-none-match"] = result.etag;
|
|
18524
18524
|
}
|
|
18525
18525
|
if (result.vary) {
|
|
18526
18526
|
for (const key in result.vary) {
|
|
18527
18527
|
if (result.vary[key] != null) {
|
|
18528
|
-
|
|
18528
|
+
headers2[key] = result.vary[key];
|
|
18529
18529
|
}
|
|
18530
18530
|
}
|
|
18531
18531
|
}
|
|
18532
|
-
return
|
|
18532
|
+
return headers2;
|
|
18533
18533
|
}
|
|
18534
18534
|
function revalidationTargetMatchesCacheKey(cacheKey, context) {
|
|
18535
18535
|
const history = context?.history;
|
|
@@ -18544,11 +18544,11 @@ var require_cache2 = __commonJS({
|
|
|
18544
18544
|
return false;
|
|
18545
18545
|
}
|
|
18546
18546
|
}
|
|
18547
|
-
function revalidationEtagMatchesCachedValue(result,
|
|
18548
|
-
if (!Object.hasOwn(
|
|
18547
|
+
function revalidationEtagMatchesCachedValue(result, headers2) {
|
|
18548
|
+
if (!Object.hasOwn(headers2, "etag")) {
|
|
18549
18549
|
return true;
|
|
18550
18550
|
}
|
|
18551
|
-
const responseEtag =
|
|
18551
|
+
const responseEtag = headers2.etag;
|
|
18552
18552
|
const cachedEtag = result.etag;
|
|
18553
18553
|
if (typeof responseEtag !== "string" || typeof cachedEtag !== "string" || !isEtagUsable(responseEtag) || !isEtagUsable(cachedEtag)) {
|
|
18554
18554
|
return false;
|
|
@@ -18660,13 +18660,13 @@ var require_cache2 = __commonJS({
|
|
|
18660
18660
|
if (stream.destroyed) {
|
|
18661
18661
|
return;
|
|
18662
18662
|
}
|
|
18663
|
-
const
|
|
18663
|
+
const headers2 = { ...result.headers, age: String(age) };
|
|
18664
18664
|
if (isStale2) {
|
|
18665
|
-
|
|
18665
|
+
headers2.warning = '110 - "response is stale"';
|
|
18666
18666
|
}
|
|
18667
|
-
controller.rawHeaders = util.toRawHeaders(
|
|
18667
|
+
controller.rawHeaders = util.toRawHeaders(headers2);
|
|
18668
18668
|
try {
|
|
18669
|
-
handler.onResponseStart?.(controller, result.statusCode,
|
|
18669
|
+
handler.onResponseStart?.(controller, result.statusCode, headers2, result.statusMessage);
|
|
18670
18670
|
} catch (err) {
|
|
18671
18671
|
stream.destroy(err);
|
|
18672
18672
|
return;
|
|
@@ -18709,11 +18709,11 @@ var require_cache2 = __commonJS({
|
|
|
18709
18709
|
if (!revalidate && withinStaleWhileRevalidateWindow(result, globalOpts.type)) {
|
|
18710
18710
|
sendCachedValue(handler, opts, result, age, null, true);
|
|
18711
18711
|
queueMicrotask(() => {
|
|
18712
|
-
const
|
|
18712
|
+
const headers3 = makeRevalidationHeaders(opts, result);
|
|
18713
18713
|
dispatch(
|
|
18714
18714
|
{
|
|
18715
18715
|
...opts,
|
|
18716
|
-
headers:
|
|
18716
|
+
headers: headers3
|
|
18717
18717
|
},
|
|
18718
18718
|
new CacheHandler(globalOpts, cacheKey, {
|
|
18719
18719
|
// Silent handler that just updates the cache
|
|
@@ -18741,7 +18741,7 @@ var require_cache2 = __commonJS({
|
|
|
18741
18741
|
withinStaleIfErrorThreshold = now < result.staleAt + staleIfErrorExpiry * 1e3;
|
|
18742
18742
|
}
|
|
18743
18743
|
}
|
|
18744
|
-
const
|
|
18744
|
+
const headers2 = makeRevalidationHeaders(opts, result);
|
|
18745
18745
|
const refetch = () => {
|
|
18746
18746
|
if (util.isStream(result.body)) {
|
|
18747
18747
|
result.body.on("error", nop).destroy();
|
|
@@ -18752,18 +18752,18 @@ var require_cache2 = __commonJS({
|
|
|
18752
18752
|
return dispatch(
|
|
18753
18753
|
{
|
|
18754
18754
|
...opts,
|
|
18755
|
-
headers
|
|
18755
|
+
headers: headers2
|
|
18756
18756
|
},
|
|
18757
18757
|
new CacheRevalidationHandler(
|
|
18758
|
-
(success, context, statusCode,
|
|
18758
|
+
(success, context, statusCode, headers3) => {
|
|
18759
18759
|
if (success) {
|
|
18760
18760
|
if (statusCode === 304) {
|
|
18761
|
-
if (!revalidationTargetMatchesCacheKey(cacheKey, context) || !revalidationEtagMatchesCachedValue(result,
|
|
18761
|
+
if (!revalidationTargetMatchesCacheKey(cacheKey, context) || !revalidationEtagMatchesCachedValue(result, headers3) || revalidationResponseDisallowsCachedReuse(globalOpts.type, headers3)) {
|
|
18762
18762
|
return refetch();
|
|
18763
18763
|
}
|
|
18764
|
-
if (revalidationResponseUpdatesCacheControl(
|
|
18764
|
+
if (revalidationResponseUpdatesCacheControl(headers3)) {
|
|
18765
18765
|
deleteCachedValue(globalOpts.store, cacheKey);
|
|
18766
|
-
} else if (revalidationResponseAddsVary(result,
|
|
18766
|
+
} else if (revalidationResponseAddsVary(result, headers3.vary ? parseVaryHeader(headers3.vary, opts.headers) : void 0)) {
|
|
18767
18767
|
return refetch();
|
|
18768
18768
|
}
|
|
18769
18769
|
}
|
|
@@ -19261,8 +19261,8 @@ var require_decompress = __commonJS({
|
|
|
19261
19261
|
this.#controller.target = controller;
|
|
19262
19262
|
return super.onRequestStart(this.#controller, context);
|
|
19263
19263
|
}
|
|
19264
|
-
onRequestUpgrade(controller, statusCode,
|
|
19265
|
-
return super.onRequestUpgrade(this.#controller, statusCode,
|
|
19264
|
+
onRequestUpgrade(controller, statusCode, headers2, socket) {
|
|
19265
|
+
return super.onRequestUpgrade(this.#controller, statusCode, headers2, socket);
|
|
19266
19266
|
}
|
|
19267
19267
|
/**
|
|
19268
19268
|
* @param {Controller} controller
|
|
@@ -19271,19 +19271,19 @@ var require_decompress = __commonJS({
|
|
|
19271
19271
|
* @param {string} statusMessage
|
|
19272
19272
|
* @returns {void}
|
|
19273
19273
|
*/
|
|
19274
|
-
onResponseStart(controller, statusCode,
|
|
19275
|
-
const rawContentEncoding =
|
|
19274
|
+
onResponseStart(controller, statusCode, headers2, statusMessage) {
|
|
19275
|
+
const rawContentEncoding = headers2["content-encoding"];
|
|
19276
19276
|
const contentEncoding = Array.isArray(rawContentEncoding) ? rawContentEncoding.join(",") : rawContentEncoding;
|
|
19277
19277
|
if (this.#shouldSkipDecompression(contentEncoding, statusCode)) {
|
|
19278
|
-
return super.onResponseStart(this.#controller, statusCode,
|
|
19278
|
+
return super.onResponseStart(this.#controller, statusCode, headers2, statusMessage);
|
|
19279
19279
|
}
|
|
19280
19280
|
const decompressors = this.#createDecompressionChain(contentEncoding.toLowerCase());
|
|
19281
19281
|
if (decompressors.length === 0) {
|
|
19282
19282
|
this.#cleanupDecompressors();
|
|
19283
|
-
return super.onResponseStart(this.#controller, statusCode,
|
|
19283
|
+
return super.onResponseStart(this.#controller, statusCode, headers2, statusMessage);
|
|
19284
19284
|
}
|
|
19285
19285
|
this.#decompressors = decompressors;
|
|
19286
|
-
const { "content-encoding": _, "content-length": __, ...newHeaders } =
|
|
19286
|
+
const { "content-encoding": _, "content-length": __, ...newHeaders } = headers2;
|
|
19287
19287
|
if (this.#controller.rawHeaders) {
|
|
19288
19288
|
const rawHeaders = this.#controller.rawHeaders;
|
|
19289
19289
|
if (Array.isArray(rawHeaders)) {
|
|
@@ -19526,8 +19526,8 @@ var require_deduplication_handler = __commonJS({
|
|
|
19526
19526
|
* @param {import('../../types/header.d.ts').IncomingHttpHeaders} headers
|
|
19527
19527
|
* @param {Socket} socket
|
|
19528
19528
|
*/
|
|
19529
|
-
onRequestUpgrade(controller, statusCode,
|
|
19530
|
-
this.#primaryHandler.onRequestUpgrade?.(controller, statusCode,
|
|
19529
|
+
onRequestUpgrade(controller, statusCode, headers2, socket) {
|
|
19530
|
+
this.#primaryHandler.onRequestUpgrade?.(controller, statusCode, headers2, socket);
|
|
19531
19531
|
}
|
|
19532
19532
|
/**
|
|
19533
19533
|
* @param {import('../../types/dispatcher.d.ts').default.DispatchController} controller
|
|
@@ -19535,12 +19535,12 @@ var require_deduplication_handler = __commonJS({
|
|
|
19535
19535
|
* @param {Record<string, string | string[]>} headers
|
|
19536
19536
|
* @param {string} statusMessage
|
|
19537
19537
|
*/
|
|
19538
|
-
onResponseStart(controller, statusCode,
|
|
19538
|
+
onResponseStart(controller, statusCode, headers2, statusMessage) {
|
|
19539
19539
|
this.#responseStarted = true;
|
|
19540
19540
|
this.#statusCode = statusCode;
|
|
19541
|
-
this.#headers =
|
|
19541
|
+
this.#headers = headers2;
|
|
19542
19542
|
this.#statusMessage = statusMessage;
|
|
19543
|
-
this.#primaryHandler.onResponseStart?.(controller, statusCode,
|
|
19543
|
+
this.#primaryHandler.onResponseStart?.(controller, statusCode, headers2, statusMessage);
|
|
19544
19544
|
for (const waitingHandler of this.#waitingHandlers) {
|
|
19545
19545
|
const { handler, controller: waitingController } = waitingHandler;
|
|
19546
19546
|
if (waitingHandler.done || waitingController.aborted) {
|
|
@@ -19551,7 +19551,7 @@ var require_deduplication_handler = __commonJS({
|
|
|
19551
19551
|
handler.onResponseStart?.(
|
|
19552
19552
|
waitingController,
|
|
19553
19553
|
statusCode,
|
|
19554
|
-
|
|
19554
|
+
headers2,
|
|
19555
19555
|
statusMessage
|
|
19556
19556
|
);
|
|
19557
19557
|
} catch {
|
|
@@ -20170,7 +20170,7 @@ var require_sqlite_cache_store = __commonJS({
|
|
|
20170
20170
|
*/
|
|
20171
20171
|
#findValue(key, canBeExpired = false) {
|
|
20172
20172
|
const url = this.#makeValueUrl(key);
|
|
20173
|
-
const { headers, method } = key;
|
|
20173
|
+
const { headers: headers2, method } = key;
|
|
20174
20174
|
const values = this.#getValuesQuery.all(url, method);
|
|
20175
20175
|
if (values.length === 0) {
|
|
20176
20176
|
return void 0;
|
|
@@ -20183,8 +20183,8 @@ var require_sqlite_cache_store = __commonJS({
|
|
|
20183
20183
|
let matches = true;
|
|
20184
20184
|
if (value.vary) {
|
|
20185
20185
|
const vary = JSON.parse(value.vary);
|
|
20186
|
-
for (const
|
|
20187
|
-
if (!headerValueEquals(
|
|
20186
|
+
for (const header2 in vary) {
|
|
20187
|
+
if (!headerValueEquals(headers2[header2], vary[header2])) {
|
|
20188
20188
|
matches = false;
|
|
20189
20189
|
break;
|
|
20190
20190
|
}
|
|
@@ -20244,22 +20244,22 @@ var require_headers = __commonJS({
|
|
|
20244
20244
|
while (j > i && isHTTPWhiteSpaceCharCode(potentialValue.charCodeAt(i))) ++i;
|
|
20245
20245
|
return i === 0 && j === potentialValue.length ? potentialValue : potentialValue.substring(i, j);
|
|
20246
20246
|
}
|
|
20247
|
-
function fill(
|
|
20247
|
+
function fill(headers2, object) {
|
|
20248
20248
|
if (Array.isArray(object)) {
|
|
20249
20249
|
for (let i = 0; i < object.length; ++i) {
|
|
20250
|
-
const
|
|
20251
|
-
if (
|
|
20250
|
+
const header2 = object[i];
|
|
20251
|
+
if (header2.length !== 2) {
|
|
20252
20252
|
throw webidl.errors.exception({
|
|
20253
20253
|
header: "Headers constructor",
|
|
20254
|
-
message: `expected name/value pair to be length 2, found ${
|
|
20254
|
+
message: `expected name/value pair to be length 2, found ${header2.length}.`
|
|
20255
20255
|
});
|
|
20256
20256
|
}
|
|
20257
|
-
appendHeader(
|
|
20257
|
+
appendHeader(headers2, header2[0], header2[1]);
|
|
20258
20258
|
}
|
|
20259
20259
|
} else if (typeof object === "object" && object !== null) {
|
|
20260
20260
|
const keys = Object.keys(object);
|
|
20261
20261
|
for (let i = 0; i < keys.length; ++i) {
|
|
20262
|
-
appendHeader(
|
|
20262
|
+
appendHeader(headers2, keys[i], object[keys[i]]);
|
|
20263
20263
|
}
|
|
20264
20264
|
} else {
|
|
20265
20265
|
throw webidl.errors.conversionFailed({
|
|
@@ -20269,7 +20269,7 @@ var require_headers = __commonJS({
|
|
|
20269
20269
|
});
|
|
20270
20270
|
}
|
|
20271
20271
|
}
|
|
20272
|
-
function appendHeader(
|
|
20272
|
+
function appendHeader(headers2, name, value) {
|
|
20273
20273
|
value = headerValueNormalize(value);
|
|
20274
20274
|
if (!isValidHeaderName(name)) {
|
|
20275
20275
|
throw webidl.errors.invalidArgument({
|
|
@@ -20284,10 +20284,10 @@ var require_headers = __commonJS({
|
|
|
20284
20284
|
type: "header value"
|
|
20285
20285
|
});
|
|
20286
20286
|
}
|
|
20287
|
-
if (getHeadersGuard(
|
|
20287
|
+
if (getHeadersGuard(headers2) === "immutable") {
|
|
20288
20288
|
throw new TypeError("immutable");
|
|
20289
20289
|
}
|
|
20290
|
-
return getHeadersList(
|
|
20290
|
+
return getHeadersList(headers2).append(name, value, false);
|
|
20291
20291
|
}
|
|
20292
20292
|
function headersListSortAndCombine(target) {
|
|
20293
20293
|
const headersList = getHeadersList(target);
|
|
@@ -20297,7 +20297,7 @@ var require_headers = __commonJS({
|
|
|
20297
20297
|
if (headersList.sortedMap) {
|
|
20298
20298
|
return headersList.sortedMap;
|
|
20299
20299
|
}
|
|
20300
|
-
const
|
|
20300
|
+
const headers2 = [];
|
|
20301
20301
|
const names = headersList.toSortedArray();
|
|
20302
20302
|
const cookies = headersList.cookies;
|
|
20303
20303
|
if (cookies === null || cookies.length === 1) {
|
|
@@ -20307,13 +20307,13 @@ var require_headers = __commonJS({
|
|
|
20307
20307
|
const { 0: name, 1: value } = names[i];
|
|
20308
20308
|
if (name === "set-cookie") {
|
|
20309
20309
|
for (let j = 0; j < cookies.length; ++j) {
|
|
20310
|
-
|
|
20310
|
+
headers2.push([name, cookies[j]]);
|
|
20311
20311
|
}
|
|
20312
20312
|
} else {
|
|
20313
|
-
|
|
20313
|
+
headers2.push([name, value]);
|
|
20314
20314
|
}
|
|
20315
20315
|
}
|
|
20316
|
-
return headersList.sortedMap =
|
|
20316
|
+
return headersList.sortedMap = headers2;
|
|
20317
20317
|
}
|
|
20318
20318
|
function compareHeaderName(a, b) {
|
|
20319
20319
|
return a[0] < b[0] ? -1 : 1;
|
|
@@ -20411,31 +20411,31 @@ var require_headers = __commonJS({
|
|
|
20411
20411
|
}
|
|
20412
20412
|
}
|
|
20413
20413
|
get entries() {
|
|
20414
|
-
const
|
|
20414
|
+
const headers2 = {};
|
|
20415
20415
|
if (this.headersMap.size !== 0) {
|
|
20416
20416
|
for (const { name, value } of this.headersMap.values()) {
|
|
20417
|
-
|
|
20417
|
+
headers2[name] = value;
|
|
20418
20418
|
}
|
|
20419
20419
|
}
|
|
20420
|
-
return
|
|
20420
|
+
return headers2;
|
|
20421
20421
|
}
|
|
20422
20422
|
rawValues() {
|
|
20423
20423
|
return this.headersMap.values();
|
|
20424
20424
|
}
|
|
20425
20425
|
get entriesList() {
|
|
20426
|
-
const
|
|
20426
|
+
const headers2 = [];
|
|
20427
20427
|
if (this.headersMap.size !== 0) {
|
|
20428
20428
|
for (const { 0: lowerName, 1: { name, value } } of this.headersMap) {
|
|
20429
20429
|
if (lowerName === "set-cookie") {
|
|
20430
20430
|
for (const cookie of this.cookies) {
|
|
20431
|
-
|
|
20431
|
+
headers2.push([name, cookie]);
|
|
20432
20432
|
}
|
|
20433
20433
|
} else {
|
|
20434
|
-
|
|
20434
|
+
headers2.push([name, value]);
|
|
20435
20435
|
}
|
|
20436
20436
|
}
|
|
20437
20437
|
}
|
|
20438
|
-
return
|
|
20438
|
+
return headers2;
|
|
20439
20439
|
}
|
|
20440
20440
|
// https://fetch.spec.whatwg.org/#convert-header-names-to-a-sorted-lowercase-set
|
|
20441
20441
|
toSortedArray() {
|
|
@@ -21036,10 +21036,10 @@ var require_response = __commonJS({
|
|
|
21036
21036
|
function fromInnerResponse(innerResponse, guard) {
|
|
21037
21037
|
const response = new Response(kConstruct);
|
|
21038
21038
|
setResponseState(response, innerResponse);
|
|
21039
|
-
const
|
|
21040
|
-
setResponseHeaders(response,
|
|
21041
|
-
setHeadersList(
|
|
21042
|
-
setHeadersGuard(
|
|
21039
|
+
const headers2 = new Headers(kConstruct);
|
|
21040
|
+
setResponseHeaders(response, headers2);
|
|
21041
|
+
setHeadersList(headers2, innerResponse.headersList);
|
|
21042
|
+
setHeadersGuard(headers2, guard);
|
|
21043
21043
|
if (innerResponse.urlList.length !== 0 && innerResponse.body?.stream) {
|
|
21044
21044
|
streamRegistry.register(response, new WeakRef(innerResponse.body.stream));
|
|
21045
21045
|
}
|
|
@@ -21390,15 +21390,15 @@ var require_request2 = __commonJS({
|
|
|
21390
21390
|
}
|
|
21391
21391
|
if (initHasKey) {
|
|
21392
21392
|
const headersList = getHeadersList(this.#headers);
|
|
21393
|
-
const
|
|
21393
|
+
const headers2 = init.headers !== void 0 ? init.headers : new HeadersList(headersList);
|
|
21394
21394
|
headersList.clear();
|
|
21395
|
-
if (
|
|
21396
|
-
for (const { name, value } of
|
|
21395
|
+
if (headers2 instanceof HeadersList) {
|
|
21396
|
+
for (const { name, value } of headers2.rawValues()) {
|
|
21397
21397
|
headersList.append(name, value, false);
|
|
21398
21398
|
}
|
|
21399
|
-
headersList.cookies =
|
|
21399
|
+
headersList.cookies = headers2.cookies;
|
|
21400
21400
|
} else {
|
|
21401
|
-
fillHeaders(this.#headers,
|
|
21401
|
+
fillHeaders(this.#headers, headers2);
|
|
21402
21402
|
}
|
|
21403
21403
|
}
|
|
21404
21404
|
const inputBody = webidl.is.Request(input) ? input.#state.body : null;
|
|
@@ -21718,10 +21718,10 @@ var require_request2 = __commonJS({
|
|
|
21718
21718
|
setRequestState(request2, innerRequest);
|
|
21719
21719
|
setRequestDispatcher(request2, dispatcher);
|
|
21720
21720
|
setRequestSignal(request2, signal);
|
|
21721
|
-
const
|
|
21722
|
-
setRequestHeaders(request2,
|
|
21723
|
-
setHeadersList(
|
|
21724
|
-
setHeadersGuard(
|
|
21721
|
+
const headers2 = new Headers(kConstruct);
|
|
21722
|
+
setRequestHeaders(request2, headers2);
|
|
21723
|
+
setHeadersList(headers2, innerRequest.headersList);
|
|
21724
|
+
setHeadersGuard(headers2, guard);
|
|
21725
21725
|
return request2;
|
|
21726
21726
|
}
|
|
21727
21727
|
Object.defineProperties(Request.prototype, {
|
|
@@ -22103,7 +22103,7 @@ var require_fetch = __commonJS({
|
|
|
22103
22103
|
function handleFetchDone(response) {
|
|
22104
22104
|
finalizeAndReportTiming(response, "fetch");
|
|
22105
22105
|
}
|
|
22106
|
-
function
|
|
22106
|
+
function fetch2(input, init = void 0) {
|
|
22107
22107
|
webidl.argumentLengthCheck(arguments, 1, "globalThis.fetch");
|
|
22108
22108
|
let p = createDeferredPromise();
|
|
22109
22109
|
let requestObject;
|
|
@@ -22955,7 +22955,7 @@ var require_fetch = __commonJS({
|
|
|
22955
22955
|
const agent = fetchParams.controller.dispatcher;
|
|
22956
22956
|
const path = url.pathname + url.search;
|
|
22957
22957
|
const hasTrailingQuestionMark = url.search.length === 0 && url.href[url.href.length - url.hash.length - 1] === "?";
|
|
22958
|
-
return new Promise((
|
|
22958
|
+
return new Promise((resolve4, reject) => agent.dispatch(
|
|
22959
22959
|
{
|
|
22960
22960
|
path: hasTrailingQuestionMark ? `${path}?` : path,
|
|
22961
22961
|
origin: url.origin,
|
|
@@ -23043,7 +23043,7 @@ var require_fetch = __commonJS({
|
|
|
23043
23043
|
}
|
|
23044
23044
|
this.body = new Readable({ read: resume });
|
|
23045
23045
|
const onError = this.onError.bind(this);
|
|
23046
|
-
|
|
23046
|
+
resolve4({
|
|
23047
23047
|
status,
|
|
23048
23048
|
statusText,
|
|
23049
23049
|
headersList,
|
|
@@ -23078,12 +23078,12 @@ var require_fetch = __commonJS({
|
|
|
23078
23078
|
fetchParams.controller.terminate(error);
|
|
23079
23079
|
reject(error);
|
|
23080
23080
|
},
|
|
23081
|
-
onRequestUpgrade(_controller, status,
|
|
23081
|
+
onRequestUpgrade(_controller, status, headers2, socket) {
|
|
23082
23082
|
if (socket.session != null && status !== 200 || socket.session == null && status !== 101) {
|
|
23083
23083
|
return false;
|
|
23084
23084
|
}
|
|
23085
23085
|
const headersList = new HeadersList();
|
|
23086
|
-
for (const [name, value] of Object.entries(
|
|
23086
|
+
for (const [name, value] of Object.entries(headers2)) {
|
|
23087
23087
|
if (value == null) {
|
|
23088
23088
|
continue;
|
|
23089
23089
|
}
|
|
@@ -23096,7 +23096,7 @@ var require_fetch = __commonJS({
|
|
|
23096
23096
|
headersList.append(headerName, String(value), true);
|
|
23097
23097
|
}
|
|
23098
23098
|
}
|
|
23099
|
-
|
|
23099
|
+
resolve4({
|
|
23100
23100
|
status,
|
|
23101
23101
|
statusText: STATUS_CODES[status],
|
|
23102
23102
|
headersList,
|
|
@@ -23120,7 +23120,7 @@ var require_fetch = __commonJS({
|
|
|
23120
23120
|
headersList.append(nameStr, value.toString("latin1"), true);
|
|
23121
23121
|
}
|
|
23122
23122
|
}
|
|
23123
|
-
|
|
23123
|
+
resolve4({
|
|
23124
23124
|
status,
|
|
23125
23125
|
statusText: STATUS_CODES[status],
|
|
23126
23126
|
headersList,
|
|
@@ -23133,7 +23133,7 @@ var require_fetch = __commonJS({
|
|
|
23133
23133
|
}
|
|
23134
23134
|
}
|
|
23135
23135
|
module.exports = {
|
|
23136
|
-
fetch,
|
|
23136
|
+
fetch: fetch2,
|
|
23137
23137
|
Fetch,
|
|
23138
23138
|
fetching,
|
|
23139
23139
|
finalizeAndReportTiming
|
|
@@ -23153,10 +23153,10 @@ var require_util3 = __commonJS({
|
|
|
23153
23153
|
const serializedB = URLSerializer(B, excludeFragment);
|
|
23154
23154
|
return serializedA === serializedB;
|
|
23155
23155
|
}
|
|
23156
|
-
function getFieldValues(
|
|
23157
|
-
assert(
|
|
23156
|
+
function getFieldValues(header2) {
|
|
23157
|
+
assert(header2 !== null);
|
|
23158
23158
|
const values = [];
|
|
23159
|
-
for (let value of
|
|
23159
|
+
for (let value of header2.split(",")) {
|
|
23160
23160
|
value = value.trim();
|
|
23161
23161
|
if (isValidHeaderName(value)) {
|
|
23162
23162
|
values.push(value);
|
|
@@ -24063,20 +24063,20 @@ var require_parse = __commonJS({
|
|
|
24063
24063
|
var { maxNameValuePairSize, maxAttributeValueSize } = require_constants4();
|
|
24064
24064
|
var { isCTLExcludingHtab } = require_util4();
|
|
24065
24065
|
var assert = __require("node:assert");
|
|
24066
|
-
function parseSetCookie2(
|
|
24067
|
-
if (isCTLExcludingHtab(
|
|
24066
|
+
function parseSetCookie2(header2) {
|
|
24067
|
+
if (isCTLExcludingHtab(header2)) {
|
|
24068
24068
|
return null;
|
|
24069
24069
|
}
|
|
24070
24070
|
let nameValuePair = "";
|
|
24071
24071
|
let unparsedAttributes = "";
|
|
24072
24072
|
let name = "";
|
|
24073
24073
|
let value = "";
|
|
24074
|
-
if (
|
|
24074
|
+
if (header2.includes(";")) {
|
|
24075
24075
|
const position = { position: 0 };
|
|
24076
|
-
nameValuePair = collectASequenceOfCodePointsFast(";",
|
|
24077
|
-
unparsedAttributes =
|
|
24076
|
+
nameValuePair = collectASequenceOfCodePointsFast(";", header2, position);
|
|
24077
|
+
unparsedAttributes = header2.slice(position.position);
|
|
24078
24078
|
} else {
|
|
24079
|
-
nameValuePair =
|
|
24079
|
+
nameValuePair = header2;
|
|
24080
24080
|
}
|
|
24081
24081
|
if (!nameValuePair.includes("=")) {
|
|
24082
24082
|
value = nameValuePair;
|
|
@@ -24201,10 +24201,10 @@ var require_cookies = __commonJS({
|
|
|
24201
24201
|
var { webidl } = require_webidl();
|
|
24202
24202
|
var { Headers } = require_headers();
|
|
24203
24203
|
var brandChecks = webidl.brandCheckMultiple([Headers, globalThis.Headers].filter(Boolean));
|
|
24204
|
-
function getCookies(
|
|
24204
|
+
function getCookies(headers2) {
|
|
24205
24205
|
webidl.argumentLengthCheck(arguments, 1, "getCookies");
|
|
24206
|
-
brandChecks(
|
|
24207
|
-
const cookie =
|
|
24206
|
+
brandChecks(headers2);
|
|
24207
|
+
const cookie = headers2.get("cookie");
|
|
24208
24208
|
const out = { __proto__: null };
|
|
24209
24209
|
if (!cookie) {
|
|
24210
24210
|
return out;
|
|
@@ -24215,23 +24215,23 @@ var require_cookies = __commonJS({
|
|
|
24215
24215
|
}
|
|
24216
24216
|
return out;
|
|
24217
24217
|
}
|
|
24218
|
-
function deleteCookie(
|
|
24219
|
-
brandChecks(
|
|
24218
|
+
function deleteCookie(headers2, name, attributes) {
|
|
24219
|
+
brandChecks(headers2);
|
|
24220
24220
|
const prefix = "deleteCookie";
|
|
24221
24221
|
webidl.argumentLengthCheck(arguments, 2, prefix);
|
|
24222
24222
|
name = webidl.converters.DOMString(name, prefix, "name");
|
|
24223
24223
|
attributes = webidl.converters.DeleteCookieAttributes(attributes);
|
|
24224
|
-
setCookie(
|
|
24224
|
+
setCookie(headers2, {
|
|
24225
24225
|
name,
|
|
24226
24226
|
value: "",
|
|
24227
24227
|
expires: /* @__PURE__ */ new Date(0),
|
|
24228
24228
|
...attributes
|
|
24229
24229
|
});
|
|
24230
24230
|
}
|
|
24231
|
-
function getSetCookies(
|
|
24231
|
+
function getSetCookies(headers2) {
|
|
24232
24232
|
webidl.argumentLengthCheck(arguments, 1, "getSetCookies");
|
|
24233
|
-
brandChecks(
|
|
24234
|
-
const cookies =
|
|
24233
|
+
brandChecks(headers2);
|
|
24234
|
+
const cookies = headers2.getSetCookie();
|
|
24235
24235
|
if (!cookies) {
|
|
24236
24236
|
return [];
|
|
24237
24237
|
}
|
|
@@ -24241,13 +24241,13 @@ var require_cookies = __commonJS({
|
|
|
24241
24241
|
cookie = webidl.converters.DOMString(cookie);
|
|
24242
24242
|
return parseSetCookie2(cookie);
|
|
24243
24243
|
}
|
|
24244
|
-
function setCookie(
|
|
24244
|
+
function setCookie(headers2, cookie) {
|
|
24245
24245
|
webidl.argumentLengthCheck(arguments, 2, "setCookie");
|
|
24246
|
-
brandChecks(
|
|
24246
|
+
brandChecks(headers2);
|
|
24247
24247
|
cookie = webidl.converters.Cookie(cookie);
|
|
24248
24248
|
const str2 = stringify(cookie);
|
|
24249
24249
|
if (str2) {
|
|
24250
|
-
|
|
24250
|
+
headers2.append("set-cookie", str2, true);
|
|
24251
24251
|
}
|
|
24252
24252
|
}
|
|
24253
24253
|
webidl.converters.DeleteCookieAttributes = webidl.dictionaryConverter([
|
|
@@ -25944,7 +25944,7 @@ var require_websocket = __commonJS({
|
|
|
25944
25944
|
}
|
|
25945
25945
|
fireEvent("open", this);
|
|
25946
25946
|
if (channels.open.hasSubscribers) {
|
|
25947
|
-
const
|
|
25947
|
+
const headers2 = response.headersList.entries;
|
|
25948
25948
|
channels.open.publish({
|
|
25949
25949
|
address: getSocketAddress(response.socket),
|
|
25950
25950
|
protocol: this.#protocol,
|
|
@@ -25953,7 +25953,7 @@ var require_websocket = __commonJS({
|
|
|
25953
25953
|
handshakeResponse: {
|
|
25954
25954
|
status: response.status,
|
|
25955
25955
|
statusText: response.statusText,
|
|
25956
|
-
headers
|
|
25956
|
+
headers: headers2
|
|
25957
25957
|
}
|
|
25958
25958
|
});
|
|
25959
25959
|
}
|
|
@@ -27278,7 +27278,7 @@ var require_undici = __commonJS({
|
|
|
27278
27278
|
var errors = require_errors();
|
|
27279
27279
|
var util = require_util();
|
|
27280
27280
|
var { InvalidArgumentError } = errors;
|
|
27281
|
-
var
|
|
27281
|
+
var api2 = require_api();
|
|
27282
27282
|
var buildConnector = require_connect();
|
|
27283
27283
|
var MockClient = require_mock_client();
|
|
27284
27284
|
var { MockCallHistory, MockCallHistoryLog } = require_mock_call_history();
|
|
@@ -27290,7 +27290,7 @@ var require_undici = __commonJS({
|
|
|
27290
27290
|
var { getGlobalDispatcher, setGlobalDispatcher } = require_global2();
|
|
27291
27291
|
var DecoratorHandler = require_decorator_handler();
|
|
27292
27292
|
var RedirectHandler = require_redirect_handler();
|
|
27293
|
-
Object.assign(Dispatcher.prototype,
|
|
27293
|
+
Object.assign(Dispatcher.prototype, api2);
|
|
27294
27294
|
module.exports.Dispatcher = Dispatcher;
|
|
27295
27295
|
module.exports.Client = Client;
|
|
27296
27296
|
module.exports.Pool = Pool;
|
|
@@ -27387,7 +27387,7 @@ var require_undici = __commonJS({
|
|
|
27387
27387
|
err.stack = stack ? `${stack}
|
|
27388
27388
|
${captureLines}` : capture.stack;
|
|
27389
27389
|
}
|
|
27390
|
-
module.exports.fetch = function
|
|
27390
|
+
module.exports.fetch = function fetch2(init, options = void 0) {
|
|
27391
27391
|
return fetchImpl(init, options).catch((err) => {
|
|
27392
27392
|
if (currentFilename) {
|
|
27393
27393
|
appendFetchStackTrace(err, currentFilename);
|
|
@@ -27425,11 +27425,11 @@ ${captureLines}` : capture.stack;
|
|
|
27425
27425
|
module.exports.ping = ping;
|
|
27426
27426
|
module.exports.WebSocketStream = require_websocketstream().WebSocketStream;
|
|
27427
27427
|
module.exports.WebSocketError = require_websocketerror().WebSocketError;
|
|
27428
|
-
module.exports.request = makeDispatcher(
|
|
27429
|
-
module.exports.stream = makeDispatcher(
|
|
27430
|
-
module.exports.pipeline = makeDispatcher(
|
|
27431
|
-
module.exports.connect = makeDispatcher(
|
|
27432
|
-
module.exports.upgrade = makeDispatcher(
|
|
27428
|
+
module.exports.request = makeDispatcher(api2.request);
|
|
27429
|
+
module.exports.stream = makeDispatcher(api2.stream);
|
|
27430
|
+
module.exports.pipeline = makeDispatcher(api2.pipeline);
|
|
27431
|
+
module.exports.connect = makeDispatcher(api2.connect);
|
|
27432
|
+
module.exports.upgrade = makeDispatcher(api2.upgrade);
|
|
27433
27433
|
module.exports.MockClient = MockClient;
|
|
27434
27434
|
module.exports.MockCallHistory = MockCallHistory;
|
|
27435
27435
|
module.exports.MockCallHistoryLog = MockCallHistoryLog;
|
|
@@ -27456,9 +27456,9 @@ ${captureLines}` : capture.stack;
|
|
|
27456
27456
|
});
|
|
27457
27457
|
|
|
27458
27458
|
// src/main.ts
|
|
27459
|
-
import { mkdir, readFile as readFile2, writeFile } from "node:fs/promises";
|
|
27460
|
-
import { dirname, resolve as
|
|
27461
|
-
import { parseArgs } from "node:util";
|
|
27459
|
+
import { mkdir as mkdir2, readFile as readFile2, writeFile as writeFile2 } from "node:fs/promises";
|
|
27460
|
+
import { dirname as dirname2, resolve as resolve3 } from "node:path";
|
|
27461
|
+
import { parseArgs as parseArgs2 } from "node:util";
|
|
27462
27462
|
|
|
27463
27463
|
// ../../packages/core/src/relay.ts
|
|
27464
27464
|
var TEXTUAL = /^(text\/|application\/(json|xml|javascript|x-www-form-urlencoded|graphql|ld\+json|problem\+json|[\w.+-]+\+(json|xml)))|image\/svg\+xml/i;
|
|
@@ -27466,9 +27466,9 @@ function isTextualContentType(contentType) {
|
|
|
27466
27466
|
if (!contentType) return true;
|
|
27467
27467
|
return TEXTUAL.test(contentType.trim());
|
|
27468
27468
|
}
|
|
27469
|
-
function headerValue(
|
|
27469
|
+
function headerValue(headers2, name) {
|
|
27470
27470
|
const lower = name.toLowerCase();
|
|
27471
|
-
return
|
|
27471
|
+
return headers2.find(([k]) => k.toLowerCase() === lower)?.[1];
|
|
27472
27472
|
}
|
|
27473
27473
|
|
|
27474
27474
|
// ../../packages/core/src/format.ts
|
|
@@ -27528,20 +27528,20 @@ var CONTENT_TYPES = {
|
|
|
27528
27528
|
xml: "application/xml",
|
|
27529
27529
|
form: "application/x-www-form-urlencoded"
|
|
27530
27530
|
};
|
|
27531
|
-
function buildSendRequest(draft,
|
|
27532
|
-
const
|
|
27533
|
-
const has = (name) =>
|
|
27534
|
-
let url =
|
|
27531
|
+
function buildSendRequest(draft, resolve4 = identity, inheritedAuth2, files) {
|
|
27532
|
+
const headers2 = draft.headers.filter((h) => h.enabled && h.key.trim()).map((h) => [resolve4(h.key).trim(), resolve4(h.value)]);
|
|
27533
|
+
const has = (name) => headers2.some(([k]) => k.toLowerCase() === name.toLowerCase());
|
|
27534
|
+
let url = resolve4(draft.url.trim());
|
|
27535
27535
|
if (url && !/^[a-z][a-z0-9+.-]*:\/\//i.test(url) && !url.startsWith("{{")) url = `http://${url}`;
|
|
27536
27536
|
const auth = draft.auth.type === "inherit" ? inheritedAuth2 ?? { type: "none" } : draft.auth;
|
|
27537
|
-
if (auth.type === "bearer" && auth.token && !has("authorization"))
|
|
27538
|
-
if (auth.type === "basic" && !has("authorization"))
|
|
27537
|
+
if (auth.type === "bearer" && auth.token && !has("authorization")) headers2.push(["Authorization", `Bearer ${resolve4(auth.token)}`]);
|
|
27538
|
+
if (auth.type === "basic" && !has("authorization")) headers2.push(["Authorization", `Basic ${base64(`${resolve4(auth.username)}:${resolve4(auth.password)}`)}`]);
|
|
27539
27539
|
if (auth.type === "oauth2" && auth.token?.accessToken && !has("authorization"))
|
|
27540
|
-
|
|
27540
|
+
headers2.push(["Authorization", `${auth.headerPrefix.trim() || "Bearer"} ${auth.token.accessToken}`]);
|
|
27541
27541
|
if (auth.type === "apikey" && auth.key) {
|
|
27542
27542
|
if (auth.in === "header") {
|
|
27543
|
-
if (!has(auth.key))
|
|
27544
|
-
} else url += `${url.includes("?") ? "&" : "?"}${encodeQuery([{ key:
|
|
27543
|
+
if (!has(auth.key)) headers2.push([resolve4(auth.key), resolve4(auth.value)]);
|
|
27544
|
+
} else url += `${url.includes("?") ? "&" : "?"}${encodeQuery([{ key: resolve4(auth.key), value: resolve4(auth.value) }])}`;
|
|
27545
27545
|
}
|
|
27546
27546
|
let body;
|
|
27547
27547
|
let bodyEncoding;
|
|
@@ -27557,36 +27557,36 @@ function buildSendRequest(draft, resolve3 = identity, inheritedAuth2, files) {
|
|
|
27557
27557
|
if (f) {
|
|
27558
27558
|
body = bytesToBase64(bytesOf(f));
|
|
27559
27559
|
bodyEncoding = "base64";
|
|
27560
|
-
if (!has("content-type"))
|
|
27560
|
+
if (!has("content-type")) headers2.push(["Content-Type", f.type || "application/octet-stream"]);
|
|
27561
27561
|
}
|
|
27562
27562
|
} else if (mode === "graphql") {
|
|
27563
|
-
body = graphqlBody(
|
|
27564
|
-
if (!has("content-type"))
|
|
27563
|
+
body = graphqlBody(resolve4(draft.body.raw), resolve4(draft.body.variables ?? ""), draft.body.operationName?.trim());
|
|
27564
|
+
if (!has("content-type")) headers2.push(["Content-Type", "application/json"]);
|
|
27565
27565
|
} else if (mode !== "none") {
|
|
27566
27566
|
const rows2 = draft.body.form.filter((f) => f.enabled && f.key);
|
|
27567
27567
|
if (mode === "multipart") {
|
|
27568
27568
|
const boundary = `----wirecatch${uid("b").replace(/\W/g, "")}`;
|
|
27569
|
-
const parts = rows2.map((f) => f.isFile ? f.file ? { key:
|
|
27569
|
+
const parts = rows2.map((f) => f.isFile ? f.file ? { key: resolve4(f.key), file: f.file, bytes: bytesOf(f.file) } : { key: resolve4(f.key), value: "" } : { key: resolve4(f.key), value: resolve4(f.value) });
|
|
27570
27570
|
if (parts.some((p) => "bytes" in p)) {
|
|
27571
27571
|
body = bytesToBase64(multipartBytes(parts, boundary));
|
|
27572
27572
|
bodyEncoding = "base64";
|
|
27573
27573
|
} else body = multipart(parts, boundary);
|
|
27574
|
-
|
|
27574
|
+
headers2.push(["Content-Type", `multipart/form-data; boundary=${boundary}`]);
|
|
27575
27575
|
} else {
|
|
27576
|
-
const fields = rows2.map((f) => ({ key:
|
|
27577
|
-
body = mode === "form" ? encodeQuery(fields) :
|
|
27578
|
-
if (!has("content-type"))
|
|
27576
|
+
const fields = rows2.map((f) => ({ key: resolve4(f.key), value: resolve4(f.value) }));
|
|
27577
|
+
body = mode === "form" ? encodeQuery(fields) : resolve4(draft.body.raw);
|
|
27578
|
+
if (!has("content-type")) headers2.push(["Content-Type", CONTENT_TYPES[mode]]);
|
|
27579
27579
|
}
|
|
27580
27580
|
}
|
|
27581
|
-
return { method: draft.method.toUpperCase(), url, headers, body, ...bodyEncoding === "base64" ? { bodyEncoding } : {} };
|
|
27581
|
+
return { method: draft.method.toUpperCase(), url, headers: headers2, body, ...bodyEncoding === "base64" ? { bodyEncoding } : {} };
|
|
27582
27582
|
}
|
|
27583
27583
|
var GraphQLVariablesError = class extends Error {
|
|
27584
27584
|
};
|
|
27585
|
-
function graphqlVariablesProblem(
|
|
27586
|
-
if (!
|
|
27585
|
+
function graphqlVariablesProblem(text2) {
|
|
27586
|
+
if (!text2.trim()) return "";
|
|
27587
27587
|
let v;
|
|
27588
27588
|
try {
|
|
27589
|
-
v = JSON.parse(
|
|
27589
|
+
v = JSON.parse(text2);
|
|
27590
27590
|
} catch (e) {
|
|
27591
27591
|
return `GraphQL variables are not valid JSON: ${e.message}`;
|
|
27592
27592
|
}
|
|
@@ -27701,8 +27701,8 @@ function dynamic(name) {
|
|
|
27701
27701
|
return void 0;
|
|
27702
27702
|
}
|
|
27703
27703
|
}
|
|
27704
|
-
function resolveVariables(
|
|
27705
|
-
let out =
|
|
27704
|
+
function resolveVariables(text2, scopes, maxDepth = 5) {
|
|
27705
|
+
let out = text2;
|
|
27706
27706
|
for (let depth = 0; depth < maxDepth && out.includes("{{"); depth++) {
|
|
27707
27707
|
const next = out.replace(VAR, (whole, name) => {
|
|
27708
27708
|
for (const s of scopes) if (Object.hasOwn(s, name)) return s[name];
|
|
@@ -27714,7 +27714,7 @@ function resolveVariables(text, scopes, maxDepth = 5) {
|
|
|
27714
27714
|
return out;
|
|
27715
27715
|
}
|
|
27716
27716
|
function makeResolver(scopes) {
|
|
27717
|
-
return (
|
|
27717
|
+
return (text2) => resolveVariables(text2, scopes);
|
|
27718
27718
|
}
|
|
27719
27719
|
|
|
27720
27720
|
// ../../packages/core/src/oauth2.ts
|
|
@@ -27725,8 +27725,8 @@ function newOAuth2() {
|
|
|
27725
27725
|
return { type: "oauth2", grant: "client_credentials", tokenUrl: "", clientId: "", clientSecret: "", scope: "", audience: "", username: "", password: "", clientAuth: "basic", headerPrefix: "Bearer" };
|
|
27726
27726
|
}
|
|
27727
27727
|
var formEncode = (s) => encodeURIComponent(s).replace(/%20/g, "+");
|
|
27728
|
-
function tokenRequest(a,
|
|
27729
|
-
const url =
|
|
27728
|
+
function tokenRequest(a, resolve4, refreshToken) {
|
|
27729
|
+
const url = resolve4(a.tokenUrl).trim();
|
|
27730
27730
|
if (!url) throw new OAuth2Error("Set the token URL first.");
|
|
27731
27731
|
const form = new URLSearchParams();
|
|
27732
27732
|
if (refreshToken) {
|
|
@@ -27736,27 +27736,27 @@ function tokenRequest(a, resolve3, refreshToken) {
|
|
|
27736
27736
|
if (a.grant === "authorization_code") throw new OAuth2Error("Sign in first: the authorization code grant needs a browser sign-in (Sign in, under Auth).");
|
|
27737
27737
|
form.set("grant_type", a.grant);
|
|
27738
27738
|
if (a.grant === "password") {
|
|
27739
|
-
form.set("username",
|
|
27740
|
-
form.set("password",
|
|
27739
|
+
form.set("username", resolve4(a.username));
|
|
27740
|
+
form.set("password", resolve4(a.password));
|
|
27741
27741
|
}
|
|
27742
27742
|
}
|
|
27743
|
-
if (
|
|
27744
|
-
if (!refreshToken &&
|
|
27745
|
-
return withClient(a,
|
|
27743
|
+
if (resolve4(a.scope).trim()) form.set("scope", resolve4(a.scope).trim());
|
|
27744
|
+
if (!refreshToken && resolve4(a.audience).trim()) form.set("audience", resolve4(a.audience).trim());
|
|
27745
|
+
return withClient(a, resolve4, url, form);
|
|
27746
27746
|
}
|
|
27747
|
-
function withClient(a,
|
|
27748
|
-
const
|
|
27749
|
-
const id =
|
|
27750
|
-
const secret =
|
|
27747
|
+
function withClient(a, resolve4, url, form) {
|
|
27748
|
+
const headers2 = [["Content-Type", "application/x-www-form-urlencoded"], ["Accept", "application/json"]];
|
|
27749
|
+
const id = resolve4(a.clientId);
|
|
27750
|
+
const secret = resolve4(a.clientSecret);
|
|
27751
27751
|
if (a.grant === "authorization_code" && !secret) {
|
|
27752
27752
|
if (id) form.set("client_id", id);
|
|
27753
27753
|
} else if (a.clientAuth === "body") {
|
|
27754
27754
|
if (id) form.set("client_id", id);
|
|
27755
27755
|
if (secret) form.set("client_secret", secret);
|
|
27756
27756
|
} else if (id || secret) {
|
|
27757
|
-
|
|
27757
|
+
headers2.push(["Authorization", `Basic ${btoa(`${formEncode(id)}:${formEncode(secret)}`)}`]);
|
|
27758
27758
|
}
|
|
27759
|
-
return { method: "POST", url, headers, body: form.toString() };
|
|
27759
|
+
return { method: "POST", url, headers: headers2, body: form.toString() };
|
|
27760
27760
|
}
|
|
27761
27761
|
function parseTokenResponse(res, now = Date.now()) {
|
|
27762
27762
|
const ct = headerValue(res.headers, "content-type") ?? "";
|
|
@@ -27786,8 +27786,8 @@ function parseTokenResponse(res, now = Date.now()) {
|
|
|
27786
27786
|
function tokenFresh(t, now = Date.now(), skewMs = 3e4) {
|
|
27787
27787
|
return !!t?.accessToken && (t.expiresAt === void 0 || t.expiresAt - skewMs > now);
|
|
27788
27788
|
}
|
|
27789
|
-
function tokenCacheKey(a,
|
|
27790
|
-
return JSON.stringify([a.grant,
|
|
27789
|
+
function tokenCacheKey(a, resolve4) {
|
|
27790
|
+
return JSON.stringify([a.grant, resolve4(a.tokenUrl), resolve4(a.clientId), resolve4(a.scope), resolve4(a.audience), a.grant === "password" ? resolve4(a.username) : ""]);
|
|
27791
27791
|
}
|
|
27792
27792
|
|
|
27793
27793
|
// ../../packages/core/src/postman.ts
|
|
@@ -27850,8 +27850,8 @@ function authOf(a, where, warnings) {
|
|
|
27850
27850
|
function script(events, listen) {
|
|
27851
27851
|
const e = events?.find((x) => x.listen === listen);
|
|
27852
27852
|
const exec = e?.script?.exec;
|
|
27853
|
-
const
|
|
27854
|
-
return
|
|
27853
|
+
const text2 = Array.isArray(exec) ? exec.join("\n") : exec ?? "";
|
|
27854
|
+
return text2.trim() ? text2 : void 0;
|
|
27855
27855
|
}
|
|
27856
27856
|
function bodyOf(b, where, warnings) {
|
|
27857
27857
|
const empty2 = { mode: "none", raw: "", form: [] };
|
|
@@ -27888,14 +27888,14 @@ function requestOf(item, path, warnings) {
|
|
|
27888
27888
|
const where = path;
|
|
27889
27889
|
const params = typeof r.url === "object" && r.url?.query ? rows(r.url.query) : [];
|
|
27890
27890
|
const url = params.length ? withQuery(urlOf(r.url), params) : urlOf(r.url);
|
|
27891
|
-
const
|
|
27891
|
+
const headers2 = typeof r.header === "string" ? [] : rows(r.header);
|
|
27892
27892
|
const preRequest = script(item.event, "prerequest");
|
|
27893
27893
|
return newRequest({
|
|
27894
27894
|
name: item.name || url || "Untitled request",
|
|
27895
27895
|
method: (r.method ?? "GET").toUpperCase(),
|
|
27896
27896
|
url,
|
|
27897
27897
|
params: params.length ? params : rows([]),
|
|
27898
|
-
headers,
|
|
27898
|
+
headers: headers2,
|
|
27899
27899
|
body: bodyOf(r.body, where, warnings),
|
|
27900
27900
|
auth: authOf(r.auth, where, warnings) ?? { type: "inherit" },
|
|
27901
27901
|
...script(item.event, "test") ? { tests: script(item.event, "test") } : {},
|
|
@@ -27974,12 +27974,12 @@ function runnableRequests(collection, folderId) {
|
|
|
27974
27974
|
walk(start, root?.type === "folder" ? [root.name] : []);
|
|
27975
27975
|
return out;
|
|
27976
27976
|
}
|
|
27977
|
-
function parseCsv(
|
|
27977
|
+
function parseCsv(text2) {
|
|
27978
27978
|
const rows2 = [];
|
|
27979
27979
|
let row = [];
|
|
27980
27980
|
let field = "";
|
|
27981
27981
|
let quoted = false;
|
|
27982
|
-
const s =
|
|
27982
|
+
const s = text2.replace(/^/, "");
|
|
27983
27983
|
for (let i = 0; i < s.length; i++) {
|
|
27984
27984
|
const c = s[i];
|
|
27985
27985
|
if (quoted) {
|
|
@@ -28004,16 +28004,16 @@ function parseCsv(text) {
|
|
|
28004
28004
|
if (row.some((f) => f !== "")) rows2.push(row);
|
|
28005
28005
|
return rows2;
|
|
28006
28006
|
}
|
|
28007
|
-
function parseDataFile(
|
|
28008
|
-
const trimmed =
|
|
28007
|
+
function parseDataFile(text2, filename = "") {
|
|
28008
|
+
const trimmed = text2.trim();
|
|
28009
28009
|
if (filename.toLowerCase().endsWith(".json") || trimmed.startsWith("[")) {
|
|
28010
28010
|
const data = JSON.parse(trimmed);
|
|
28011
28011
|
if (!Array.isArray(data) || !data.every((r) => r && typeof r === "object" && !Array.isArray(r))) throw new Error("A JSON data file must be an array of objects.");
|
|
28012
28012
|
return data.map((r) => Object.fromEntries(Object.entries(r).map(([k, v]) => [k, typeof v === "string" ? v : JSON.stringify(v)])));
|
|
28013
28013
|
}
|
|
28014
|
-
const [
|
|
28015
|
-
if (!
|
|
28016
|
-
return rows2.map((r) => Object.fromEntries(
|
|
28014
|
+
const [header2, ...rows2] = parseCsv(text2);
|
|
28015
|
+
if (!header2?.length) throw new Error("The CSV file is empty.");
|
|
28016
|
+
return rows2.map((r) => Object.fromEntries(header2.map((h, i) => [h.trim(), r[i] ?? ""])));
|
|
28017
28017
|
}
|
|
28018
28018
|
function summarise(steps) {
|
|
28019
28019
|
const tests = steps.flatMap((s) => s.tests);
|
|
@@ -28049,15 +28049,15 @@ function pathMatch(reqPath, cookiePath) {
|
|
|
28049
28049
|
return cookiePath.endsWith("/") || reqPath[cookiePath.length] === "/";
|
|
28050
28050
|
}
|
|
28051
28051
|
var secureOk = (u) => u.protocol === "https:" || ["localhost", "127.0.0.1", "::1"].includes(hostOf(u)) || hostOf(u).endsWith(".localhost");
|
|
28052
|
-
function parseSetCookie(
|
|
28052
|
+
function parseSetCookie(header2, url, now = Date.now()) {
|
|
28053
28053
|
let u;
|
|
28054
28054
|
try {
|
|
28055
28055
|
u = new URL(url);
|
|
28056
28056
|
} catch {
|
|
28057
28057
|
return null;
|
|
28058
28058
|
}
|
|
28059
|
-
if (
|
|
28060
|
-
const [pair = "", ...attrs] =
|
|
28059
|
+
if (header2.length > MAX_COOKIE_BYTES) return null;
|
|
28060
|
+
const [pair = "", ...attrs] = header2.split(";");
|
|
28061
28061
|
const eq = pair.indexOf("=");
|
|
28062
28062
|
if (eq < 1) return null;
|
|
28063
28063
|
const name = pair.slice(0, eq).trim();
|
|
@@ -28163,6 +28163,249 @@ function mergeCookieHeader(userHeader, jarCookies) {
|
|
|
28163
28163
|
return [...own, ...jarCookies.filter((c) => !names.has(c.name)).map((c) => `${c.name}=${c.value}`)].join("; ");
|
|
28164
28164
|
}
|
|
28165
28165
|
|
|
28166
|
+
// ../../packages/core/src/security.ts
|
|
28167
|
+
var ORDER = ["high", "medium", "low", "info"];
|
|
28168
|
+
var SECURITY_SEVERITIES = ORDER;
|
|
28169
|
+
var atLeast = (severity, threshold) => ORDER.indexOf(severity) <= ORDER.indexOf(threshold);
|
|
28170
|
+
var BODY_SCAN = 256 * 1024;
|
|
28171
|
+
var LOCAL = /^(localhost|127(?:\.\d{1,3}){3}|\[::1\]|::1|0\.0\.0\.0)$/i;
|
|
28172
|
+
var SESSION_COOKIE = /(sess|sid|auth|token|jwt|login|remember|csrf|xsrf)/i;
|
|
28173
|
+
var URL_SECRET = /^(access_?token|id_?token|refresh_?token|token|api_?key|apikey|key|secret|client_?secret|password|passwd|pwd|auth|session_?id|sessionid|jwt)$/i;
|
|
28174
|
+
var BODY_SECRET = /^(password|passwd|pwd|password_?hash|passwordhash|secret|client_?secret|api_?secret|private_?key|privatekey|ssn|card_?number|cardnumber|cvv|cvc)$/i;
|
|
28175
|
+
var ERROR_SIGNS = [
|
|
28176
|
+
[/\n\s+at [\w$.<>]+ \(?[^\n]*:\d+:\d+\)?/, "a JavaScript stack trace"],
|
|
28177
|
+
[/Traceback \(most recent call last\)/, "a Python traceback"],
|
|
28178
|
+
[/(?:^|\n)\s*at (?:java|javax|org\.springframework|com\.)[\w.$]+\([\w.]+:\d+\)/, "a Java stack trace"],
|
|
28179
|
+
[/Exception in thread "/, "a Java exception"],
|
|
28180
|
+
[/You have an error in your SQL syntax|SQLSTATE\[|ORA-\d{5}|PG::\w+Error|pg_query\(\)|SQLite3::|Microsoft OLE DB Provider|Unclosed quotation mark after the character string/i, "a database error"],
|
|
28181
|
+
[/(?:Fatal error|Warning|Notice): .+ in \/[^\s]+\.php on line \d+/, "a PHP error with a file path"],
|
|
28182
|
+
[/\/node_modules\/[\w@.-]+\//, "server file paths"],
|
|
28183
|
+
[/System\.\w+Exception|at System\.[\w.]+\(/, "a .NET exception"],
|
|
28184
|
+
[/ActionController::|ActiveRecord::\w+Error/, "a Rails error"]
|
|
28185
|
+
];
|
|
28186
|
+
var header = (list, name) => list.find(([k]) => k.toLowerCase() === name)?.[1];
|
|
28187
|
+
var headers = (list, name) => list.filter(([k]) => k.toLowerCase() === name).map(([, v]) => v);
|
|
28188
|
+
function passiveFindings(input) {
|
|
28189
|
+
const out = [];
|
|
28190
|
+
const add = (f) => {
|
|
28191
|
+
if (!out.some((x) => x.id === f.id)) out.push(f);
|
|
28192
|
+
};
|
|
28193
|
+
let url = null;
|
|
28194
|
+
try {
|
|
28195
|
+
url = new URL(input.url);
|
|
28196
|
+
} catch {
|
|
28197
|
+
}
|
|
28198
|
+
const local = !!url && LOCAL.test(url.hostname);
|
|
28199
|
+
const https = url?.protocol === "https:";
|
|
28200
|
+
const res = input.response;
|
|
28201
|
+
const type = (header(res.headers, "content-type") ?? "").toLowerCase();
|
|
28202
|
+
const html = type.includes("text/html");
|
|
28203
|
+
if (url?.protocol === "http:" && !local) add({
|
|
28204
|
+
id: "transport.http",
|
|
28205
|
+
severity: "medium",
|
|
28206
|
+
title: "Sent over plain HTTP",
|
|
28207
|
+
detail: "Anyone on the network path can read and change this request and its answer, including tokens and cookies.",
|
|
28208
|
+
fix: "Serve the API over HTTPS only, and redirect or refuse plain HTTP."
|
|
28209
|
+
});
|
|
28210
|
+
if (https && !local) {
|
|
28211
|
+
const hsts = header(res.headers, "strict-transport-security");
|
|
28212
|
+
if (!hsts) add({
|
|
28213
|
+
id: "hsts.missing",
|
|
28214
|
+
severity: "low",
|
|
28215
|
+
title: "No Strict-Transport-Security header",
|
|
28216
|
+
detail: "Without HSTS, a browser can be tricked into using plain HTTP for this host on a first visit or a typed URL.",
|
|
28217
|
+
fix: "Send Strict-Transport-Security: max-age=31536000; includeSubDomains on HTTPS responses.",
|
|
28218
|
+
evidence: "strict-transport-security"
|
|
28219
|
+
});
|
|
28220
|
+
else {
|
|
28221
|
+
const age = Number(/max-age\s*=\s*"?(\d+)/i.exec(hsts)?.[1] ?? "0");
|
|
28222
|
+
if (age < 15552e3) add({
|
|
28223
|
+
id: "hsts.short",
|
|
28224
|
+
severity: "info",
|
|
28225
|
+
title: "Strict-Transport-Security max-age is short",
|
|
28226
|
+
detail: `max-age is ${age} seconds. Under 180 days, browsers forget the rule quickly and the protection lapses.`,
|
|
28227
|
+
fix: "Use max-age=31536000 (one year) once HTTPS works everywhere on the host.",
|
|
28228
|
+
evidence: "strict-transport-security"
|
|
28229
|
+
});
|
|
28230
|
+
}
|
|
28231
|
+
}
|
|
28232
|
+
if (!header(res.headers, "x-content-type-options")?.toLowerCase().includes("nosniff") && res.body.length > 0) add({
|
|
28233
|
+
id: "headers.nosniff",
|
|
28234
|
+
severity: "low",
|
|
28235
|
+
title: "No X-Content-Type-Options: nosniff",
|
|
28236
|
+
detail: "Browsers may guess the type of the answer and run it as script or HTML, which can turn an upload or a JSON answer into an attack.",
|
|
28237
|
+
fix: "Send X-Content-Type-Options: nosniff on every response.",
|
|
28238
|
+
evidence: "x-content-type-options"
|
|
28239
|
+
});
|
|
28240
|
+
if (html) {
|
|
28241
|
+
const csp = headers(res.headers, "content-security-policy").join("; ");
|
|
28242
|
+
if (!csp) add({
|
|
28243
|
+
id: "headers.csp-missing",
|
|
28244
|
+
severity: "medium",
|
|
28245
|
+
title: "HTML page without a Content-Security-Policy",
|
|
28246
|
+
detail: "A CSP limits what scripts a page can load and run. Without one, any injected script runs with the page's full rights.",
|
|
28247
|
+
fix: "Add a Content-Security-Policy, starting from default-src 'self' and loosening only what the page needs.",
|
|
28248
|
+
evidence: "content-security-policy"
|
|
28249
|
+
});
|
|
28250
|
+
const xfo = header(res.headers, "x-frame-options");
|
|
28251
|
+
if (!/frame-ancestors/i.test(csp) && !xfo) add({
|
|
28252
|
+
id: "headers.framing",
|
|
28253
|
+
severity: "low",
|
|
28254
|
+
title: "Page can be shown inside another site's frame",
|
|
28255
|
+
detail: "Another site can load this page in a hidden frame and trick people into clicking on it (clickjacking).",
|
|
28256
|
+
fix: "Send Content-Security-Policy: frame-ancestors 'none' (or 'self'), or X-Frame-Options: DENY.",
|
|
28257
|
+
evidence: "x-frame-options"
|
|
28258
|
+
});
|
|
28259
|
+
}
|
|
28260
|
+
const acao = header(res.headers, "access-control-allow-origin")?.trim();
|
|
28261
|
+
const acac = header(res.headers, "access-control-allow-credentials")?.trim().toLowerCase() === "true";
|
|
28262
|
+
const sentOrigin = header(input.requestHeaders, "origin");
|
|
28263
|
+
if (acao === "*" && acac) add({
|
|
28264
|
+
id: "cors.wildcard-credentials",
|
|
28265
|
+
severity: "high",
|
|
28266
|
+
title: "CORS allows any origin with credentials",
|
|
28267
|
+
detail: "Access-Control-Allow-Origin: * together with Allow-Credentials: true shows the server means to let any website read signed-in answers. Browsers block this exact pair, so the server likely also echoes origins elsewhere.",
|
|
28268
|
+
fix: "Allow only a fixed list of your own origins, and send credentials only to those.",
|
|
28269
|
+
evidence: "access-control-allow-origin"
|
|
28270
|
+
});
|
|
28271
|
+
if (acao === "null") add({
|
|
28272
|
+
id: "cors.null-origin",
|
|
28273
|
+
severity: "medium",
|
|
28274
|
+
title: 'CORS allows the "null" origin',
|
|
28275
|
+
detail: "Sandboxed frames and local files send Origin: null, so any attacker page can use a sandboxed frame to read these answers.",
|
|
28276
|
+
fix: "Never allow the null origin; list your real origins instead.",
|
|
28277
|
+
evidence: "access-control-allow-origin"
|
|
28278
|
+
});
|
|
28279
|
+
if (sentOrigin && acao && acao !== "*" && acao === sentOrigin && acac && !local) add({
|
|
28280
|
+
id: "cors.reflected-origin",
|
|
28281
|
+
severity: "medium",
|
|
28282
|
+
title: "CORS echoes the request's origin with credentials",
|
|
28283
|
+
detail: `The answer allowed ${sentOrigin} to read it with cookies. If the server copies any Origin it receives, every website can read signed-in data. Run the active checks to confirm with an origin you do not own.`,
|
|
28284
|
+
fix: "Compare the Origin against a fixed allow-list before echoing it.",
|
|
28285
|
+
evidence: "access-control-allow-origin"
|
|
28286
|
+
});
|
|
28287
|
+
const setCookies = headers(res.headers, "set-cookie");
|
|
28288
|
+
const noSecure = [], noHttpOnly = [], noSameSite = [];
|
|
28289
|
+
for (const c of setCookies) {
|
|
28290
|
+
const [pair = "", ...attrs] = c.split(";");
|
|
28291
|
+
const name = pair.split("=")[0].trim();
|
|
28292
|
+
if (!name) continue;
|
|
28293
|
+
const a = attrs.map((x) => x.trim().toLowerCase());
|
|
28294
|
+
const has = (k) => a.some((x) => x === k || x.startsWith(`${k}=`));
|
|
28295
|
+
if (https && !has("secure")) noSecure.push(name);
|
|
28296
|
+
if (SESSION_COOKIE.test(name) && !has("httponly")) noHttpOnly.push(name);
|
|
28297
|
+
if (!has("samesite")) noSameSite.push(name);
|
|
28298
|
+
}
|
|
28299
|
+
if (noSecure.length) add({
|
|
28300
|
+
id: "cookie.secure",
|
|
28301
|
+
severity: "medium",
|
|
28302
|
+
title: "Cookie without the Secure flag",
|
|
28303
|
+
detail: "The browser will also send this cookie over plain HTTP, where it can be read on the network.",
|
|
28304
|
+
fix: "Add Secure to every cookie set over HTTPS.",
|
|
28305
|
+
evidence: noSecure.join(", ")
|
|
28306
|
+
});
|
|
28307
|
+
if (noHttpOnly.length) add({
|
|
28308
|
+
id: "cookie.httponly",
|
|
28309
|
+
severity: "medium",
|
|
28310
|
+
title: "Session cookie readable by scripts",
|
|
28311
|
+
detail: "Without HttpOnly, any script injected into the page can read this cookie and take over the session.",
|
|
28312
|
+
fix: "Add HttpOnly to session and authentication cookies.",
|
|
28313
|
+
evidence: noHttpOnly.join(", ")
|
|
28314
|
+
});
|
|
28315
|
+
if (noSameSite.length) add({
|
|
28316
|
+
id: "cookie.samesite",
|
|
28317
|
+
severity: "low",
|
|
28318
|
+
title: "Cookie without a SameSite setting",
|
|
28319
|
+
detail: "Older browsers send cookies without SameSite on requests started by other sites, which helps cross-site request forgery.",
|
|
28320
|
+
fix: "Set SameSite=Lax (or Strict) explicitly; use None only with Secure and when cross-site use is needed.",
|
|
28321
|
+
evidence: noSameSite.join(", ")
|
|
28322
|
+
});
|
|
28323
|
+
const server = header(res.headers, "server");
|
|
28324
|
+
if (server && /\d+\.\d+/.test(server)) add({
|
|
28325
|
+
id: "disclosure.server-version",
|
|
28326
|
+
severity: "low",
|
|
28327
|
+
title: "Server version given away",
|
|
28328
|
+
detail: `The Server header says "${server.slice(0, 80)}". Exact versions tell attackers which known flaws to try.`,
|
|
28329
|
+
fix: "Hide the version (for example server_tokens off in nginx, ServerTokens Prod in Apache).",
|
|
28330
|
+
evidence: "server"
|
|
28331
|
+
});
|
|
28332
|
+
for (const name of ["x-powered-by", "x-aspnet-version", "x-aspnetmvc-version", "x-generator"]) {
|
|
28333
|
+
const v = header(res.headers, name);
|
|
28334
|
+
if (v) {
|
|
28335
|
+
add({
|
|
28336
|
+
id: "disclosure.powered-by",
|
|
28337
|
+
severity: "low",
|
|
28338
|
+
title: "Framework given away in a header",
|
|
28339
|
+
detail: `${name}: ${v.slice(0, 80)} tells attackers what the server runs.`,
|
|
28340
|
+
fix: "Remove the header (for example app.disable('x-powered-by') in Express, expose_php = Off in PHP).",
|
|
28341
|
+
evidence: name
|
|
28342
|
+
});
|
|
28343
|
+
break;
|
|
28344
|
+
}
|
|
28345
|
+
}
|
|
28346
|
+
const text2 = res.bodyEncoding === "utf8" ? res.body.slice(0, BODY_SCAN) : "";
|
|
28347
|
+
if (text2) {
|
|
28348
|
+
const sign = ERROR_SIGNS.find(([re]) => re.test(text2));
|
|
28349
|
+
if (sign) add({
|
|
28350
|
+
id: "disclosure.error-detail",
|
|
28351
|
+
severity: "medium",
|
|
28352
|
+
title: "Internal error details in the answer",
|
|
28353
|
+
detail: `The body contains ${sign[1]}. Stack traces and database errors reveal code paths, file names and queries that make attacks easier.`,
|
|
28354
|
+
fix: "Return a short error with a reference id, and log the details on the server only.",
|
|
28355
|
+
evidence: sign[1]
|
|
28356
|
+
});
|
|
28357
|
+
}
|
|
28358
|
+
if (url) {
|
|
28359
|
+
const names = [...url.searchParams.keys()].filter((k) => URL_SECRET.test(k));
|
|
28360
|
+
if (names.length) add({
|
|
28361
|
+
id: "url.credentials",
|
|
28362
|
+
severity: "medium",
|
|
28363
|
+
title: "Credentials in the URL",
|
|
28364
|
+
detail: "URLs end up in server logs, proxy logs, browser history and Referer headers, so a secret in the query string leaks widely.",
|
|
28365
|
+
fix: "Send credentials in a header (Authorization) or the request body instead.",
|
|
28366
|
+
evidence: [...new Set(names)].join(", ")
|
|
28367
|
+
});
|
|
28368
|
+
}
|
|
28369
|
+
if (header(input.requestHeaders, "authorization") || header(input.requestHeaders, "cookie")) {
|
|
28370
|
+
const cc = (header(res.headers, "cache-control") ?? "").toLowerCase();
|
|
28371
|
+
if (res.status < 400 && !/no-store|private/.test(cc)) add({
|
|
28372
|
+
id: "cache.authenticated",
|
|
28373
|
+
severity: "low",
|
|
28374
|
+
title: "Signed-in answer may be cached",
|
|
28375
|
+
detail: "The request carried credentials, but the answer does not say Cache-Control: no-store or private, so a shared cache or proxy may keep it and serve it to someone else.",
|
|
28376
|
+
fix: "Send Cache-Control: no-store on answers that depend on who is signed in.",
|
|
28377
|
+
evidence: "cache-control"
|
|
28378
|
+
});
|
|
28379
|
+
}
|
|
28380
|
+
if (text2 && (type.includes("json") || /^\s*[[{]/.test(text2))) {
|
|
28381
|
+
let data;
|
|
28382
|
+
try {
|
|
28383
|
+
data = JSON.parse(res.body.length > BODY_SCAN ? "" : res.body);
|
|
28384
|
+
} catch {
|
|
28385
|
+
data = void 0;
|
|
28386
|
+
}
|
|
28387
|
+
const paths = [];
|
|
28388
|
+
const walk = (v, path, depth) => {
|
|
28389
|
+
if (depth > 12 || paths.length >= 10 || !v || typeof v !== "object") return;
|
|
28390
|
+
for (const [k, child] of Object.entries(v)) {
|
|
28391
|
+
const p = path ? `${path}.${k}` : k;
|
|
28392
|
+
if (BODY_SECRET.test(k) && (typeof child === "string" || typeof child === "number") && String(child).length > 0) paths.push(Array.isArray(v) ? path : p);
|
|
28393
|
+
else walk(child, Array.isArray(v) ? `${path}[]` : p, depth + 1);
|
|
28394
|
+
}
|
|
28395
|
+
};
|
|
28396
|
+
walk(data, "", 0);
|
|
28397
|
+
if (paths.length) add({
|
|
28398
|
+
id: "body.secret-field",
|
|
28399
|
+
severity: "medium",
|
|
28400
|
+
title: "Secret field sent back in the answer",
|
|
28401
|
+
detail: "The JSON answer includes fields that look like passwords, password hashes, keys or card data. Answers are logged and cached in many places; secrets should never leave the server.",
|
|
28402
|
+
fix: "Leave these fields out of the response model (an explicit allow-list of fields to return).",
|
|
28403
|
+
evidence: [...new Set(paths)].join(", ")
|
|
28404
|
+
});
|
|
28405
|
+
}
|
|
28406
|
+
return out.sort((a, b) => ORDER.indexOf(a.severity) - ORDER.indexOf(b.severity));
|
|
28407
|
+
}
|
|
28408
|
+
|
|
28166
28409
|
// ../../packages/core/src/pipeline.ts
|
|
28167
28410
|
function applyVariableUpdates(rows2, updates) {
|
|
28168
28411
|
let out = rows2;
|
|
@@ -28208,17 +28451,17 @@ async function executeRequest(host, input) {
|
|
|
28208
28451
|
}
|
|
28209
28452
|
}
|
|
28210
28453
|
const s = host.scopes();
|
|
28211
|
-
const
|
|
28454
|
+
const resolve4 = makeResolver([local, iterationData, s.environment ?? {}, s.collection ?? {}, s.globals]);
|
|
28212
28455
|
let auth = draft.auth.type === "inherit" ? inherited : draft.auth;
|
|
28213
28456
|
if (auth?.type === "oauth2") {
|
|
28214
|
-
const got = await ensureToken(host, auth,
|
|
28457
|
+
const got = await ensureToken(host, auth, resolve4, signal);
|
|
28215
28458
|
if (!got.ok) return { result: { ok: false, error: { code: "auth", error: `Could not get an OAuth 2.0 token: ${got.error}` } }, scripts: hasOutput() ? merged : void 0 };
|
|
28216
28459
|
auth = { ...auth, token: got.token };
|
|
28217
28460
|
draft.auth = auth;
|
|
28218
28461
|
}
|
|
28219
28462
|
let wire;
|
|
28220
28463
|
try {
|
|
28221
|
-
wire = buildSendRequest(draft,
|
|
28464
|
+
wire = buildSendRequest(draft, resolve4, inherited, host.files);
|
|
28222
28465
|
} catch (e) {
|
|
28223
28466
|
return { result: { ok: false, error: { code: "invalid_request", error: e.message } }, scripts: hasOutput() ? merged : void 0 };
|
|
28224
28467
|
}
|
|
@@ -28235,8 +28478,8 @@ async function executeRequest(host, input) {
|
|
|
28235
28478
|
const result = await host.send(wire, signal);
|
|
28236
28479
|
if (host.cookies && result.ok) {
|
|
28237
28480
|
for (const c of result.response.setCookies ?? []) host.cookies.store(c.url, [c.value]);
|
|
28238
|
-
const
|
|
28239
|
-
if (
|
|
28481
|
+
const set2 = result.response.headers.filter(([k]) => k.toLowerCase() === "set-cookie").map(([, v]) => v);
|
|
28482
|
+
if (set2.length) host.cookies.store(result.response.url || wire.url, set2);
|
|
28240
28483
|
}
|
|
28241
28484
|
if (signal?.aborted || !result.ok || chain.tests.length === 0) {
|
|
28242
28485
|
return { result, wire, scripts: chain.preRequest.length && hasOutput() ? merged : void 0 };
|
|
@@ -28254,8 +28497,8 @@ async function executeRequest(host, input) {
|
|
|
28254
28497
|
}
|
|
28255
28498
|
return { result, wire, scripts: merged };
|
|
28256
28499
|
}
|
|
28257
|
-
async function ensureToken(host, a,
|
|
28258
|
-
const key = tokenCacheKey(a,
|
|
28500
|
+
async function ensureToken(host, a, resolve4, signal, force = false) {
|
|
28501
|
+
const key = tokenCacheKey(a, resolve4);
|
|
28259
28502
|
const cached = host.tokens?.get(key);
|
|
28260
28503
|
if (!force) {
|
|
28261
28504
|
if (tokenFresh(a.token)) return { ok: true, token: a.token };
|
|
@@ -28263,7 +28506,7 @@ async function ensureToken(host, a, resolve3, signal, force = false) {
|
|
|
28263
28506
|
}
|
|
28264
28507
|
const refresh = force ? void 0 : cached?.refreshToken ?? a.token?.refreshToken;
|
|
28265
28508
|
const attempt = async (refreshToken) => {
|
|
28266
|
-
const r = await host.send(tokenRequest(a,
|
|
28509
|
+
const r = await host.send(tokenRequest(a, resolve4, refreshToken), signal);
|
|
28267
28510
|
if (!r.ok) throw new OAuth2Error(r.error.error);
|
|
28268
28511
|
const t = parseTokenResponse(r.response);
|
|
28269
28512
|
return refreshToken && !t.refreshToken ? { ...t, refreshToken } : t;
|
|
@@ -28284,6 +28527,7 @@ async function ensureToken(host, a, resolve3, signal, force = false) {
|
|
|
28284
28527
|
}
|
|
28285
28528
|
function toRunStep(iteration, requestId, path, request2, out) {
|
|
28286
28529
|
const { result, scripts } = out;
|
|
28530
|
+
const security = result?.ok && out.wire ? passiveFindings({ method: out.wire.method, url: out.wire.url, requestHeaders: out.wire.headers, response: result.response }) : [];
|
|
28287
28531
|
return {
|
|
28288
28532
|
iteration,
|
|
28289
28533
|
requestId,
|
|
@@ -28293,48 +28537,98 @@ function toRunStep(iteration, requestId, path, request2, out) {
|
|
|
28293
28537
|
url: out.wire?.url ?? request2.url,
|
|
28294
28538
|
...result?.ok ? { status: result.response.status, timeMs: result.response.timeMs } : { error: result ? result.error.error : `Pre-request script failed: ${scripts?.error ?? "unknown error"}` },
|
|
28295
28539
|
tests: [...scripts?.tests ?? [], ...scripts?.error && result?.ok ? [{ name: "Script error", passed: false, error: scripts.error }] : []],
|
|
28296
|
-
...scripts?.logs.length ? { logs: scripts.logs } : {}
|
|
28540
|
+
...scripts?.logs.length ? { logs: scripts.logs } : {},
|
|
28541
|
+
...security.length ? { security } : {}
|
|
28297
28542
|
};
|
|
28298
28543
|
}
|
|
28299
28544
|
var failed = (s) => !!s.error || s.tests.some((t) => !t.passed);
|
|
28545
|
+
var MAX_PARALLEL = 50;
|
|
28546
|
+
function laneHost(host, start) {
|
|
28547
|
+
const env = start.environment ? { ...start.environment } : null;
|
|
28548
|
+
const col = start.collection ? { ...start.collection } : null;
|
|
28549
|
+
const glob = { ...start.globals };
|
|
28550
|
+
const put = (scope, u) => {
|
|
28551
|
+
if (!scope) return;
|
|
28552
|
+
for (const [k, v] of Object.entries(u)) {
|
|
28553
|
+
if (v === null) delete scope[k];
|
|
28554
|
+
else scope[k] = v;
|
|
28555
|
+
}
|
|
28556
|
+
};
|
|
28557
|
+
const jar = host.cookies ? new CookieJar(host.cookies.list?.() ?? []) : void 0;
|
|
28558
|
+
return {
|
|
28559
|
+
...host,
|
|
28560
|
+
scopes: () => ({ environment: env ? { ...env } : null, collection: col ? { ...col } : null, globals: { ...glob } }),
|
|
28561
|
+
apply: (u) => {
|
|
28562
|
+
put(env, u.environment);
|
|
28563
|
+
put(col, u.collection);
|
|
28564
|
+
put(glob, u.globals);
|
|
28565
|
+
},
|
|
28566
|
+
cookies: jar
|
|
28567
|
+
};
|
|
28568
|
+
}
|
|
28300
28569
|
async function runCollection(host, opts) {
|
|
28301
|
-
const { collection
|
|
28302
|
-
const
|
|
28570
|
+
const { collection } = opts;
|
|
28571
|
+
const parallel = opts.parallel ?? 1;
|
|
28572
|
+
if (!Number.isInteger(parallel) || parallel < 1 || parallel > MAX_PARALLEL) throw new RangeError(`parallel must be a whole number between 1 and ${MAX_PARALLEL}.`);
|
|
28573
|
+
const only = opts.requestIds ? new Set(opts.requestIds) : null;
|
|
28574
|
+
const list = runnableRequests(collection, opts.folderId).filter((r) => !only || only.has(r.requestId));
|
|
28303
28575
|
const rounds = opts.data?.length ? opts.data.length : Math.max(1, opts.iterations ?? 1);
|
|
28304
|
-
const
|
|
28576
|
+
const stop = new AbortController();
|
|
28577
|
+
const onOuterAbort = () => stop.abort();
|
|
28578
|
+
opts.signal?.addEventListener("abort", onOuterAbort);
|
|
28579
|
+
if (opts.signal?.aborted) stop.abort();
|
|
28580
|
+
const signal = stop.signal;
|
|
28581
|
+
const byIteration = Array.from({ length: rounds }, () => []);
|
|
28305
28582
|
let bailed = false;
|
|
28306
|
-
|
|
28583
|
+
const start = parallel > 1 ? host.scopes() : null;
|
|
28584
|
+
const iteration = async (it) => {
|
|
28585
|
+
const h = start ? laneHost(host, start) : host;
|
|
28307
28586
|
opts.onIteration?.(it, rounds);
|
|
28308
28587
|
for (const r of list) {
|
|
28309
|
-
if (signal
|
|
28588
|
+
if (signal.aborted) return;
|
|
28310
28589
|
const current = findItem(collection.items, r.requestId);
|
|
28311
28590
|
const request2 = current?.type === "request" ? current.request : r.request;
|
|
28312
|
-
const out = await executeRequest(
|
|
28313
|
-
if (signal
|
|
28591
|
+
const out = await executeRequest(h, { draft: request2, collection, requestId: r.requestId, data: opts.data?.[it], iteration: it, signal });
|
|
28592
|
+
if (signal.aborted) return;
|
|
28314
28593
|
const step = toRunStep(it, r.requestId, r.path, request2, out);
|
|
28315
|
-
|
|
28594
|
+
byIteration[it].push(step);
|
|
28316
28595
|
opts.onStep?.(step, out);
|
|
28317
28596
|
if (opts.bail && failed(step)) {
|
|
28318
28597
|
bailed = true;
|
|
28319
|
-
|
|
28598
|
+
stop.abort();
|
|
28599
|
+
return;
|
|
28320
28600
|
}
|
|
28321
28601
|
if (opts.delayMs) await new Promise((res) => setTimeout(res, opts.delayMs));
|
|
28322
28602
|
}
|
|
28603
|
+
opts.onIterationDone?.(it, rounds, byIteration[it]);
|
|
28604
|
+
};
|
|
28605
|
+
try {
|
|
28606
|
+
let next = 0;
|
|
28607
|
+
const worker = async () => {
|
|
28608
|
+
while (!signal.aborted && next < rounds) await iteration(next++);
|
|
28609
|
+
};
|
|
28610
|
+
await Promise.all(Array.from({ length: Math.min(parallel, rounds) }, worker));
|
|
28611
|
+
} finally {
|
|
28612
|
+
opts.signal?.removeEventListener("abort", onOuterAbort);
|
|
28323
28613
|
}
|
|
28614
|
+
const steps = byIteration.flat();
|
|
28324
28615
|
return { collection: collection.name, steps, summary: summarise(steps), bailed };
|
|
28325
28616
|
}
|
|
28326
28617
|
var xml = (s) => s.replace(/[\u0000-\u0008\u000B\u000C\u000E-\u001F\uFFFE\uFFFF]/g, "").replace(/[<>&"']/g, (c) => ({ "<": "<", ">": ">", "&": "&", '"': """, "'": "'" })[c]);
|
|
28327
|
-
function toJUnit(report) {
|
|
28618
|
+
function toJUnit(report, opts = {}) {
|
|
28619
|
+
const securityCases = (s) => (opts.securityFailOn ? (s.security ?? []).filter((f) => atLeast(f.severity, opts.securityFailOn)) : []).map((f) => ` <testcase name="${xml(`Security: ${f.title}`)}" classname="${xml(s.name)}" time="0"><failure message="${xml(`${f.severity}: ${f.detail}`)}" type="SecurityFinding">${xml(`Fix: ${f.fix}`)}</failure></testcase>`);
|
|
28328
28620
|
const suites = report.steps.map((s) => {
|
|
28329
28621
|
const name = [...s.path, s.name].join(" / ");
|
|
28330
|
-
const
|
|
28331
|
-
const
|
|
28622
|
+
const sec = securityCases(s);
|
|
28623
|
+
const plain = s.error ? [` <testcase name="Request" classname="${xml(s.name)}" time="0"><failure message="${xml(s.error)}" type="RequestError">${xml(`${s.method} ${s.url}`)}</failure></testcase>`] : s.tests.map((t) => t.passed ? ` <testcase name="${xml(t.name)}" classname="${xml(s.name)}" time="${((s.timeMs ?? 0) / 1e3).toFixed(3)}"/>` : ` <testcase name="${xml(t.name)}" classname="${xml(s.name)}" time="${((s.timeMs ?? 0) / 1e3).toFixed(3)}"><failure message="${xml(t.error ?? "failed")}" type="AssertionError"/></testcase>`);
|
|
28624
|
+
const cases = [...plain, ...sec];
|
|
28625
|
+
const failures2 = (s.error ? 1 : s.tests.filter((t) => !t.passed).length) + sec.length;
|
|
28332
28626
|
return ` <testsuite name="${xml(name)}" tests="${cases.length}" failures="${failures2}" errors="0" time="${((s.timeMs ?? 0) / 1e3).toFixed(3)}" iteration="${s.iteration}">
|
|
28333
28627
|
${cases.join("\n")}
|
|
28334
28628
|
</testsuite>`;
|
|
28335
28629
|
});
|
|
28336
|
-
const tests = report.steps.reduce((n, s) => n + (s.error ? 1 : s.tests.length), 0);
|
|
28337
|
-
const failures = report.steps.reduce((n, s) => n + (s.error ? 1 : s.tests.filter((t) => !t.passed).length), 0);
|
|
28630
|
+
const tests = report.steps.reduce((n, s) => n + (s.error ? 1 : s.tests.length) + securityCases(s).length, 0);
|
|
28631
|
+
const failures = report.steps.reduce((n, s) => n + (s.error ? 1 : s.tests.filter((t) => !t.passed).length) + securityCases(s).length, 0);
|
|
28338
28632
|
return `<?xml version="1.0" encoding="UTF-8"?>
|
|
28339
28633
|
<testsuites name="${xml(report.collection)}" tests="${tests}" failures="${failures}">
|
|
28340
28634
|
${suites.join("\n")}
|
|
@@ -28449,6 +28743,194 @@ var OutputFormat;
|
|
|
28449
28743
|
// ../../packages/core/src/validation.ts
|
|
28450
28744
|
var MAX_CONFIG_BYTES = 64 * 1024;
|
|
28451
28745
|
|
|
28746
|
+
// ../../packages/core/src/active.ts
|
|
28747
|
+
var SAFE = /* @__PURE__ */ new Set(["GET", "HEAD", "OPTIONS"]);
|
|
28748
|
+
var PROBE_HOST = "wirecatch-probe.invalid";
|
|
28749
|
+
var PROBE_ORIGIN = `https://${PROBE_HOST}`;
|
|
28750
|
+
var CANARY = "wc<b>wcprobe7q</b>";
|
|
28751
|
+
var CANARY_SEEN = "<b>wcprobe7q</b>";
|
|
28752
|
+
var CRED_HEADERS = /^(authorization|cookie|x-api-key|api-key|apikey|x-auth-token|x-access-token|proxy-authorization)$/i;
|
|
28753
|
+
var CRED_PARAMS = /^(access_?token|token|api_?key|apikey|key|auth|session_?id|jwt)$/i;
|
|
28754
|
+
var DB_ERROR = /You have an error in your SQL syntax|SQLSTATE\[|ORA-\d{5}|PG::\w+Error|pg_query\(\)|SQLite3::|SQLITE_ERROR|Microsoft OLE DB Provider|Unclosed quotation mark|unterminated quoted string|syntax error at or near|quoted string not properly terminated/i;
|
|
28755
|
+
var ROUTING_HEADER = /^(host|:authority|:path|:scheme|:method|forwarded|x-forwarded-[\w-]+|x-real-ip|x-client-ip|true-client-ip|x-originating-ip|x-original-url|x-rewrite-url|connection|keep-alive|transfer-encoding|te|trailer|upgrade|proxy-[\w-]+|content-length)$/i;
|
|
28756
|
+
var LOCAL_HOST = /^(localhost|[\w-]+\.localhost|127(?:\.\d{1,3}){3}|::1|\[::1\])$/i;
|
|
28757
|
+
function isLocalTarget(url) {
|
|
28758
|
+
try {
|
|
28759
|
+
return LOCAL_HOST.test(new URL(url).hostname);
|
|
28760
|
+
} catch {
|
|
28761
|
+
return false;
|
|
28762
|
+
}
|
|
28763
|
+
}
|
|
28764
|
+
var hdr = (list, name) => list.find(([k]) => k.toLowerCase() === name)?.[1];
|
|
28765
|
+
var without = (list, test) => list.filter(([k]) => !test(k));
|
|
28766
|
+
var set = (list, name, value) => [...without(list, (k) => k.toLowerCase() === name.toLowerCase()), [name, value]];
|
|
28767
|
+
var probe = (id, title, request2) => ({ id, title, request: { ...request2, followRedirects: false, timeoutMs: request2.timeoutMs ?? 15e3 } });
|
|
28768
|
+
function activeProbes(given, opts = {}) {
|
|
28769
|
+
const base = { ...given, headers: given.headers.filter(([k]) => !ROUTING_HEADER.test(k)) };
|
|
28770
|
+
const url = new URL(base.url);
|
|
28771
|
+
const method = base.method.toUpperCase();
|
|
28772
|
+
const replay = SAFE.has(method) || !!opts.allowUnsafe;
|
|
28773
|
+
const probes = [];
|
|
28774
|
+
const skipped = [];
|
|
28775
|
+
const credHeaders = base.headers.filter(([k]) => CRED_HEADERS.test(k));
|
|
28776
|
+
const credParams = [...url.searchParams.keys()].filter((k) => CRED_PARAMS.test(k));
|
|
28777
|
+
if (!replay) skipped.push(`Checks that resend the ${method} request were left out: they could change data. Allow requests that change data to include them.`);
|
|
28778
|
+
if (replay) {
|
|
28779
|
+
if (credHeaders.length || credParams.length) {
|
|
28780
|
+
const bare = new URL(url);
|
|
28781
|
+
for (const k of credParams) bare.searchParams.delete(k);
|
|
28782
|
+
probes.push(probe("auth.removed", "Same request without credentials", { ...base, url: bare.toString(), headers: without(base.headers, (k) => CRED_HEADERS.test(k)) }));
|
|
28783
|
+
const auth = hdr(base.headers, "authorization");
|
|
28784
|
+
if (auth) {
|
|
28785
|
+
const bogus = /^basic\s/i.test(auth) ? `Basic ${btoa("wirecatch:not-the-password")}` : "Bearer wirecatch-invalid-token";
|
|
28786
|
+
const others = new URL(url);
|
|
28787
|
+
for (const k of credParams) others.searchParams.delete(k);
|
|
28788
|
+
probes.push(probe("auth.invalid", "Same request with a made-up token", { ...base, url: others.toString(), headers: [...without(base.headers, (k) => CRED_HEADERS.test(k)), ["Authorization", bogus]] }));
|
|
28789
|
+
}
|
|
28790
|
+
} else skipped.push("Credential checks were left out: the request carries no credentials.");
|
|
28791
|
+
probes.push(probe("cors.origin", "Request from another website's origin", { ...base, headers: set(base.headers, "Origin", PROBE_ORIGIN) }));
|
|
28792
|
+
probes.push(probe("cors.null", "Request from a sandboxed (null) origin", { ...base, headers: set(base.headers, "Origin", "null") }));
|
|
28793
|
+
probes.push(probe("host.forwarded", "Forwarded host header from elsewhere", { ...base, headers: set(base.headers, "X-Forwarded-Host", PROBE_HOST) }));
|
|
28794
|
+
} else {
|
|
28795
|
+
probes.push(probe("cors.origin", "Preflight from another website's origin", {
|
|
28796
|
+
method: "OPTIONS",
|
|
28797
|
+
url: base.url,
|
|
28798
|
+
headers: [["Origin", PROBE_ORIGIN], ["Access-Control-Request-Method", method], ["Access-Control-Request-Headers", "authorization,content-type"]]
|
|
28799
|
+
}));
|
|
28800
|
+
}
|
|
28801
|
+
probes.push(probe("method.trace", "TRACE request", { method: "TRACE", url: base.url, headers: [["X-Wirecatch-Probe", "trace"]] }));
|
|
28802
|
+
if (method === "GET") {
|
|
28803
|
+
const reflect = new URL(url);
|
|
28804
|
+
reflect.searchParams.set("wc_probe", CANARY);
|
|
28805
|
+
probes.push(probe("input.reflect", "Marked input in the query string", { ...base, url: reflect.toString() }));
|
|
28806
|
+
const quoted = new URL(url);
|
|
28807
|
+
const param = [...quoted.searchParams.keys()].find((k) => !CRED_PARAMS.test(k));
|
|
28808
|
+
if (param) quoted.searchParams.set(param, `${quoted.searchParams.get(param)}'`);
|
|
28809
|
+
else {
|
|
28810
|
+
const parts = quoted.pathname.split("/");
|
|
28811
|
+
const last = parts.length - 1;
|
|
28812
|
+
if (parts[last]) parts[last] = `${parts[last]}'`;
|
|
28813
|
+
quoted.pathname = parts.join("/");
|
|
28814
|
+
}
|
|
28815
|
+
if (quoted.toString() !== url.toString()) probes.push(probe("input.quote", "A single quote added to an input", { ...base, url: quoted.toString() }));
|
|
28816
|
+
} else skipped.push("Input checks were left out: they only run on GET requests.");
|
|
28817
|
+
return { probes, skipped };
|
|
28818
|
+
}
|
|
28819
|
+
var ok = (r) => !!r && r.status >= 200 && r.status < 300;
|
|
28820
|
+
var text = (r) => r && r.bodyEncoding === "utf8" ? r.body.slice(0, 256 * 1024) : "";
|
|
28821
|
+
var similar = (a, b) => {
|
|
28822
|
+
if (a.body === b.body) return true;
|
|
28823
|
+
const la = a.body.length, lb = b.body.length;
|
|
28824
|
+
return la > 0 && Math.abs(la - lb) / la < 0.1;
|
|
28825
|
+
};
|
|
28826
|
+
var JUDGES = {
|
|
28827
|
+
"auth.removed": (b, r) => ok(b) && ok(r) && similar(b, r) ? {
|
|
28828
|
+
id: "active.auth-not-required",
|
|
28829
|
+
severity: "high",
|
|
28830
|
+
title: "Answers without credentials",
|
|
28831
|
+
detail: "The same request with its credentials removed got the same successful answer. Anyone who knows the URL can read this. If the endpoint is meant to be public, ignore this.",
|
|
28832
|
+
fix: "Check authentication on every route on the server (a default-deny middleware), not only in the client."
|
|
28833
|
+
} : null,
|
|
28834
|
+
"auth.invalid": (b, r) => ok(b) && ok(r) && similar(b, r) ? {
|
|
28835
|
+
id: "active.auth-invalid-accepted",
|
|
28836
|
+
severity: "high",
|
|
28837
|
+
title: "Accepts a made-up token",
|
|
28838
|
+
detail: "A request with an invented token got the same successful answer as the real one, so the token is not being checked.",
|
|
28839
|
+
fix: "Verify the token's signature, expiry and audience on every request, and reject anything that does not verify."
|
|
28840
|
+
} : null,
|
|
28841
|
+
"cors.origin": (_b, r) => {
|
|
28842
|
+
const acao = hdr(r.headers, "access-control-allow-origin");
|
|
28843
|
+
if (acao !== PROBE_ORIGIN && acao !== "*") return null;
|
|
28844
|
+
const creds = hdr(r.headers, "access-control-allow-credentials")?.toLowerCase() === "true";
|
|
28845
|
+
if (acao === "*" && !creds) return null;
|
|
28846
|
+
return {
|
|
28847
|
+
id: "active.cors-any-origin",
|
|
28848
|
+
severity: creds ? "high" : "medium",
|
|
28849
|
+
title: "CORS trusts any website",
|
|
28850
|
+
detail: `A request from ${PROBE_ORIGIN}, a site you do not own, was allowed${creds ? " with credentials, so any website a signed-in user visits can read their data from this API" : ", so any website can read these answers"}.`,
|
|
28851
|
+
fix: "Compare the Origin against a fixed list of your own origins before allowing it.",
|
|
28852
|
+
evidence: "access-control-allow-origin"
|
|
28853
|
+
};
|
|
28854
|
+
},
|
|
28855
|
+
"cors.null": (_b, r) => hdr(r.headers, "access-control-allow-origin") === "null" ? {
|
|
28856
|
+
id: "active.cors-null-origin",
|
|
28857
|
+
severity: "medium",
|
|
28858
|
+
title: "CORS trusts the null origin",
|
|
28859
|
+
detail: "A request with Origin: null was allowed. Any page can send that origin from a sandboxed frame and read the answer.",
|
|
28860
|
+
fix: "Never allow the null origin.",
|
|
28861
|
+
evidence: "access-control-allow-origin"
|
|
28862
|
+
} : null,
|
|
28863
|
+
"host.forwarded": (_b, r) => text(r).includes(PROBE_HOST) || (hdr(r.headers, "location") ?? "").includes(PROBE_HOST) ? {
|
|
28864
|
+
id: "active.host-reflected",
|
|
28865
|
+
severity: "medium",
|
|
28866
|
+
title: "Forwarded host copied into the answer",
|
|
28867
|
+
detail: `X-Forwarded-Host: ${PROBE_HOST} came back in the answer's links. Attackers use this to poison caches and password-reset emails with their own domain.`,
|
|
28868
|
+
fix: "Build absolute links from a configured public URL, and only trust forwarded headers set by your own proxy.",
|
|
28869
|
+
evidence: "x-forwarded-host"
|
|
28870
|
+
} : null,
|
|
28871
|
+
"ip.spoof": (b, r) => !ok(b) && ok(r) ? {
|
|
28872
|
+
id: "active.ip-spoof-bypass",
|
|
28873
|
+
severity: "high",
|
|
28874
|
+
title: "Block bypassed with a forwarded-for header",
|
|
28875
|
+
detail: `The request was refused (${b.status}) until it claimed to come from 127.0.0.1 in X-Forwarded-For and similar headers, then it succeeded. Anyone can send those headers.`,
|
|
28876
|
+
fix: "Take the client address from your proxy configuration (trusted hop count), never from headers the client controls.",
|
|
28877
|
+
evidence: "x-forwarded-for"
|
|
28878
|
+
} : null,
|
|
28879
|
+
"method.trace": (_b, r) => r.status === 200 && /x-wirecatch-probe/i.test(text(r)) ? {
|
|
28880
|
+
id: "active.trace-enabled",
|
|
28881
|
+
severity: "low",
|
|
28882
|
+
title: "TRACE is enabled",
|
|
28883
|
+
detail: "The server echoes TRACE requests back, headers included. Combined with other flaws it can expose cookies and tokens.",
|
|
28884
|
+
fix: "Turn TRACE off on the server or proxy (for example TraceEnable off in Apache)."
|
|
28885
|
+
} : null,
|
|
28886
|
+
"input.reflect": (_b, r) => text(r).includes(CANARY_SEEN) && (hdr(r.headers, "content-type") ?? "").toLowerCase().includes("html") ? {
|
|
28887
|
+
id: "active.input-reflected",
|
|
28888
|
+
severity: "medium",
|
|
28889
|
+
title: "Input sent back without escaping",
|
|
28890
|
+
detail: "A marked value in the query string came back in an HTML answer with its tags intact. That is how reflected cross-site scripting starts.",
|
|
28891
|
+
fix: "Escape everything you put into HTML (use your template engine's auto-escaping), and add a Content-Security-Policy.",
|
|
28892
|
+
evidence: "wc_probe"
|
|
28893
|
+
} : null,
|
|
28894
|
+
"input.quote": (b, r) => DB_ERROR.test(text(r)) && !DB_ERROR.test(text(b)) ? {
|
|
28895
|
+
id: "active.sql-error",
|
|
28896
|
+
severity: "high",
|
|
28897
|
+
title: "A quote breaks a database query",
|
|
28898
|
+
detail: "Adding a single quote to an input produced a database error. The input is likely pasted into SQL, which allows SQL injection.",
|
|
28899
|
+
fix: "Use parameterised queries or your ORM's query builder for every value; never build SQL from strings."
|
|
28900
|
+
} : null
|
|
28901
|
+
};
|
|
28902
|
+
async function runActiveChecks(send2, given, opts = {}) {
|
|
28903
|
+
const report = { findings: [], probes: [], skipped: [], requests: 0 };
|
|
28904
|
+
const base = { ...given, headers: given.headers.filter(([k]) => !ROUTING_HEADER.test(k)) };
|
|
28905
|
+
const first = await send2({ ...base, followRedirects: false });
|
|
28906
|
+
report.requests++;
|
|
28907
|
+
if (!first.ok) return { ...report, error: `The request itself failed: ${first.error.error}` };
|
|
28908
|
+
const baseline = first.response;
|
|
28909
|
+
const { probes, skipped } = activeProbes(base, opts);
|
|
28910
|
+
if (base.headers.length !== given.headers.length) skipped.push("Headers that route a request (Host, Forwarded, X-Forwarded-*, Connection and similar) were left out of every check.");
|
|
28911
|
+
report.skipped = skipped;
|
|
28912
|
+
if ([401, 403].includes(baseline.status) && (SAFE.has(base.method.toUpperCase()) || opts.allowUnsafe)) {
|
|
28913
|
+
let h = base.headers;
|
|
28914
|
+
for (const name of ["X-Forwarded-For", "X-Real-IP", "X-Client-IP", "True-Client-IP", "X-Originating-IP"]) h = set(h, name, "127.0.0.1");
|
|
28915
|
+
probes.push(probe("ip.spoof", "Claiming to come from 127.0.0.1", { ...base, headers: h }));
|
|
28916
|
+
}
|
|
28917
|
+
for (const p of probes) {
|
|
28918
|
+
if (opts.signal?.aborted) break;
|
|
28919
|
+
const r = await send2(p.request);
|
|
28920
|
+
report.requests++;
|
|
28921
|
+
if (!r.ok) {
|
|
28922
|
+
report.probes.push({ id: p.id, title: p.title, method: p.request.method, error: r.error.error, flagged: false });
|
|
28923
|
+
continue;
|
|
28924
|
+
}
|
|
28925
|
+
const finding = JUDGES[p.id]?.(baseline, r.response, p.request) ?? null;
|
|
28926
|
+
if (finding && !report.findings.some((f) => f.id === finding.id)) report.findings.push(finding);
|
|
28927
|
+
report.probes.push({ id: p.id, title: p.title, method: p.request.method, status: r.response.status, flagged: !!finding });
|
|
28928
|
+
}
|
|
28929
|
+
const order = ["high", "medium", "low", "info"];
|
|
28930
|
+
report.findings.sort((a, b) => order.indexOf(a.severity) - order.indexOf(b.severity));
|
|
28931
|
+
return report;
|
|
28932
|
+
}
|
|
28933
|
+
|
|
28452
28934
|
// ../server/src/send.ts
|
|
28453
28935
|
var import_undici = __toESM(require_undici(), 1);
|
|
28454
28936
|
import zlib from "node:zlib";
|
|
@@ -28556,23 +29038,23 @@ function validate2(input) {
|
|
|
28556
29038
|
throw fail(400, "invalid_request", `Not a valid URL: ${r.url}`);
|
|
28557
29039
|
}
|
|
28558
29040
|
if (url.protocol !== "http:" && url.protocol !== "https:") throw fail(400, "invalid_request", "Only http and https URLs can be sent");
|
|
28559
|
-
const
|
|
28560
|
-
for (const h of
|
|
29041
|
+
const headers2 = Array.isArray(r.headers) ? r.headers : [];
|
|
29042
|
+
for (const h of headers2) {
|
|
28561
29043
|
if (!Array.isArray(h) || typeof h[0] !== "string" || typeof h[1] !== "string" || !TOKEN.test(h[0]) || /[\r\n]/.test(h[1]))
|
|
28562
29044
|
throw fail(400, "invalid_request", `Invalid header: ${JSON.stringify(h)}`);
|
|
28563
29045
|
}
|
|
28564
29046
|
if (r.body !== void 0 && typeof r.body !== "string") throw fail(400, "invalid_request", "Body must be a string");
|
|
28565
29047
|
if (r.cookieJar !== void 0) {
|
|
28566
|
-
const
|
|
28567
|
-
if (!
|
|
29048
|
+
const ok2 = Array.isArray(r.cookieJar) && r.cookieJar.length <= 300 && r.cookieJar.every((c) => c && typeof c === "object" && typeof c.name === "string" && typeof c.value === "string" && typeof c.domain === "string" && typeof c.path === "string" && c.name.length + c.value.length < 4096 && c.domain.length < 256 && c.path.length < 1024 && !/[\r\n;]/.test(c.name + c.value));
|
|
29049
|
+
if (!ok2) throw fail(400, "invalid_request", "cookieJar must be a list of at most 300 cookies");
|
|
28568
29050
|
}
|
|
28569
|
-
return { ...r, method: r.method.toUpperCase(), url: url.toString(), headers };
|
|
29051
|
+
return { ...r, method: r.method.toUpperCase(), url: url.toString(), headers: headers2 };
|
|
28570
29052
|
}
|
|
28571
29053
|
async function decode(buf, encoding, cap) {
|
|
28572
29054
|
const kind = (encoding ?? "").trim().toLowerCase();
|
|
28573
29055
|
const make = (raw = false) => kind === "gzip" || kind === "x-gzip" ? zlib.createGunzip() : kind === "br" ? zlib.createBrotliDecompress() : raw ? zlib.createInflateRaw() : zlib.createInflate();
|
|
28574
29056
|
if (!["gzip", "x-gzip", "deflate", "br"].includes(kind)) return { bytes: buf, truncated: false };
|
|
28575
|
-
const run2 = (stream) => new Promise((
|
|
29057
|
+
const run2 = (stream) => new Promise((resolve4, reject) => {
|
|
28576
29058
|
const chunks = [];
|
|
28577
29059
|
let size = 0;
|
|
28578
29060
|
let done = false;
|
|
@@ -28584,7 +29066,7 @@ async function decode(buf, encoding, cap) {
|
|
|
28584
29066
|
size = cap;
|
|
28585
29067
|
done = true;
|
|
28586
29068
|
stream.destroy();
|
|
28587
|
-
|
|
29069
|
+
resolve4({ bytes: Buffer.concat(chunks), truncated: true });
|
|
28588
29070
|
return;
|
|
28589
29071
|
}
|
|
28590
29072
|
chunks.push(c);
|
|
@@ -28593,7 +29075,7 @@ async function decode(buf, encoding, cap) {
|
|
|
28593
29075
|
stream.on("end", () => {
|
|
28594
29076
|
if (!done) {
|
|
28595
29077
|
done = true;
|
|
28596
|
-
|
|
29078
|
+
resolve4({ bytes: Buffer.concat(chunks), truncated: false });
|
|
28597
29079
|
}
|
|
28598
29080
|
});
|
|
28599
29081
|
stream.on("error", (e) => {
|
|
@@ -28622,12 +29104,12 @@ async function send(input, opts) {
|
|
|
28622
29104
|
const started = performance.now();
|
|
28623
29105
|
let url = new URL(req.url);
|
|
28624
29106
|
let method = req.method;
|
|
28625
|
-
let
|
|
29107
|
+
let headers2 = req.headers;
|
|
28626
29108
|
let body = req.body === void 0 ? void 0 : Buffer.from(req.body, req.bodyEncoding === "base64" ? "base64" : "utf8");
|
|
28627
29109
|
let redirects = 0;
|
|
28628
29110
|
const hopJar = new CookieJar((req.cookieJar ?? []).map((c) => ({ ...c, hostOnly: !!c.hostOnly, secure: !!c.secure, httpOnly: !!c.httpOnly, created: Number(c.created) || 0, ...typeof c.expires === "number" ? { expires: c.expires } : {} })));
|
|
28629
29111
|
const fromJar = new Map(hopJar.matching(url.toString()).map((c) => [c.name, c.value]));
|
|
28630
|
-
let userCookies =
|
|
29112
|
+
let userCookies = headers2.filter(([k]) => k.toLowerCase() === "cookie").flatMap(([, v]) => v.split(";")).map((s) => s.trim()).filter(Boolean).filter((p) => {
|
|
28631
29113
|
const i = p.indexOf("=");
|
|
28632
29114
|
return fromJar.get(p.slice(0, i).trim()) !== p.slice(i + 1).trim();
|
|
28633
29115
|
});
|
|
@@ -28637,9 +29119,9 @@ async function send(input, opts) {
|
|
|
28637
29119
|
if (!opts.allowPrivate) await assertPublicUrl(url);
|
|
28638
29120
|
const res = await (0, import_undici.request)(url, {
|
|
28639
29121
|
method,
|
|
28640
|
-
headers:
|
|
29122
|
+
headers: headers2.flat(),
|
|
28641
29123
|
body: method === "GET" || method === "HEAD" ? void 0 : body,
|
|
28642
|
-
dispatcher: !opts.allowPrivate ? guardedAgent : opts.insecure ? insecureAgent : openAgent,
|
|
29124
|
+
dispatcher: opts.dispatcher ?? (!opts.allowPrivate ? guardedAgent : opts.insecure ? insecureAgent : openAgent),
|
|
28643
29125
|
signal,
|
|
28644
29126
|
maxRedirections: 0
|
|
28645
29127
|
});
|
|
@@ -28649,8 +29131,8 @@ async function send(input, opts) {
|
|
|
28649
29131
|
if (++redirects > MAX_REDIRECTS) throw fail(502, "too_many_redirects", `Stopped after ${MAX_REDIRECTS} redirects`);
|
|
28650
29132
|
const next = new URL(location2, url);
|
|
28651
29133
|
if (next.protocol !== "http:" && next.protocol !== "https:") throw fail(502, "network", `Redirect to unsupported URL ${next}`);
|
|
28652
|
-
const
|
|
28653
|
-
const setList =
|
|
29134
|
+
const set2 = res.headers["set-cookie"];
|
|
29135
|
+
const setList = set2 === void 0 ? [] : Array.isArray(set2) ? set2 : [String(set2)];
|
|
28654
29136
|
if (setList.length) {
|
|
28655
29137
|
hopJar.store(url.toString(), setList);
|
|
28656
29138
|
for (const value of setList) hopCookies.push({ url: url.toString(), value });
|
|
@@ -28658,17 +29140,17 @@ async function send(input, opts) {
|
|
|
28658
29140
|
userCookies = userCookies.filter((p) => !setNames.has(p.split("=")[0].trim()));
|
|
28659
29141
|
}
|
|
28660
29142
|
if (next.origin !== url.origin) {
|
|
28661
|
-
|
|
29143
|
+
headers2 = headers2.filter(([k]) => !["authorization", "proxy-authorization"].includes(k.toLowerCase()));
|
|
28662
29144
|
userCookies = [];
|
|
28663
29145
|
}
|
|
28664
29146
|
const jarCookies = hopJar.matching(next.toString());
|
|
28665
29147
|
const names = new Set(userCookies.map((p) => p.split("=")[0].trim()));
|
|
28666
29148
|
const cookie = [...userCookies, ...jarCookies.filter((c) => !names.has(c.name)).map((c) => `${c.name}=${c.value}`)].join("; ");
|
|
28667
|
-
|
|
29149
|
+
headers2 = [...headers2.filter(([k]) => k.toLowerCase() !== "cookie"), ...cookie ? [["Cookie", cookie]] : []];
|
|
28668
29150
|
if (res.statusCode === 303 || (res.statusCode === 301 || res.statusCode === 302) && method === "POST") {
|
|
28669
29151
|
method = "GET";
|
|
28670
29152
|
body = void 0;
|
|
28671
|
-
|
|
29153
|
+
headers2 = headers2.filter(([k]) => !["content-type", "content-length"].includes(k.toLowerCase()));
|
|
28672
29154
|
}
|
|
28673
29155
|
url = next;
|
|
28674
29156
|
continue;
|
|
@@ -28811,7 +29293,7 @@ var Sandbox = class {
|
|
|
28811
29293
|
async run(source, ctx, phase) {
|
|
28812
29294
|
const w = await this.start();
|
|
28813
29295
|
const runId = ++this.runs;
|
|
28814
|
-
return new Promise((
|
|
29296
|
+
return new Promise((resolve4) => {
|
|
28815
29297
|
let waiting = 0;
|
|
28816
29298
|
let idle;
|
|
28817
29299
|
const cleanup = () => {
|
|
@@ -28823,13 +29305,13 @@ var Sandbox = class {
|
|
|
28823
29305
|
};
|
|
28824
29306
|
const finish = (r) => {
|
|
28825
29307
|
cleanup();
|
|
28826
|
-
|
|
29308
|
+
resolve4(r);
|
|
28827
29309
|
};
|
|
28828
29310
|
const kill = (why) => {
|
|
28829
29311
|
cleanup();
|
|
28830
29312
|
this.worker = void 0;
|
|
28831
29313
|
void w.terminate();
|
|
28832
|
-
|
|
29314
|
+
resolve4({ ...empty(), error: why });
|
|
28833
29315
|
};
|
|
28834
29316
|
const arm = () => {
|
|
28835
29317
|
clearTimeout(idle);
|
|
@@ -28867,12 +29349,12 @@ var Sandbox = class {
|
|
|
28867
29349
|
const onError = (e) => {
|
|
28868
29350
|
cleanup();
|
|
28869
29351
|
this.worker = void 0;
|
|
28870
|
-
|
|
29352
|
+
resolve4({ ...empty(), error: `The script sandbox failed: ${e.message}` });
|
|
28871
29353
|
};
|
|
28872
29354
|
const onExit = () => {
|
|
28873
29355
|
cleanup();
|
|
28874
29356
|
this.worker = void 0;
|
|
28875
|
-
|
|
29357
|
+
resolve4({ ...empty(), error: "The script sandbox stopped." });
|
|
28876
29358
|
};
|
|
28877
29359
|
w.on("message", onMessage);
|
|
28878
29360
|
w.on("error", onError);
|
|
@@ -28998,9 +29480,181 @@ async function attachFiles(collection, opts) {
|
|
|
28998
29480
|
return (id) => store.get(id);
|
|
28999
29481
|
}
|
|
29000
29482
|
|
|
29483
|
+
// src/scan.ts
|
|
29484
|
+
import { writeFile, mkdir } from "node:fs/promises";
|
|
29485
|
+
import { dirname, resolve as resolve2 } from "node:path";
|
|
29486
|
+
import { parseArgs } from "node:util";
|
|
29487
|
+
var SCAN_USAGE = `Usage: wirecatch scan <url> [options]
|
|
29488
|
+
|
|
29489
|
+
Active security checks on one request (Team plan): about ten altered copies of it (no credentials, a made-up
|
|
29490
|
+
token, another website's origin, forwarded headers, TRACE, marked input) to find weaknesses. Needs an
|
|
29491
|
+
organization key. Sites your organization has verified are checked by the Wirecatch server; localhost is
|
|
29492
|
+
checked from this machine. Exits 0 when nothing at --fail-on or above was found, 1 when something was,
|
|
29493
|
+
2 when the scan could not run.
|
|
29494
|
+
|
|
29495
|
+
Options:
|
|
29496
|
+
-X, --method <method> Request method (default GET)
|
|
29497
|
+
-H, --header <name: value> Request header (repeatable)
|
|
29498
|
+
-d, --data <body> Request body
|
|
29499
|
+
--allow-unsafe Also resend requests that change data (POST, PUT, PATCH, DELETE)
|
|
29500
|
+
--org-key <key> Organization key (default: $WIRECATCH_ORG_KEY)
|
|
29501
|
+
--server <url> Wirecatch server (default: $WIRECATCH_SERVER or https://app.wirecatch.com)
|
|
29502
|
+
--fail-on <level> high, medium (default), low, info, or none
|
|
29503
|
+
-r, --reporters <list> cli, json, junit (default cli)
|
|
29504
|
+
--reporter-json-export <file> (default wirecatch-scan.json)
|
|
29505
|
+
--reporter-junit-export <file> (default wirecatch-scan.xml)
|
|
29506
|
+
-k, --insecure Accept any TLS certificate (localhost only)
|
|
29507
|
+
-h, --help Show this help`;
|
|
29508
|
+
var ScanError = class extends Error {
|
|
29509
|
+
};
|
|
29510
|
+
var color = !process.env.NO_COLOR && process.stdout.isTTY;
|
|
29511
|
+
var paint = (code) => (s) => color ? `\x1B[${code}m${s}\x1B[0m` : s;
|
|
29512
|
+
var red = paint("31");
|
|
29513
|
+
var green = paint("32");
|
|
29514
|
+
var dim = paint("2");
|
|
29515
|
+
var bold = paint("1");
|
|
29516
|
+
var xml2 = (s) => s.replace(/[\u0000-\u0008\u000B\u000C\u000E-\u001F]/g, "").replace(/[<>&"']/g, (c) => ({ "<": "<", ">": ">", "&": "&", '"': """, "'": "'" })[c]);
|
|
29517
|
+
async function api(server, path, key, body) {
|
|
29518
|
+
let res;
|
|
29519
|
+
try {
|
|
29520
|
+
res = await fetch(`${server}${path}`, { method: body ? "POST" : "GET", headers: { authorization: `Bearer ${key}`, ...body ? { "content-type": "application/json" } : {} }, body: body ? JSON.stringify(body) : void 0 });
|
|
29521
|
+
} catch (e) {
|
|
29522
|
+
throw new ScanError(`Could not reach ${server}: ${e.message}`);
|
|
29523
|
+
}
|
|
29524
|
+
const data = await res.json().catch(() => null);
|
|
29525
|
+
if (!res.ok) throw new ScanError(data?.error ?? `${server} answered ${res.status}`);
|
|
29526
|
+
return data;
|
|
29527
|
+
}
|
|
29528
|
+
function junit(url, report, failOn) {
|
|
29529
|
+
const failing = (sev) => failOn !== "none" && atLeast(sev, failOn);
|
|
29530
|
+
const cases = report.probes.map((p) => {
|
|
29531
|
+
const f = report.findings.find((x) => p.flagged && JUDGED[p.id] === x.id);
|
|
29532
|
+
return f && failing(f.severity) ? ` <testcase name="${xml2(p.title)}" classname="security"><failure message="${xml2(`${f.severity}: ${f.title}`)}" type="SecurityFinding">${xml2(`${f.detail}
|
|
29533
|
+
Fix: ${f.fix}`)}</failure></testcase>` : ` <testcase name="${xml2(p.title)}" classname="security"/>`;
|
|
29534
|
+
});
|
|
29535
|
+
const failures = report.findings.filter((f) => failing(f.severity)).length;
|
|
29536
|
+
return `<?xml version="1.0" encoding="UTF-8"?>
|
|
29537
|
+
<testsuites name="Wirecatch security scan" tests="${cases.length}" failures="${failures}">
|
|
29538
|
+
<testsuite name="${xml2(url)}" tests="${cases.length}" failures="${failures}">
|
|
29539
|
+
${cases.join("\n")}
|
|
29540
|
+
</testsuite>
|
|
29541
|
+
</testsuites>
|
|
29542
|
+
`;
|
|
29543
|
+
}
|
|
29544
|
+
var JUDGED = {
|
|
29545
|
+
"auth.removed": "active.auth-not-required",
|
|
29546
|
+
"auth.invalid": "active.auth-invalid-accepted",
|
|
29547
|
+
"cors.origin": "active.cors-any-origin",
|
|
29548
|
+
"cors.null": "active.cors-null-origin",
|
|
29549
|
+
"host.forwarded": "active.host-reflected",
|
|
29550
|
+
"ip.spoof": "active.ip-spoof-bypass",
|
|
29551
|
+
"method.trace": "active.trace-enabled",
|
|
29552
|
+
"input.reflect": "active.input-reflected",
|
|
29553
|
+
"input.quote": "active.sql-error"
|
|
29554
|
+
};
|
|
29555
|
+
async function scanCommand(argv2) {
|
|
29556
|
+
try {
|
|
29557
|
+
return await scan(argv2);
|
|
29558
|
+
} catch (e) {
|
|
29559
|
+
if (e instanceof ScanError || e.code?.startsWith("ERR_PARSE_ARGS")) {
|
|
29560
|
+
process.stderr.write(`wirecatch scan: ${e.message}
|
|
29561
|
+
${e instanceof ScanError ? "" : `
|
|
29562
|
+
${SCAN_USAGE}
|
|
29563
|
+
`}`);
|
|
29564
|
+
return 2;
|
|
29565
|
+
}
|
|
29566
|
+
throw e;
|
|
29567
|
+
}
|
|
29568
|
+
}
|
|
29569
|
+
async function scan(argv2) {
|
|
29570
|
+
const { values: o, positionals } = parseArgs({
|
|
29571
|
+
args: argv2,
|
|
29572
|
+
allowPositionals: true,
|
|
29573
|
+
options: {
|
|
29574
|
+
method: { type: "string", short: "X" },
|
|
29575
|
+
header: { type: "string", short: "H", multiple: true },
|
|
29576
|
+
data: { type: "string", short: "d" },
|
|
29577
|
+
"allow-unsafe": { type: "boolean" },
|
|
29578
|
+
"org-key": { type: "string" },
|
|
29579
|
+
server: { type: "string" },
|
|
29580
|
+
"fail-on": { type: "string" },
|
|
29581
|
+
reporters: { type: "string", short: "r" },
|
|
29582
|
+
"reporter-json-export": { type: "string" },
|
|
29583
|
+
"reporter-junit-export": { type: "string" },
|
|
29584
|
+
insecure: { type: "boolean", short: "k" },
|
|
29585
|
+
help: { type: "boolean", short: "h" }
|
|
29586
|
+
}
|
|
29587
|
+
});
|
|
29588
|
+
if (o.help) {
|
|
29589
|
+
process.stdout.write(`${SCAN_USAGE}
|
|
29590
|
+
`);
|
|
29591
|
+
return 0;
|
|
29592
|
+
}
|
|
29593
|
+
const [url, ...extra] = positionals;
|
|
29594
|
+
if (!url || extra.length) throw new ScanError(`Which URL should be checked?
|
|
29595
|
+
|
|
29596
|
+
${SCAN_USAGE}`);
|
|
29597
|
+
try {
|
|
29598
|
+
new URL(url);
|
|
29599
|
+
} catch {
|
|
29600
|
+
throw new ScanError(`Not a URL: ${url}`);
|
|
29601
|
+
}
|
|
29602
|
+
const failOn = o["fail-on"] ?? "medium";
|
|
29603
|
+
if (failOn !== "none" && !SECURITY_SEVERITIES.includes(failOn)) throw new ScanError(`--fail-on must be one of ${SECURITY_SEVERITIES.join(", ")} or none`);
|
|
29604
|
+
const reporters = new Set((o.reporters ?? "cli").split(",").map((r) => r.trim()).filter(Boolean));
|
|
29605
|
+
for (const r of reporters) if (!["cli", "json", "junit"].includes(r)) throw new ScanError(`Unknown reporter "${r}". Use cli, json or junit.`);
|
|
29606
|
+
const key = o["org-key"] || process.env.WIRECATCH_ORG_KEY;
|
|
29607
|
+
if (!key) throw new ScanError("Active checks need an organization key: pass --org-key or set WIRECATCH_ORG_KEY (Organization in the Wirecatch app).");
|
|
29608
|
+
const server = (o.server ?? process.env.WIRECATCH_SERVER ?? "https://app.wirecatch.com").replace(/\/+$/, "");
|
|
29609
|
+
const headers2 = (o.header ?? []).map((h) => {
|
|
29610
|
+
const i = h.indexOf(":");
|
|
29611
|
+
if (i < 1) throw new ScanError(`--header needs "Name: value", got "${h}"`);
|
|
29612
|
+
return [h.slice(0, i).trim(), h.slice(i + 1).trim()];
|
|
29613
|
+
});
|
|
29614
|
+
const request2 = { method: (o.method ?? (o.data ? "POST" : "GET")).toUpperCase(), url, headers: headers2, ...o.data !== void 0 ? { body: o.data } : {} };
|
|
29615
|
+
let report;
|
|
29616
|
+
if (isLocalTarget(url)) {
|
|
29617
|
+
const me = await api(server, "/api/orgs/me", key);
|
|
29618
|
+
if (me.plan !== "team") throw new ScanError("Active security checks are part of the Team plan. Ask Wired Technologies to upgrade this organization.");
|
|
29619
|
+
report = await runActiveChecks(async (r) => {
|
|
29620
|
+
try {
|
|
29621
|
+
return { ok: true, response: await send({ ...r, timeoutMs: r.timeoutMs ?? 15e3 }, { allowPrivate: true, insecure: !!o.insecure, maxTimeoutMs: 3e4, maxBodyBytes: 1024 * 1024 }) };
|
|
29622
|
+
} catch (e) {
|
|
29623
|
+
return { ok: false, error: e instanceof SendFailure ? e.detail : { code: "network", error: e.message } };
|
|
29624
|
+
}
|
|
29625
|
+
}, request2, { allowUnsafe: !!o["allow-unsafe"] });
|
|
29626
|
+
} else {
|
|
29627
|
+
report = await api(server, "/api/security/scan", key, { request: request2, allowUnsafe: !!o["allow-unsafe"] });
|
|
29628
|
+
}
|
|
29629
|
+
if (reporters.has("cli")) {
|
|
29630
|
+
const out = [`${bold("Security scan")} ${request2.method} ${url}`, ""];
|
|
29631
|
+
if (report.error) out.push(red(report.error));
|
|
29632
|
+
for (const f of report.findings) {
|
|
29633
|
+
out.push(`${f.severity === "high" || f.severity === "medium" ? red(f.severity.toUpperCase()) : dim(f.severity.toUpperCase())} ${f.title}${f.evidence ? dim(` (${f.evidence})`) : ""}`);
|
|
29634
|
+
out.push(` ${dim(f.detail)}`, ` Fix: ${f.fix}`, "");
|
|
29635
|
+
}
|
|
29636
|
+
for (const p of report.probes) out.push(` ${p.flagged ? red("\u2717") : green("\u2713")} ${p.title} ${dim(`${p.method} \u2192 ${p.error ?? p.status}`)}`);
|
|
29637
|
+
for (const s of report.skipped) out.push(dim(` ${s}`));
|
|
29638
|
+
out.push("", `${report.requests} requests sent \xB7 ${report.findings.length === 0 ? green("no weaknesses found") : red(`${report.findings.length} finding${report.findings.length === 1 ? "" : "s"}`)}`);
|
|
29639
|
+
process.stdout.write(`${out.join("\n")}
|
|
29640
|
+
`);
|
|
29641
|
+
}
|
|
29642
|
+
const write = async (path, content) => {
|
|
29643
|
+
const p = resolve2(path);
|
|
29644
|
+
await mkdir(dirname(p), { recursive: true });
|
|
29645
|
+
await writeFile(p, content);
|
|
29646
|
+
};
|
|
29647
|
+
if (reporters.has("json")) await write(o["reporter-json-export"] ?? "wirecatch-scan.json", `${JSON.stringify({ url, method: request2.method, at: (/* @__PURE__ */ new Date()).toISOString(), ...report }, null, 2)}
|
|
29648
|
+
`);
|
|
29649
|
+
if (reporters.has("junit")) await write(o["reporter-junit-export"] ?? "wirecatch-scan.xml", junit(url, report, failOn));
|
|
29650
|
+
if (report.error) return 2;
|
|
29651
|
+
return failOn !== "none" && report.findings.some((f) => atLeast(f.severity, failOn)) ? 1 : 0;
|
|
29652
|
+
}
|
|
29653
|
+
|
|
29001
29654
|
// src/main.ts
|
|
29002
|
-
var VERSION = true ? "0.
|
|
29655
|
+
var VERSION = true ? "0.2.0" : "0.1.0-dev";
|
|
29003
29656
|
var USAGE = `Usage: wirecatch run <collection.json> [options]
|
|
29657
|
+
wirecatch scan <url> [options] Active security checks (Team plan); see wirecatch scan --help
|
|
29004
29658
|
|
|
29005
29659
|
Runs every request in a collection file (v2.0 or v2.1 format, as Wirecatch exports), with its scripts and tests.
|
|
29006
29660
|
Exits 0 when everything passed, 1 when a request or test failed, 2 when the input could not be used.
|
|
@@ -29017,6 +29671,11 @@ Options:
|
|
|
29017
29671
|
--timeout-request <ms> Give up on a request after this long (default 30000)
|
|
29018
29672
|
--script-timeout <ms> Stop a script that runs this long on its own (default 5000)
|
|
29019
29673
|
--bail Stop at the first failed request or test
|
|
29674
|
+
--fail-on-security <level> Fail the run when a security finding is at least this severe:
|
|
29675
|
+
high, medium, low or info (findings are shown either way)
|
|
29676
|
+
-p, --parallel <n> Run up to n iterations at once (1-50). Requests inside an iteration
|
|
29677
|
+
stay in order; each iteration keeps the variables its scripts set to
|
|
29678
|
+
itself, so --export-environment writes the starting values
|
|
29020
29679
|
--working-dir <dir> Where file uploads named in the collection are read from (default: here)
|
|
29021
29680
|
--insecure-file-read Allow uploads from outside the working directory
|
|
29022
29681
|
-k, --insecure Accept any TLS certificate
|
|
@@ -29030,21 +29689,21 @@ Options:
|
|
|
29030
29689
|
-v, --version Show the version`;
|
|
29031
29690
|
var UsageError = class extends Error {
|
|
29032
29691
|
};
|
|
29033
|
-
var
|
|
29034
|
-
var
|
|
29035
|
-
var
|
|
29036
|
-
var
|
|
29037
|
-
var
|
|
29038
|
-
var
|
|
29692
|
+
var color2 = !process.env.NO_COLOR && process.stdout.isTTY;
|
|
29693
|
+
var paint2 = (code) => (s) => color2 ? `\x1B[${code}m${s}\x1B[0m` : s;
|
|
29694
|
+
var green2 = paint2("32");
|
|
29695
|
+
var red2 = paint2("31");
|
|
29696
|
+
var dim2 = paint2("2");
|
|
29697
|
+
var bold2 = paint2("1");
|
|
29039
29698
|
async function readJson(path, what) {
|
|
29040
|
-
let
|
|
29699
|
+
let text2;
|
|
29041
29700
|
try {
|
|
29042
|
-
|
|
29701
|
+
text2 = await readFile2(path, "utf8");
|
|
29043
29702
|
} catch {
|
|
29044
29703
|
throw new UsageError(`Could not read the ${what} file: ${path}`);
|
|
29045
29704
|
}
|
|
29046
29705
|
try {
|
|
29047
|
-
return JSON.parse(
|
|
29706
|
+
return JSON.parse(text2);
|
|
29048
29707
|
} catch {
|
|
29049
29708
|
throw new UsageError(`The ${what} file is not valid JSON: ${path}`);
|
|
29050
29709
|
}
|
|
@@ -29077,19 +29736,20 @@ function withOverrides(rows2, overrides) {
|
|
|
29077
29736
|
return applyVariableUpdates(rows2, overrides);
|
|
29078
29737
|
}
|
|
29079
29738
|
async function writeOut(path, content) {
|
|
29080
|
-
await
|
|
29081
|
-
await
|
|
29739
|
+
await mkdir2(dirname2(resolve3(path)), { recursive: true });
|
|
29740
|
+
await writeFile2(path, content);
|
|
29082
29741
|
}
|
|
29083
29742
|
function printStep(step, verbose) {
|
|
29084
29743
|
const name = [...step.path, step.name].join(" / ");
|
|
29085
|
-
const out = [`${
|
|
29086
|
-
const line = step.error ? ` ${step.method} ${step.url} ${
|
|
29744
|
+
const out = [`${bold2("\u2192")} ${name}`];
|
|
29745
|
+
const line = step.error ? ` ${step.method} ${step.url} ${red2(`failed: ${step.error}`)}` : ` ${step.method} ${step.url} ${(step.status ?? 0) >= 400 ? red2(String(step.status)) : green2(String(step.status))} ${dim2(formatDuration(step.timeMs ?? 0))}`;
|
|
29087
29746
|
out.push(line);
|
|
29088
29747
|
for (const t of step.tests) {
|
|
29089
|
-
out.push(t.passed ? ` ${
|
|
29090
|
-
if (!t.passed && t.error) out.push(` ${
|
|
29748
|
+
out.push(t.passed ? ` ${green2("\u2713")} ${t.name}` : ` ${red2("\u2717")} ${t.name}`);
|
|
29749
|
+
if (!t.passed && t.error) out.push(` ${red2(t.error)}`);
|
|
29091
29750
|
}
|
|
29092
|
-
|
|
29751
|
+
for (const f of step.security ?? []) out.push(` ${f.severity === "high" || f.severity === "medium" ? red2("!") : dim2("\xB7")} ${dim2(`security ${f.severity}:`)} ${f.title}${f.evidence ? dim2(` (${f.evidence})`) : ""}`);
|
|
29752
|
+
if (verbose) for (const l of step.logs ?? []) out.push(` ${dim2(`\u2502 ${l}`)}`);
|
|
29093
29753
|
process.stdout.write(`${out.join("\n")}
|
|
29094
29754
|
|
|
29095
29755
|
`);
|
|
@@ -29098,18 +29758,18 @@ function printSummary(report) {
|
|
|
29098
29758
|
const s = report.summary;
|
|
29099
29759
|
const parts = [
|
|
29100
29760
|
`${s.requests} request${s.requests === 1 ? "" : "s"}`,
|
|
29101
|
-
|
|
29102
|
-
s.failed ?
|
|
29103
|
-
...s.failedRequests ? [
|
|
29104
|
-
|
|
29761
|
+
green2(`${s.passed} passed`),
|
|
29762
|
+
s.failed ? red2(`${s.failed} failed`) : `${s.failed} failed`,
|
|
29763
|
+
...s.failedRequests ? [red2(`${s.failedRequests} with problems`)] : [],
|
|
29764
|
+
dim2(`avg ${formatDuration(s.avgMs)}`)
|
|
29105
29765
|
];
|
|
29106
29766
|
process.stdout.write(`${parts.join(" \xB7 ")}
|
|
29107
29767
|
`);
|
|
29108
|
-
if (report.bailed) process.stdout.write(
|
|
29768
|
+
if (report.bailed) process.stdout.write(red2("Stopped at the first failure (--bail).\n"));
|
|
29109
29769
|
}
|
|
29110
|
-
async function run(
|
|
29111
|
-
const { values: o, positionals } =
|
|
29112
|
-
args:
|
|
29770
|
+
async function run(argv2) {
|
|
29771
|
+
const { values: o, positionals } = parseArgs2({
|
|
29772
|
+
args: argv2,
|
|
29113
29773
|
allowPositionals: true,
|
|
29114
29774
|
options: {
|
|
29115
29775
|
environment: { type: "string", short: "e" },
|
|
@@ -29123,6 +29783,8 @@ async function run(argv) {
|
|
|
29123
29783
|
"timeout-request": { type: "string" },
|
|
29124
29784
|
"script-timeout": { type: "string" },
|
|
29125
29785
|
bail: { type: "boolean" },
|
|
29786
|
+
parallel: { type: "string", short: "p" },
|
|
29787
|
+
"fail-on-security": { type: "string" },
|
|
29126
29788
|
"working-dir": { type: "string" },
|
|
29127
29789
|
"insecure-file-read": { type: "boolean" },
|
|
29128
29790
|
insecure: { type: "boolean", short: "k" },
|
|
@@ -29176,14 +29838,14 @@ async function run(argv) {
|
|
|
29176
29838
|
globals = withOverrides(globals, pairs(o["global-var"], "--global-var"));
|
|
29177
29839
|
let data;
|
|
29178
29840
|
if (o["iteration-data"]) {
|
|
29179
|
-
let
|
|
29841
|
+
let text2;
|
|
29180
29842
|
try {
|
|
29181
|
-
|
|
29843
|
+
text2 = await readFile2(o["iteration-data"], "utf8");
|
|
29182
29844
|
} catch {
|
|
29183
29845
|
throw new UsageError(`Could not read the data file: ${o["iteration-data"]}`);
|
|
29184
29846
|
}
|
|
29185
29847
|
try {
|
|
29186
|
-
data = parseDataFile(
|
|
29848
|
+
data = parseDataFile(text2, o["iteration-data"]);
|
|
29187
29849
|
} catch (e) {
|
|
29188
29850
|
throw new UsageError(`${o["iteration-data"]}: ${e.message}`);
|
|
29189
29851
|
}
|
|
@@ -29197,11 +29859,15 @@ async function run(argv) {
|
|
|
29197
29859
|
const delayMs = intOption(o["delay-request"], "--delay-request", 0);
|
|
29198
29860
|
const timeoutMs = intOption(o["timeout-request"], "--timeout-request", 3e4, 1);
|
|
29199
29861
|
const scriptMs = intOption(o["script-timeout"], "--script-timeout", 5e3, 50);
|
|
29862
|
+
const parallel = intOption(o.parallel, "--parallel", 1, 1);
|
|
29863
|
+
const securityFailOn = o["fail-on-security"];
|
|
29864
|
+
if (securityFailOn !== void 0 && !SECURITY_SEVERITIES.includes(securityFailOn)) throw new UsageError(`--fail-on-security must be one of ${SECURITY_SEVERITIES.join(", ")}`);
|
|
29865
|
+
if (parallel > MAX_PARALLEL) throw new UsageError(`--parallel can be at most ${MAX_PARALLEL}.`);
|
|
29200
29866
|
const state = { collection, environment, globals };
|
|
29201
29867
|
const files = await attachFiles(collection, { workingDir: o["working-dir"] ?? process.cwd(), insecureFileRead: !!o["insecure-file-read"] });
|
|
29202
29868
|
const { host, close } = createHost(state, { timeoutMs, scriptMs, insecure: !!o.insecure, files });
|
|
29203
29869
|
const cli = reporters.has("cli");
|
|
29204
|
-
if (cli) process.stdout.write(`${
|
|
29870
|
+
if (cli) process.stdout.write(`${bold2(collection.name)}${o.folder ? dim2(` / ${o.folder}`) : ""}
|
|
29205
29871
|
|
|
29206
29872
|
`);
|
|
29207
29873
|
let report;
|
|
@@ -29213,13 +29879,22 @@ async function run(argv) {
|
|
|
29213
29879
|
data,
|
|
29214
29880
|
delayMs,
|
|
29215
29881
|
bail: !!o.bail,
|
|
29882
|
+
parallel,
|
|
29883
|
+
// In parallel, iterations finish in any order: print each one whole when it is done.
|
|
29216
29884
|
onIteration: (it, total) => {
|
|
29217
|
-
if (cli && total > 1) process.stdout.write(`${
|
|
29885
|
+
if (cli && total > 1 && parallel === 1) process.stdout.write(`${bold2(`Iteration ${it + 1}/${total}`)}
|
|
29218
29886
|
|
|
29219
29887
|
`);
|
|
29220
29888
|
},
|
|
29221
29889
|
onStep: (step) => {
|
|
29222
|
-
if (cli) printStep(step, !!o.verbose);
|
|
29890
|
+
if (cli && parallel === 1) printStep(step, !!o.verbose);
|
|
29891
|
+
},
|
|
29892
|
+
onIterationDone: (it, total, steps) => {
|
|
29893
|
+
if (!cli || parallel === 1) return;
|
|
29894
|
+
if (total > 1) process.stdout.write(`${bold2(`Iteration ${it + 1}/${total}`)}
|
|
29895
|
+
|
|
29896
|
+
`);
|
|
29897
|
+
for (const step of steps) printStep(step, !!o.verbose);
|
|
29223
29898
|
}
|
|
29224
29899
|
});
|
|
29225
29900
|
} finally {
|
|
@@ -29228,14 +29903,18 @@ async function run(argv) {
|
|
|
29228
29903
|
if (cli) printSummary(report);
|
|
29229
29904
|
if (reporters.has("json")) await writeOut(o["reporter-json-export"] ?? "wirecatch-run.json", `${JSON.stringify({ collection: report.collection, at: (/* @__PURE__ */ new Date()).toISOString(), summary: report.summary, bailed: report.bailed, steps: report.steps }, null, 2)}
|
|
29230
29905
|
`);
|
|
29231
|
-
if (reporters.has("junit")) await writeOut(o["reporter-junit-export"] ?? "wirecatch-junit.xml", toJUnit(report));
|
|
29906
|
+
if (reporters.has("junit")) await writeOut(o["reporter-junit-export"] ?? "wirecatch-junit.xml", toJUnit(report, { securityFailOn }));
|
|
29232
29907
|
if (o["export-environment"]) await writeOut(o["export-environment"], `${JSON.stringify(exportPostmanEnvironment(state.environment ?? { id: "env_cli", name: "CLI", variables: [] }), null, 2)}
|
|
29233
29908
|
`);
|
|
29234
29909
|
if (o["export-globals"]) await writeOut(o["export-globals"], `${JSON.stringify({ ...exportPostmanEnvironment({ id: "globals", name: "Globals", variables: state.globals }), _postman_variable_scope: "globals" }, null, 2)}
|
|
29235
29910
|
`);
|
|
29236
|
-
|
|
29911
|
+
const insecure = securityFailOn ? report.steps.some((st) => st.security?.some((f) => atLeast(f.severity, securityFailOn))) : false;
|
|
29912
|
+
if (cli && insecure) process.stdout.write(red2(`Security findings at ${securityFailOn} or above (--fail-on-security).
|
|
29913
|
+
`));
|
|
29914
|
+
return report.summary.failedRequests > 0 || report.summary.failed > 0 || insecure ? 1 : 0;
|
|
29237
29915
|
}
|
|
29238
|
-
|
|
29916
|
+
var argv = process.argv.slice(2);
|
|
29917
|
+
(argv[0] === "scan" ? scanCommand(argv.slice(1)) : run(argv)).then(
|
|
29239
29918
|
(code) => {
|
|
29240
29919
|
process.exitCode = code;
|
|
29241
29920
|
},
|