@ferricstore/ferricstore 0.11.9 → 0.11.11
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 +29 -9
- package/dist/index.cjs +494 -159
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +3 -1
- package/dist/index.d.ts +3 -1
- package/dist/index.js +483 -148
- package/dist/index.js.map +1 -1
- package/docs/api/classes/HTTPAdapter.html +7 -7
- package/docs/api/classes/KeyValueStore.html +4 -4
- package/docs/api/functions/httpCommandDisposition.html +1 -1
- package/docs/api/index.html +25 -9
- package/docs/api/interfaces/HTTPAdapterOptions.html +19 -15
- package/docs/api/types/HTTPCommandDisposition.html +1 -1
- package/docs/api/variables/FERRICSTORE_SDK_VERSION.html +1 -1
- package/package.json +2 -1
package/dist/index.js
CHANGED
|
@@ -1456,6 +1456,7 @@ var neverAutoBatchCommandPrefixes = /* @__PURE__ */ new Set([
|
|
|
1456
1456
|
"BLPOP",
|
|
1457
1457
|
"BRPOP",
|
|
1458
1458
|
"BRPOPLPUSH",
|
|
1459
|
+
"BZMPOP",
|
|
1459
1460
|
"BZPOPMAX",
|
|
1460
1461
|
"BZPOPMIN",
|
|
1461
1462
|
"CLIENT",
|
|
@@ -1567,6 +1568,9 @@ var connectionBlockingCommands = /* @__PURE__ */ new Set([
|
|
|
1567
1568
|
"BLPOP",
|
|
1568
1569
|
"BRPOP",
|
|
1569
1570
|
"BRPOPLPUSH",
|
|
1571
|
+
"BZMPOP",
|
|
1572
|
+
"BZPOPMAX",
|
|
1573
|
+
"BZPOPMIN",
|
|
1570
1574
|
"XREAD",
|
|
1571
1575
|
"XREADGROUP"
|
|
1572
1576
|
]);
|
|
@@ -2435,8 +2439,10 @@ function serverBlockMetadata(args) {
|
|
|
2435
2439
|
serverBlockMs = blockDurationMs(args[3], 1e3);
|
|
2436
2440
|
} else if (command === "BLMOVE" && args.length >= 6) {
|
|
2437
2441
|
serverBlockMs = blockDurationMs(args[args.length - 1], 1e3);
|
|
2438
|
-
} else if (command === "BLMPOP" && args.length >= 2) {
|
|
2442
|
+
} else if ((command === "BLMPOP" || command === "BZMPOP") && args.length >= 2) {
|
|
2439
2443
|
serverBlockMs = blockDurationMs(args[1], 1e3);
|
|
2444
|
+
} else if ((command === "BZPOPMAX" || command === "BZPOPMIN") && args.length >= 3) {
|
|
2445
|
+
serverBlockMs = blockDurationMs(args[args.length - 1], 1e3);
|
|
2440
2446
|
} else if (command === "XREAD" || command === "XREADGROUP") {
|
|
2441
2447
|
serverBlockMs = optionBlockDurationMs(args, ["BLOCK"], "STREAMS");
|
|
2442
2448
|
} else if (command === "WAIT" && args.length === 3) {
|
|
@@ -7496,6 +7502,24 @@ async function executeIndividually(host, commands, laneId, options) {
|
|
|
7496
7502
|
}, commands, options);
|
|
7497
7503
|
}
|
|
7498
7504
|
|
|
7505
|
+
// src/server-response-timeout.ts
|
|
7506
|
+
function serverResponseTimeoutMs(requestTimeoutMs, serverBlockMs) {
|
|
7507
|
+
if (serverBlockMs == null) return requestTimeoutMs;
|
|
7508
|
+
if (serverBlockMs === 0) return void 0;
|
|
7509
|
+
return saturatingAdd(requestTimeoutMs, serverBlockMs);
|
|
7510
|
+
}
|
|
7511
|
+
function combinedServerBlockMs(values) {
|
|
7512
|
+
let total;
|
|
7513
|
+
for (const value of values) {
|
|
7514
|
+
if (value === 0) return 0;
|
|
7515
|
+
if (value != null) total = saturatingAdd(total ?? 0, value);
|
|
7516
|
+
}
|
|
7517
|
+
return total;
|
|
7518
|
+
}
|
|
7519
|
+
function saturatingAdd(left, right) {
|
|
7520
|
+
return Math.min(Number.MAX_SAFE_INTEGER, left + right);
|
|
7521
|
+
}
|
|
7522
|
+
|
|
7499
7523
|
// src/native-pending-timeout.ts
|
|
7500
7524
|
function timeoutNativePendingRequest(operations, requestId, timeoutMs) {
|
|
7501
7525
|
const pending = operations.getPending(requestId);
|
|
@@ -7524,10 +7548,7 @@ function timeoutNativePendingRequest(operations, requestId, timeoutMs) {
|
|
|
7524
7548
|
pending.reject(new RequestTimeoutError(timeoutMs, "possibly_sent"));
|
|
7525
7549
|
}
|
|
7526
7550
|
function nativeResponseTimeoutMs(command, requestTimeoutMs) {
|
|
7527
|
-
|
|
7528
|
-
if (blockMs == null) return requestTimeoutMs;
|
|
7529
|
-
if (blockMs === 0) return void 0;
|
|
7530
|
-
return Math.min(Number.MAX_SAFE_INTEGER, requestTimeoutMs + blockMs);
|
|
7551
|
+
return serverResponseTimeoutMs(requestTimeoutMs, command.serverBlockMs);
|
|
7531
7552
|
}
|
|
7532
7553
|
|
|
7533
7554
|
// src/native-chunk-assembler.ts
|
|
@@ -8555,12 +8576,14 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
8555
8576
|
};
|
|
8556
8577
|
|
|
8557
8578
|
// src/http-command-policy.ts
|
|
8579
|
+
import { Buffer as Buffer33 } from "buffer";
|
|
8558
8580
|
var nativeOnlyCommands = /* @__PURE__ */ new Set([
|
|
8559
8581
|
"AUTH",
|
|
8560
8582
|
"BACKPRESSURE",
|
|
8561
8583
|
"CLIENT",
|
|
8562
8584
|
"CLIENT.INFO",
|
|
8563
8585
|
"CLIENT.SETNAME",
|
|
8586
|
+
"COMMAND_EXEC",
|
|
8564
8587
|
"EVENT",
|
|
8565
8588
|
"GOAWAY",
|
|
8566
8589
|
"HELLO",
|
|
@@ -8576,84 +8599,139 @@ var nativeOnlyCommands = /* @__PURE__ */ new Set([
|
|
|
8576
8599
|
"WINDOW_UPDATE"
|
|
8577
8600
|
]);
|
|
8578
8601
|
var sessionOnlyCommands = /* @__PURE__ */ new Set([
|
|
8602
|
+
"ASKING",
|
|
8579
8603
|
"AUTH",
|
|
8580
|
-
"BLMOVE",
|
|
8581
|
-
"BLMPOP",
|
|
8582
|
-
"BLPOP",
|
|
8583
|
-
"BRPOP",
|
|
8584
8604
|
"CLIENT",
|
|
8585
8605
|
"DISCARD",
|
|
8586
8606
|
"EXEC",
|
|
8607
|
+
"FETCH_OR_COMPUTE",
|
|
8608
|
+
"FETCH_OR_COMPUTE_ERROR",
|
|
8609
|
+
"FETCH_OR_COMPUTE_RESULT",
|
|
8587
8610
|
"HELLO",
|
|
8611
|
+
"MONITOR",
|
|
8588
8612
|
"MULTI",
|
|
8589
8613
|
"PSUBSCRIBE",
|
|
8614
|
+
"PSYNC",
|
|
8590
8615
|
"PUNSUBSCRIBE",
|
|
8591
8616
|
"QUIT",
|
|
8617
|
+
"READONLY",
|
|
8618
|
+
"READWRITE",
|
|
8619
|
+
"REPLCONF",
|
|
8620
|
+
"RESET",
|
|
8621
|
+
"SANDBOX",
|
|
8592
8622
|
"SELECT",
|
|
8623
|
+
"SSUBSCRIBE",
|
|
8593
8624
|
"SUBSCRIBE",
|
|
8625
|
+
"SUNSUBSCRIBE",
|
|
8626
|
+
"SYNC",
|
|
8594
8627
|
"UNSUBSCRIBE",
|
|
8595
8628
|
"UNWATCH",
|
|
8596
|
-
"WATCH"
|
|
8597
|
-
"XREAD",
|
|
8598
|
-
"XREADGROUP"
|
|
8629
|
+
"WATCH"
|
|
8599
8630
|
]);
|
|
8600
8631
|
function httpCommandDisposition(name) {
|
|
8601
8632
|
const normalized = name.toUpperCase();
|
|
8602
8633
|
return nativeOnlyCommands.has(normalized) || sessionOnlyCommands.has(normalized) ? "native_only" : "supported";
|
|
8603
8634
|
}
|
|
8604
8635
|
function assertHTTPCommandSupported(name) {
|
|
8605
|
-
|
|
8606
|
-
if (
|
|
8607
|
-
|
|
8636
|
+
const normalized = normalizedCommandName(name);
|
|
8637
|
+
if (normalized == null || normalized === "") throw new TypeError("HTTP command must have a name");
|
|
8638
|
+
if (sessionOnlyCommands.has(normalized)) {
|
|
8639
|
+
throw new InvalidCommandError(`${normalized} requires a persistent native TCP session`);
|
|
8640
|
+
}
|
|
8641
|
+
if (nativeOnlyCommands.has(normalized)) {
|
|
8642
|
+
throw new InvalidCommandError(`${normalized} is a native TCP transport control command`);
|
|
8608
8643
|
}
|
|
8609
8644
|
}
|
|
8645
|
+
function normalizedCommandName(value) {
|
|
8646
|
+
if (typeof value === "string") return value.toUpperCase();
|
|
8647
|
+
if (Buffer33.isBuffer(value) || value instanceof Uint8Array) {
|
|
8648
|
+
return Buffer33.from(value).toString("utf8").toUpperCase();
|
|
8649
|
+
}
|
|
8650
|
+
return void 0;
|
|
8651
|
+
}
|
|
8610
8652
|
|
|
8611
8653
|
// src/http-envelope.ts
|
|
8612
|
-
import { Buffer as
|
|
8654
|
+
import { Buffer as Buffer34 } from "buffer";
|
|
8613
8655
|
var encoding = "ferricstore-json-v1";
|
|
8614
8656
|
var bytesMarker = "$ferricstore_bytes";
|
|
8615
8657
|
var mapMarker = "$ferricstore_map";
|
|
8616
8658
|
var maxDepth = 64;
|
|
8617
|
-
|
|
8618
|
-
|
|
8659
|
+
var integerJSON = /^-?(?:0|[1-9][0-9]*)$/u;
|
|
8660
|
+
var bytesMarkerBaseBytes = Buffer34.byteLength(bytesMarker) + 7;
|
|
8661
|
+
var mapMarkerBaseBytes = Buffer34.byteLength(mapMarker) + 7;
|
|
8662
|
+
function encodeHTTPCommands(commands, maxBytes = Number.MAX_SAFE_INTEGER) {
|
|
8663
|
+
const budget = { remaining: maxBytes };
|
|
8664
|
+
return Buffer34.from(JSON.stringify({
|
|
8619
8665
|
encoding,
|
|
8620
|
-
commands: commands.map((command) => encodeValue(command, 0))
|
|
8666
|
+
commands: commands.map((command) => encodeValue(command, 0, budget))
|
|
8621
8667
|
}));
|
|
8622
8668
|
}
|
|
8623
8669
|
function decodeHTTPEnvelope(source) {
|
|
8624
8670
|
let parsed;
|
|
8625
8671
|
try {
|
|
8626
|
-
parsed = JSON.parse(source.toString("utf8"));
|
|
8672
|
+
parsed = JSON.parse(source.toString("utf8"), preserveIntegerPrecision);
|
|
8627
8673
|
} catch (error) {
|
|
8628
8674
|
throw new TypeError("invalid HTTP command response JSON", { cause: error });
|
|
8629
8675
|
}
|
|
8630
8676
|
if (!isRecord(parsed)) throw new TypeError("HTTP command response must be an object");
|
|
8631
8677
|
return decodePlainRecord(parsed, 0);
|
|
8632
8678
|
}
|
|
8633
|
-
function
|
|
8679
|
+
function preserveIntegerPrecision(_key, value, context) {
|
|
8680
|
+
if (typeof value !== "number" || Number.isSafeInteger(value) || !Number.isInteger(value)) {
|
|
8681
|
+
return value;
|
|
8682
|
+
}
|
|
8683
|
+
const literal = context?.source;
|
|
8684
|
+
return literal != null && integerJSON.test(literal) ? BigInt(literal) : value;
|
|
8685
|
+
}
|
|
8686
|
+
function encodeValue(value, depth, budget) {
|
|
8634
8687
|
if (depth > maxDepth) throw new TypeError("HTTP command value exceeds maximum depth");
|
|
8635
|
-
if (value == null
|
|
8636
|
-
|
|
8637
|
-
return
|
|
8688
|
+
if (value == null) {
|
|
8689
|
+
consumeBudget(budget, 1);
|
|
8690
|
+
return value;
|
|
8691
|
+
}
|
|
8692
|
+
if (typeof value === "string") {
|
|
8693
|
+
consumeBudget(budget, Buffer34.byteLength(value) + 2);
|
|
8694
|
+
return value;
|
|
8695
|
+
}
|
|
8696
|
+
if (typeof value === "boolean") {
|
|
8697
|
+
consumeBudget(budget, 1);
|
|
8698
|
+
return value;
|
|
8699
|
+
}
|
|
8700
|
+
if (Buffer34.isBuffer(value) || value instanceof Uint8Array) {
|
|
8701
|
+
consumeBudget(budget, bytesMarkerBaseBytes + 4 * Math.ceil(value.byteLength / 3));
|
|
8702
|
+
return { [bytesMarker]: Buffer34.from(value).toString("base64") };
|
|
8638
8703
|
}
|
|
8639
8704
|
if (typeof value === "number") {
|
|
8640
8705
|
if (!Number.isFinite(value)) throw new TypeError("HTTP command numbers must be finite");
|
|
8706
|
+
consumeBudget(budget, 1);
|
|
8641
8707
|
return value;
|
|
8642
8708
|
}
|
|
8643
8709
|
if (typeof value === "bigint") {
|
|
8644
|
-
|
|
8710
|
+
const encoded = value >= BigInt(Number.MIN_SAFE_INTEGER) && value <= BigInt(Number.MAX_SAFE_INTEGER) ? Number(value) : value.toString();
|
|
8711
|
+
consumeBudget(budget, typeof encoded === "number" ? 1 : Buffer34.byteLength(encoded) + 2);
|
|
8712
|
+
return encoded;
|
|
8713
|
+
}
|
|
8714
|
+
if (Array.isArray(value)) {
|
|
8715
|
+
consumeBudget(budget, 2 + Math.max(0, value.length - 1));
|
|
8716
|
+
return denseArray(value, depth + 1, (item, itemDepth) => encodeValue(item, itemDepth, budget));
|
|
8645
8717
|
}
|
|
8646
|
-
if (Array.isArray(value)) return denseArray(value, depth + 1, encodeValue);
|
|
8647
8718
|
if (value instanceof Map) {
|
|
8648
|
-
|
|
8649
|
-
|
|
8650
|
-
|
|
8651
|
-
|
|
8719
|
+
consumeBudget(budget, mapMarkerBaseBytes + value.size);
|
|
8720
|
+
const pairs = [];
|
|
8721
|
+
for (const [key, item] of value.entries()) {
|
|
8722
|
+
pairs.push([
|
|
8723
|
+
encodeValue(key, depth + 1, budget),
|
|
8724
|
+
encodeValue(item, depth + 1, budget)
|
|
8725
|
+
]);
|
|
8726
|
+
}
|
|
8727
|
+
return { [mapMarker]: pairs };
|
|
8652
8728
|
}
|
|
8653
8729
|
if (isRecord(value)) {
|
|
8654
|
-
|
|
8655
|
-
|
|
8656
|
-
|
|
8730
|
+
const keys = Object.keys(value);
|
|
8731
|
+
consumeBudget(budget, mapMarkerBaseBytes + keys.length);
|
|
8732
|
+
return { [mapMarker]: keys.map((key) => [
|
|
8733
|
+
encodeValue(key, depth + 1, budget),
|
|
8734
|
+
encodeValue(value[key], depth + 1, budget)
|
|
8657
8735
|
]) };
|
|
8658
8736
|
}
|
|
8659
8737
|
throw new TypeError(`unsupported HTTP command value: ${typeof value}`);
|
|
@@ -8679,15 +8757,28 @@ function decodeBase64(value) {
|
|
|
8679
8757
|
if (value.length % 4 !== 0 || !/^(?:[A-Za-z0-9+/]{4})*(?:[A-Za-z0-9+/]{2}==|[A-Za-z0-9+/]{3}=)?$/.test(value)) {
|
|
8680
8758
|
throw new TypeError("invalid HTTP bytes marker");
|
|
8681
8759
|
}
|
|
8682
|
-
const decoded =
|
|
8760
|
+
const decoded = Buffer34.from(value, "base64");
|
|
8683
8761
|
if (decoded.toString("base64") !== value) throw new TypeError("invalid HTTP bytes marker");
|
|
8684
8762
|
return decoded;
|
|
8685
8763
|
}
|
|
8686
8764
|
function decodePlainRecord(value, depth) {
|
|
8687
8765
|
const result = {};
|
|
8688
|
-
for (const [key, item] of Object.entries(value))
|
|
8766
|
+
for (const [key, item] of Object.entries(value)) {
|
|
8767
|
+
Object.defineProperty(result, key, {
|
|
8768
|
+
configurable: true,
|
|
8769
|
+
enumerable: true,
|
|
8770
|
+
value: decodeValue2(item, depth),
|
|
8771
|
+
writable: true
|
|
8772
|
+
});
|
|
8773
|
+
}
|
|
8689
8774
|
return result;
|
|
8690
8775
|
}
|
|
8776
|
+
function consumeBudget(budget, amount) {
|
|
8777
|
+
if (amount > budget.remaining) {
|
|
8778
|
+
throw new HTTPTransportError("HTTP command request exceeds maxRequestBytes");
|
|
8779
|
+
}
|
|
8780
|
+
budget.remaining -= amount;
|
|
8781
|
+
}
|
|
8691
8782
|
function denseArray(values, depth, transform) {
|
|
8692
8783
|
const result = new Array(values.length);
|
|
8693
8784
|
for (let index = 0; index < values.length; index += 1) {
|
|
@@ -8697,10 +8788,12 @@ function denseArray(values, depth, transform) {
|
|
|
8697
8788
|
return result;
|
|
8698
8789
|
}
|
|
8699
8790
|
function isRecord(value) {
|
|
8700
|
-
return typeof value === "object" && value != null && !Array.isArray(value) && !
|
|
8791
|
+
return typeof value === "object" && value != null && !Array.isArray(value) && !Buffer34.isBuffer(value);
|
|
8701
8792
|
}
|
|
8702
8793
|
|
|
8703
8794
|
// src/http-options.ts
|
|
8795
|
+
import { Buffer as Buffer35 } from "buffer";
|
|
8796
|
+
import { validateHeaderName, validateHeaderValue } from "http";
|
|
8704
8797
|
function normalizeHTTPOptions(value, options) {
|
|
8705
8798
|
const url = new URL(value);
|
|
8706
8799
|
if (url.protocol !== "http:" && url.protocol !== "https:") {
|
|
@@ -8726,10 +8819,10 @@ function normalizeHTTPOptions(value, options) {
|
|
|
8726
8819
|
});
|
|
8727
8820
|
}
|
|
8728
8821
|
function normalizedHeaders(source) {
|
|
8729
|
-
const headers =
|
|
8822
|
+
const headers = /* @__PURE__ */ Object.create(null);
|
|
8730
8823
|
for (const [rawName, value] of Object.entries(source)) {
|
|
8731
8824
|
const name = rawName.toLowerCase();
|
|
8732
|
-
if (
|
|
8825
|
+
if (typeof value !== "string" || !validHeader(name, value)) {
|
|
8733
8826
|
throw new TypeError(`invalid HTTP header: ${rawName}`);
|
|
8734
8827
|
}
|
|
8735
8828
|
headers[name] = value;
|
|
@@ -8741,7 +8834,9 @@ function authorizationHeader(url, options, custom) {
|
|
|
8741
8834
|
const count = Number(custom != null) + Number(options.bearerToken != null) + Number(basic);
|
|
8742
8835
|
if (count > 1) throw new TypeError("HTTP credentials are mutually exclusive");
|
|
8743
8836
|
if (options.bearerToken != null) {
|
|
8744
|
-
if (
|
|
8837
|
+
if (options.bearerToken === "" || !validHeader("authorization", `Bearer ${options.bearerToken}`)) {
|
|
8838
|
+
throw new TypeError("invalid bearer token");
|
|
8839
|
+
}
|
|
8745
8840
|
return `Bearer ${options.bearerToken}`;
|
|
8746
8841
|
}
|
|
8747
8842
|
if (!basic) return custom;
|
|
@@ -8751,7 +8846,7 @@ function authorizationHeader(url, options, custom) {
|
|
|
8751
8846
|
if (username === "" || username.includes(":") || !safeHeader(username) || !safeHeader(options.password)) {
|
|
8752
8847
|
throw new TypeError("invalid Basic authentication credentials");
|
|
8753
8848
|
}
|
|
8754
|
-
return `Basic ${
|
|
8849
|
+
return `Basic ${Buffer35.from(`${username}:${options.password}`).toString("base64")}`;
|
|
8755
8850
|
}
|
|
8756
8851
|
function positiveInteger(value, fallback, name) {
|
|
8757
8852
|
const result = value ?? fallback;
|
|
@@ -8771,36 +8866,167 @@ function booleanOption(value, fallback, name) {
|
|
|
8771
8866
|
function safeHeader(value) {
|
|
8772
8867
|
return !value.includes("\r") && !value.includes("\n");
|
|
8773
8868
|
}
|
|
8869
|
+
function validHeader(name, value) {
|
|
8870
|
+
try {
|
|
8871
|
+
validateHeaderName(name);
|
|
8872
|
+
validateHeaderValue(name, value);
|
|
8873
|
+
return true;
|
|
8874
|
+
} catch {
|
|
8875
|
+
return false;
|
|
8876
|
+
}
|
|
8877
|
+
}
|
|
8774
8878
|
|
|
8775
8879
|
// src/http-transport.ts
|
|
8776
8880
|
import http from "http";
|
|
8777
8881
|
import http2 from "http2";
|
|
8778
8882
|
import https from "https";
|
|
8779
|
-
import { Buffer as
|
|
8883
|
+
import { Buffer as Buffer36 } from "buffer";
|
|
8884
|
+
|
|
8885
|
+
// src/http2-slot-pool.ts
|
|
8886
|
+
var HTTP2SessionRetiredError = class extends Error {
|
|
8887
|
+
constructor(message, cause) {
|
|
8888
|
+
super(message, { cause });
|
|
8889
|
+
this.name = "HTTP2SessionRetiredError";
|
|
8890
|
+
}
|
|
8891
|
+
};
|
|
8892
|
+
var HTTP2SlotPool = class {
|
|
8893
|
+
active = 0;
|
|
8894
|
+
idleCallback;
|
|
8895
|
+
limit;
|
|
8896
|
+
retiredError;
|
|
8897
|
+
waiterHead;
|
|
8898
|
+
waiterTail;
|
|
8899
|
+
acquire(signal) {
|
|
8900
|
+
if (signal.aborted) return Promise.reject(signalAbortError(signal));
|
|
8901
|
+
if (this.retiredError != null) return Promise.reject(this.retiredError);
|
|
8902
|
+
if (this.limit != null && this.active < this.limit) {
|
|
8903
|
+
this.active += 1;
|
|
8904
|
+
return Promise.resolve(this.releaseOnce());
|
|
8905
|
+
}
|
|
8906
|
+
return new Promise((resolve, reject) => {
|
|
8907
|
+
const waiter = {
|
|
8908
|
+
abort: () => {
|
|
8909
|
+
if (waiter.settled) return;
|
|
8910
|
+
waiter.settled = true;
|
|
8911
|
+
this.removeWaiter(waiter);
|
|
8912
|
+
reject(signalAbortError(signal));
|
|
8913
|
+
},
|
|
8914
|
+
queued: true,
|
|
8915
|
+
reject,
|
|
8916
|
+
resolve,
|
|
8917
|
+
settled: false,
|
|
8918
|
+
signal
|
|
8919
|
+
};
|
|
8920
|
+
this.enqueueWaiter(waiter);
|
|
8921
|
+
signal.addEventListener("abort", waiter.abort, { once: true });
|
|
8922
|
+
});
|
|
8923
|
+
}
|
|
8924
|
+
updateLimit(limit) {
|
|
8925
|
+
if (this.retiredError != null) return;
|
|
8926
|
+
this.limit = limit;
|
|
8927
|
+
this.drain();
|
|
8928
|
+
}
|
|
8929
|
+
retire(error) {
|
|
8930
|
+
if (this.retiredError != null) return;
|
|
8931
|
+
this.retiredError = error;
|
|
8932
|
+
while (this.waiterHead != null) {
|
|
8933
|
+
const waiter = this.waiterHead;
|
|
8934
|
+
this.removeWaiter(waiter);
|
|
8935
|
+
if (waiter.settled) continue;
|
|
8936
|
+
waiter.settled = true;
|
|
8937
|
+
waiter.signal.removeEventListener("abort", waiter.abort);
|
|
8938
|
+
waiter.reject(error);
|
|
8939
|
+
}
|
|
8940
|
+
}
|
|
8941
|
+
whenIdle(callback) {
|
|
8942
|
+
if (this.active === 0) callback();
|
|
8943
|
+
else this.idleCallback = callback;
|
|
8944
|
+
}
|
|
8945
|
+
drain() {
|
|
8946
|
+
while (this.retiredError == null && this.limit != null && this.active < this.limit) {
|
|
8947
|
+
const waiter = this.waiterHead;
|
|
8948
|
+
if (waiter == null) return;
|
|
8949
|
+
this.removeWaiter(waiter);
|
|
8950
|
+
if (waiter.settled) continue;
|
|
8951
|
+
waiter.settled = true;
|
|
8952
|
+
waiter.signal.removeEventListener("abort", waiter.abort);
|
|
8953
|
+
this.active += 1;
|
|
8954
|
+
waiter.resolve(this.releaseOnce());
|
|
8955
|
+
}
|
|
8956
|
+
}
|
|
8957
|
+
enqueueWaiter(waiter) {
|
|
8958
|
+
waiter.previous = this.waiterTail;
|
|
8959
|
+
if (this.waiterTail == null) this.waiterHead = waiter;
|
|
8960
|
+
else this.waiterTail.next = waiter;
|
|
8961
|
+
this.waiterTail = waiter;
|
|
8962
|
+
}
|
|
8963
|
+
removeWaiter(waiter) {
|
|
8964
|
+
if (!waiter.queued) return;
|
|
8965
|
+
if (waiter.previous == null) this.waiterHead = waiter.next;
|
|
8966
|
+
else waiter.previous.next = waiter.next;
|
|
8967
|
+
if (waiter.next == null) this.waiterTail = waiter.previous;
|
|
8968
|
+
else waiter.next.previous = waiter.previous;
|
|
8969
|
+
waiter.next = void 0;
|
|
8970
|
+
waiter.previous = void 0;
|
|
8971
|
+
waiter.queued = false;
|
|
8972
|
+
}
|
|
8973
|
+
releaseOnce() {
|
|
8974
|
+
let released = false;
|
|
8975
|
+
return () => {
|
|
8976
|
+
if (released) return;
|
|
8977
|
+
released = true;
|
|
8978
|
+
this.active -= 1;
|
|
8979
|
+
this.drain();
|
|
8980
|
+
if (this.active === 0) {
|
|
8981
|
+
const callback = this.idleCallback;
|
|
8982
|
+
this.idleCallback = void 0;
|
|
8983
|
+
callback?.();
|
|
8984
|
+
}
|
|
8985
|
+
};
|
|
8986
|
+
}
|
|
8987
|
+
};
|
|
8988
|
+
function signalAbortError(signal) {
|
|
8989
|
+
return signal.reason instanceof Error ? signal.reason : new HTTPTransportError("HTTP request was aborted", { raw: signal.reason });
|
|
8990
|
+
}
|
|
8991
|
+
|
|
8992
|
+
// src/http-transport.ts
|
|
8780
8993
|
var HTTPTransport = class {
|
|
8781
8994
|
constructor(config) {
|
|
8782
8995
|
this.config = config;
|
|
8783
|
-
this.#httpAgent = new http.Agent({
|
|
8996
|
+
this.#httpAgent = new http.Agent({
|
|
8997
|
+
keepAlive: true,
|
|
8998
|
+
maxFreeSockets: config.maxConnections,
|
|
8999
|
+
maxSockets: config.maxConnections,
|
|
9000
|
+
maxTotalSockets: config.maxConnections
|
|
9001
|
+
});
|
|
8784
9002
|
this.#httpsAgent = new https.Agent({
|
|
8785
9003
|
...config.tlsOptions,
|
|
8786
9004
|
keepAlive: true,
|
|
8787
|
-
|
|
9005
|
+
maxFreeSockets: config.maxConnections,
|
|
9006
|
+
maxSockets: config.maxConnections,
|
|
9007
|
+
maxTotalSockets: config.maxConnections
|
|
8788
9008
|
});
|
|
8789
9009
|
}
|
|
8790
9010
|
config;
|
|
8791
9011
|
#httpAgent;
|
|
8792
9012
|
#httpsAgent;
|
|
9013
|
+
#allSessions = /* @__PURE__ */ new Set();
|
|
8793
9014
|
#sessions = /* @__PURE__ */ new Map();
|
|
9015
|
+
#sessionSlots = /* @__PURE__ */ new WeakMap();
|
|
9016
|
+
#requests = /* @__PURE__ */ new Set();
|
|
8794
9017
|
#closed = false;
|
|
8795
|
-
async post(body) {
|
|
9018
|
+
async post(body, timeoutMs) {
|
|
8796
9019
|
if (this.#closed) throw new HTTPTransportError("HTTP transport is closed");
|
|
8797
9020
|
const controller = new AbortController();
|
|
8798
|
-
|
|
9021
|
+
this.#requests.add(controller);
|
|
9022
|
+
const timer = timeoutMs == null ? void 0 : setLongTimeout(() => controller.abort(requestTimeoutReason), timeoutMs);
|
|
9023
|
+
timer?.unref();
|
|
8799
9024
|
try {
|
|
8800
9025
|
return await this.request(this.config.commandUrl, "POST", body, 0, controller.signal);
|
|
8801
9026
|
} catch (error) {
|
|
8802
9027
|
if (controller.signal.aborted) {
|
|
8803
|
-
|
|
9028
|
+
if (controller.signal.reason instanceof HTTPTransportError) throw controller.signal.reason;
|
|
9029
|
+
throw new RequestTimeoutError(timeoutMs ?? this.config.timeoutMs, "possibly_sent", {
|
|
8804
9030
|
cause: error,
|
|
8805
9031
|
raw: { retryable: true, safe_to_retry: false }
|
|
8806
9032
|
});
|
|
@@ -8812,15 +9038,19 @@ var HTTPTransport = class {
|
|
|
8812
9038
|
safeToRetry: false
|
|
8813
9039
|
});
|
|
8814
9040
|
} finally {
|
|
8815
|
-
|
|
9041
|
+
timer?.cancel();
|
|
9042
|
+
this.#requests.delete(controller);
|
|
8816
9043
|
}
|
|
8817
9044
|
}
|
|
8818
9045
|
async close() {
|
|
8819
9046
|
if (this.#closed) return;
|
|
8820
9047
|
this.#closed = true;
|
|
9048
|
+
const error = new HTTPTransportError("HTTP transport is closed");
|
|
9049
|
+
for (const controller of this.#requests) controller.abort(error);
|
|
8821
9050
|
this.#httpAgent.destroy();
|
|
8822
9051
|
this.#httpsAgent.destroy();
|
|
8823
|
-
for (const session of this.#
|
|
9052
|
+
for (const session of this.#allSessions) session.destroy();
|
|
9053
|
+
this.#allSessions.clear();
|
|
8824
9054
|
this.#sessions.clear();
|
|
8825
9055
|
}
|
|
8826
9056
|
async request(url, method, body, redirects, signal) {
|
|
@@ -8868,7 +9098,6 @@ var HTTPTransport = class {
|
|
|
8868
9098
|
);
|
|
8869
9099
|
}
|
|
8870
9100
|
async http2Request(url, method, body, signal) {
|
|
8871
|
-
const session = this.session(url);
|
|
8872
9101
|
const headers = {
|
|
8873
9102
|
...this.requestHeaders(body),
|
|
8874
9103
|
":authority": url.host,
|
|
@@ -8876,8 +9105,41 @@ var HTTPTransport = class {
|
|
|
8876
9105
|
":path": `${url.pathname}${url.search}`,
|
|
8877
9106
|
":scheme": url.protocol.slice(0, -1)
|
|
8878
9107
|
};
|
|
9108
|
+
if (signal.aborted) throw signalAbortError(signal);
|
|
9109
|
+
for (let attempt = 0; attempt < 2; attempt += 1) {
|
|
9110
|
+
const session = this.session(url);
|
|
9111
|
+
let release;
|
|
9112
|
+
try {
|
|
9113
|
+
release = await this.slotPool(session).acquire(signal);
|
|
9114
|
+
} catch (error) {
|
|
9115
|
+
if (attempt === 0 && error instanceof HTTP2SessionRetiredError && !signal.aborted) continue;
|
|
9116
|
+
throw error;
|
|
9117
|
+
}
|
|
9118
|
+
try {
|
|
9119
|
+
let stream;
|
|
9120
|
+
try {
|
|
9121
|
+
stream = session.request(headers);
|
|
9122
|
+
} catch (error) {
|
|
9123
|
+
if (attempt === 0 && retryableSessionOpenError(error) && !signal.aborted) {
|
|
9124
|
+
this.retireSession(url.origin, session, true, error);
|
|
9125
|
+
continue;
|
|
9126
|
+
}
|
|
9127
|
+
throw error;
|
|
9128
|
+
}
|
|
9129
|
+
try {
|
|
9130
|
+
return await this.collectHttp2(stream, body, signal);
|
|
9131
|
+
} catch (error) {
|
|
9132
|
+
if (attempt === 0 && refusedStreamError(error) && !signal.aborted) continue;
|
|
9133
|
+
throw error;
|
|
9134
|
+
}
|
|
9135
|
+
} finally {
|
|
9136
|
+
release();
|
|
9137
|
+
}
|
|
9138
|
+
}
|
|
9139
|
+
throw new HTTPTransportError("HTTP/2 session could not accept the request");
|
|
9140
|
+
}
|
|
9141
|
+
async collectHttp2(stream, body, signal) {
|
|
8879
9142
|
return await new Promise((resolve, reject) => {
|
|
8880
|
-
const stream = session.request(headers);
|
|
8881
9143
|
let responseHeaders = {};
|
|
8882
9144
|
const abort = () => stream.close(http2.constants.NGHTTP2_CANCEL);
|
|
8883
9145
|
signal.addEventListener("abort", abort, { once: true });
|
|
@@ -8887,19 +9149,60 @@ var HTTPTransport = class {
|
|
|
8887
9149
|
const status = Number(responseHeaders[":status"] ?? 0);
|
|
8888
9150
|
resolve({ body: response.body, headers: normalizeHeaders(responseHeaders), status });
|
|
8889
9151
|
}, reject).finally(() => signal.removeEventListener("abort", abort));
|
|
8890
|
-
|
|
9152
|
+
if (signal.aborted) abort();
|
|
9153
|
+
else stream.end(body);
|
|
8891
9154
|
});
|
|
8892
9155
|
}
|
|
8893
9156
|
session(url) {
|
|
8894
9157
|
const origin = url.origin;
|
|
8895
9158
|
const current = this.#sessions.get(origin);
|
|
8896
9159
|
if (current != null && !current.closed && !current.destroyed) return current;
|
|
8897
|
-
const session = http2.connect(origin,
|
|
8898
|
-
|
|
8899
|
-
|
|
9160
|
+
const session = http2.connect(origin, {
|
|
9161
|
+
...this.config.tlsOptions,
|
|
9162
|
+
settings: { enablePush: false }
|
|
9163
|
+
});
|
|
9164
|
+
const slots = new HTTP2SlotPool();
|
|
9165
|
+
this.#allSessions.add(session);
|
|
9166
|
+
this.#sessionSlots.set(session, slots);
|
|
9167
|
+
session.on("remoteSettings", (settings) => {
|
|
9168
|
+
const remoteLimit = settings.maxConcurrentStreams;
|
|
9169
|
+
const limit = typeof remoteLimit === "number" && Number.isFinite(remoteLimit) ? Math.max(0, Math.floor(remoteLimit)) : this.config.maxConnections;
|
|
9170
|
+
slots.updateLimit(Math.min(this.config.maxConnections, limit));
|
|
9171
|
+
});
|
|
9172
|
+
session.on("error", (error) => this.retireSession(origin, session, true, error));
|
|
9173
|
+
session.once("goaway", () => {
|
|
9174
|
+
this.retireSession(
|
|
9175
|
+
origin,
|
|
9176
|
+
session,
|
|
9177
|
+
"when_idle",
|
|
9178
|
+
new HTTP2SessionRetiredError("HTTP/2 session received GOAWAY")
|
|
9179
|
+
);
|
|
9180
|
+
});
|
|
9181
|
+
session.once("close", () => {
|
|
9182
|
+
if (session.destroyed) this.#allSessions.delete(session);
|
|
9183
|
+
this.retireSession(origin, session);
|
|
9184
|
+
});
|
|
8900
9185
|
this.#sessions.set(origin, session);
|
|
8901
9186
|
return session;
|
|
8902
9187
|
}
|
|
9188
|
+
retireSession(origin, session, destroy = false, cause) {
|
|
9189
|
+
if (this.#sessions.get(origin) === session) this.#sessions.delete(origin);
|
|
9190
|
+
const slots = this.#sessionSlots.get(session);
|
|
9191
|
+
slots?.retire(
|
|
9192
|
+
cause instanceof HTTP2SessionRetiredError ? cause : new HTTP2SessionRetiredError("HTTP/2 session is unavailable", cause)
|
|
9193
|
+
);
|
|
9194
|
+
if (destroy === true && !session.destroyed) session.destroy();
|
|
9195
|
+
else if (destroy === "when_idle") {
|
|
9196
|
+
slots?.whenIdle(() => {
|
|
9197
|
+
if (!session.destroyed) session.destroy();
|
|
9198
|
+
});
|
|
9199
|
+
}
|
|
9200
|
+
}
|
|
9201
|
+
slotPool(session) {
|
|
9202
|
+
const slots = this.#sessionSlots.get(session);
|
|
9203
|
+
if (slots == null) throw new HTTP2SessionRetiredError("HTTP/2 session is unavailable");
|
|
9204
|
+
return slots;
|
|
9205
|
+
}
|
|
8903
9206
|
requestHeaders(body) {
|
|
8904
9207
|
const headers = { ...this.config.headers };
|
|
8905
9208
|
delete headers["content-length"];
|
|
@@ -8911,11 +9214,21 @@ var HTTPTransport = class {
|
|
|
8911
9214
|
};
|
|
8912
9215
|
}
|
|
8913
9216
|
};
|
|
9217
|
+
var requestTimeoutReason = /* @__PURE__ */ Symbol("ferricstore-http-request-timeout");
|
|
9218
|
+
function retryableSessionOpenError(error) {
|
|
9219
|
+
if (typeof error !== "object" || error == null || !("code" in error)) return false;
|
|
9220
|
+
const code = error.code;
|
|
9221
|
+
return code === "ERR_HTTP2_GOAWAY_SESSION" || code === "ERR_HTTP2_INVALID_SESSION";
|
|
9222
|
+
}
|
|
9223
|
+
function refusedStreamError(error) {
|
|
9224
|
+
if (!(error instanceof Error)) return false;
|
|
9225
|
+
return error.code === "ERR_HTTP2_STREAM_ERROR" && error.message.includes("NGHTTP2_REFUSED_STREAM");
|
|
9226
|
+
}
|
|
8914
9227
|
async function collectBody(source, status, headers, maximum) {
|
|
8915
9228
|
const chunks = [];
|
|
8916
9229
|
let size = 0;
|
|
8917
9230
|
for await (const chunk of source) {
|
|
8918
|
-
const bytes2 =
|
|
9231
|
+
const bytes2 = Buffer36.from(chunk);
|
|
8919
9232
|
size += bytes2.byteLength;
|
|
8920
9233
|
if (size > maximum) {
|
|
8921
9234
|
const destroy = source.destroy;
|
|
@@ -8924,10 +9237,10 @@ async function collectBody(source, status, headers, maximum) {
|
|
|
8924
9237
|
}
|
|
8925
9238
|
chunks.push(bytes2);
|
|
8926
9239
|
}
|
|
8927
|
-
return { body:
|
|
9240
|
+
return { body: Buffer36.concat(chunks, size), headers, status };
|
|
8928
9241
|
}
|
|
8929
9242
|
function normalizeHeaders(headers) {
|
|
8930
|
-
const result =
|
|
9243
|
+
const result = /* @__PURE__ */ Object.create(null);
|
|
8931
9244
|
for (const [name, raw] of Object.entries(headers)) {
|
|
8932
9245
|
const value = headerValue(raw);
|
|
8933
9246
|
if (value != null) result[name.toLowerCase()] = value;
|
|
@@ -8979,11 +9292,16 @@ var HTTPAdapter = class _HTTPAdapter {
|
|
|
8979
9292
|
throw new HTTPTransportError("HTTP command batch exceeds maxBatchItems");
|
|
8980
9293
|
}
|
|
8981
9294
|
for (const command of commands) assertHTTPCommandSupported(command[0]);
|
|
8982
|
-
const
|
|
9295
|
+
const prepared = commands.map((command) => prepareHTTPCommand(command, this.#config.maxRequestBytes));
|
|
9296
|
+
const body = encodeHTTPCommands(prepared.map((command) => command.encoded), this.#config.maxRequestBytes);
|
|
8983
9297
|
if (body.byteLength > this.#config.maxRequestBytes) {
|
|
8984
9298
|
throw new HTTPTransportError("HTTP command request exceeds maxRequestBytes");
|
|
8985
9299
|
}
|
|
8986
|
-
const
|
|
9300
|
+
const serverBlockMs = combinedServerBlockMs(prepared.map((command) => command.serverBlockMs));
|
|
9301
|
+
const response = await this.#transport.post(
|
|
9302
|
+
body,
|
|
9303
|
+
serverResponseTimeoutMs(this.#config.timeoutMs, serverBlockMs)
|
|
9304
|
+
);
|
|
8987
9305
|
let envelope = {};
|
|
8988
9306
|
try {
|
|
8989
9307
|
if (response.body.byteLength > 0) envelope = decodeHTTPEnvelope(response.body);
|
|
@@ -9007,12 +9325,17 @@ var HTTPAdapter = class _HTTPAdapter {
|
|
|
9007
9325
|
var commandNamesByOpcode = new Map(
|
|
9008
9326
|
Object.entries(COMMAND_OPCODES).map(([name, opcode]) => [opcode, name])
|
|
9009
9327
|
);
|
|
9010
|
-
function
|
|
9328
|
+
function prepareHTTPCommand(command, maxRequestBytes) {
|
|
9011
9329
|
const protocol = buildProtocolCommand(command, maxRequestBytes, false);
|
|
9012
|
-
if (protocol.opcode === OPCODES.commandExec)
|
|
9330
|
+
if (protocol.opcode === OPCODES.commandExec) {
|
|
9331
|
+
return { encoded: command, serverBlockMs: protocol.serverBlockMs };
|
|
9332
|
+
}
|
|
9013
9333
|
const name = commandNamesByOpcode.get(protocol.opcode);
|
|
9014
9334
|
if (name == null) throw new HTTPTransportError(`HTTP command has unknown opcode ${protocol.opcode}`);
|
|
9015
|
-
return {
|
|
9335
|
+
return {
|
|
9336
|
+
encoded: { command: name, opcode: protocol.opcode, payload: protocol.payload ?? {} },
|
|
9337
|
+
serverBlockMs: protocol.serverBlockMs
|
|
9338
|
+
};
|
|
9016
9339
|
}
|
|
9017
9340
|
function validatedResult(value) {
|
|
9018
9341
|
if (!isRecord2(value)) throw new HTTPTransportError("HTTP response has an invalid result item");
|
|
@@ -9032,7 +9355,7 @@ function commandError(value) {
|
|
|
9032
9355
|
function topLevelError(status, envelope, retryAfter) {
|
|
9033
9356
|
const details = isRecord2(envelope.error) ? envelope.error : {};
|
|
9034
9357
|
const message = typeof details.message === "string" ? details.message : `HTTP command request failed with status ${status}`;
|
|
9035
|
-
const retryAfterMs2 =
|
|
9358
|
+
const retryAfterMs2 = retryAfterMilliseconds(retryAfter);
|
|
9036
9359
|
return new HTTPTransportError(message, {
|
|
9037
9360
|
raw: details,
|
|
9038
9361
|
retryable: status === 408 || status === 425 || status === 429 || status >= 500,
|
|
@@ -9041,6 +9364,18 @@ function topLevelError(status, envelope, retryAfter) {
|
|
|
9041
9364
|
statusCode: status
|
|
9042
9365
|
});
|
|
9043
9366
|
}
|
|
9367
|
+
function retryAfterMilliseconds(value) {
|
|
9368
|
+
if (value == null) return void 0;
|
|
9369
|
+
if (/^\d+$/u.test(value)) {
|
|
9370
|
+
const seconds = Number.parseInt(value, 10);
|
|
9371
|
+
const milliseconds2 = seconds * 1e3;
|
|
9372
|
+
return Number.isSafeInteger(milliseconds2) ? milliseconds2 : void 0;
|
|
9373
|
+
}
|
|
9374
|
+
const deadline = Date.parse(value);
|
|
9375
|
+
if (!Number.isFinite(deadline)) return void 0;
|
|
9376
|
+
const milliseconds = Math.max(0, deadline - Date.now());
|
|
9377
|
+
return Number.isSafeInteger(milliseconds) ? milliseconds : void 0;
|
|
9378
|
+
}
|
|
9044
9379
|
function isRecord2(value) {
|
|
9045
9380
|
return typeof value === "object" && value != null && !Array.isArray(value);
|
|
9046
9381
|
}
|
|
@@ -9056,7 +9391,7 @@ function executeCommandArgs(executor, args) {
|
|
|
9056
9391
|
import "buffer";
|
|
9057
9392
|
|
|
9058
9393
|
// src/command-retry-policy.ts
|
|
9059
|
-
import { Buffer as
|
|
9394
|
+
import { Buffer as Buffer37 } from "buffer";
|
|
9060
9395
|
function isCasMutation(args) {
|
|
9061
9396
|
const offset = commandName2(args[0]) === "COMMAND_EXEC" ? 1 : 0;
|
|
9062
9397
|
const name = commandName2(args[offset]);
|
|
@@ -9070,8 +9405,8 @@ function isCasMutation(args) {
|
|
|
9070
9405
|
}
|
|
9071
9406
|
function commandName2(value) {
|
|
9072
9407
|
if (typeof value === "string") return value.toUpperCase();
|
|
9073
|
-
if (
|
|
9074
|
-
return
|
|
9408
|
+
if (Buffer37.isBuffer(value) || value instanceof Uint8Array) {
|
|
9409
|
+
return Buffer37.from(value).toString("utf8").toUpperCase();
|
|
9075
9410
|
}
|
|
9076
9411
|
return void 0;
|
|
9077
9412
|
}
|
|
@@ -9286,12 +9621,12 @@ function normalizeNonNegativeInteger2(value, fallback) {
|
|
|
9286
9621
|
import "buffer";
|
|
9287
9622
|
|
|
9288
9623
|
// src/topology-routing.ts
|
|
9289
|
-
import { Buffer as
|
|
9624
|
+
import { Buffer as Buffer40 } from "buffer";
|
|
9290
9625
|
|
|
9291
9626
|
// src/flow-partition-route-cache.ts
|
|
9292
|
-
import { Buffer as
|
|
9627
|
+
import { Buffer as Buffer39 } from "buffer";
|
|
9293
9628
|
import { createHash } from "crypto";
|
|
9294
|
-
var AUTO_PREFIX =
|
|
9629
|
+
var AUTO_PREFIX = Buffer39.from("__flow_auto__:", "ascii");
|
|
9295
9630
|
var MAX_CACHEABLE_PARTITION_BYTES = 4 * 1024;
|
|
9296
9631
|
var MAX_CACHE_BYTES = 1 * 1024 * 1024;
|
|
9297
9632
|
var MAX_CACHE_ENTRIES = 1024;
|
|
@@ -9301,10 +9636,10 @@ var cacheBytes = 0;
|
|
|
9301
9636
|
var cacheHits = 0;
|
|
9302
9637
|
var cacheMisses = 0;
|
|
9303
9638
|
function flowLogicalPartitionRoutingKey(value) {
|
|
9304
|
-
if (typeof value !== "string" && !
|
|
9639
|
+
if (typeof value !== "string" && !Buffer39.isBuffer(value)) return void 0;
|
|
9305
9640
|
const autoBucket = flowAutoBucket(value);
|
|
9306
9641
|
if (autoBucket != null) return `{fa:${autoBucket}}`;
|
|
9307
|
-
const bytes2 =
|
|
9642
|
+
const bytes2 = Buffer39.isBuffer(value) ? value : Buffer39.from(value);
|
|
9308
9643
|
if (bytes2.byteLength > MAX_CACHEABLE_PARTITION_BYTES) return hashRoute(bytes2);
|
|
9309
9644
|
const cacheKey = bytes2.toString("base64");
|
|
9310
9645
|
const cached = routeCache.get(cacheKey);
|
|
@@ -9378,7 +9713,7 @@ function routingKeyFromProtocolPayload(name, command) {
|
|
|
9378
9713
|
"scope"
|
|
9379
9714
|
]) {
|
|
9380
9715
|
const value = getField(command.payload, field3);
|
|
9381
|
-
if (typeof value === "string" ||
|
|
9716
|
+
if (typeof value === "string" || Buffer40.isBuffer(value)) {
|
|
9382
9717
|
return value;
|
|
9383
9718
|
}
|
|
9384
9719
|
}
|
|
@@ -9426,7 +9761,7 @@ function flowRoutingData(name, args) {
|
|
|
9426
9761
|
if (typeof partition === "string" && partition.toUpperCase() !== "AUTO" && partition.toUpperCase() !== "MIXED") {
|
|
9427
9762
|
return flowRoutingResult(flowLogicalPartitionRoutingKey(partition));
|
|
9428
9763
|
}
|
|
9429
|
-
if (
|
|
9764
|
+
if (Buffer40.isBuffer(partition)) {
|
|
9430
9765
|
const text3 = partition.toString("utf8").toUpperCase();
|
|
9431
9766
|
if (text3 !== "AUTO" && text3 !== "MIXED") {
|
|
9432
9767
|
return flowRoutingResult(flowLogicalPartitionRoutingKey(partition));
|
|
@@ -9517,17 +9852,17 @@ function flowPartitionRoutingKeyFromCommand(command, claim) {
|
|
|
9517
9852
|
return { handled: false };
|
|
9518
9853
|
}
|
|
9519
9854
|
function isRoutingKey(value) {
|
|
9520
|
-
return typeof value === "string" ||
|
|
9855
|
+
return typeof value === "string" || Buffer40.isBuffer(value);
|
|
9521
9856
|
}
|
|
9522
9857
|
function flowAutoIdRoutingKey(value) {
|
|
9523
|
-
if (typeof value !== "string" && !
|
|
9858
|
+
if (typeof value !== "string" && !Buffer40.isBuffer(value)) {
|
|
9524
9859
|
return void 0;
|
|
9525
9860
|
}
|
|
9526
|
-
const bucket = (
|
|
9861
|
+
const bucket = (Buffer40.isBuffer(value) ? crc32(value) : crc32Utf8(value)) & 255;
|
|
9527
9862
|
return `{fa:${bucket}}`;
|
|
9528
9863
|
}
|
|
9529
9864
|
function flowClaimLogicalPartitionRoutingKey(value) {
|
|
9530
|
-
if (typeof value !== "string" && !
|
|
9865
|
+
if (typeof value !== "string" && !Buffer40.isBuffer(value)) return void 0;
|
|
9531
9866
|
const selector = commandPart(value);
|
|
9532
9867
|
if (selector === "AUTO" || selector === "ANY") return void 0;
|
|
9533
9868
|
if (selector === "GLOBAL") return "{f}";
|
|
@@ -9542,7 +9877,7 @@ function singleShardFlowClaimPartitionKey(values) {
|
|
|
9542
9877
|
return keys.some((key) => key == null) ? void 0 : singleShardKey(keys);
|
|
9543
9878
|
}
|
|
9544
9879
|
function singleShardKey(keys) {
|
|
9545
|
-
if (keys.length === 0 || keys.some((key) => typeof key !== "string" && !
|
|
9880
|
+
if (keys.length === 0 || keys.some((key) => typeof key !== "string" && !Buffer40.isBuffer(key))) {
|
|
9546
9881
|
return void 0;
|
|
9547
9882
|
}
|
|
9548
9883
|
const usable = keys;
|
|
@@ -9575,7 +9910,7 @@ function routedKeyGroups(keys, routeKey) {
|
|
|
9575
9910
|
const groups = /* @__PURE__ */ new Map();
|
|
9576
9911
|
for (let index = 0; index < keys.length; index += 1) {
|
|
9577
9912
|
const key = keys[index];
|
|
9578
|
-
if (typeof key !== "string" && !
|
|
9913
|
+
if (typeof key !== "string" && !Buffer40.isBuffer(key)) return void 0;
|
|
9579
9914
|
const route = routeKey(key);
|
|
9580
9915
|
const groupKey = `${route.endpointKey}\0${route.laneId}`;
|
|
9581
9916
|
const group = groups.get(groupKey);
|
|
@@ -10664,7 +10999,7 @@ var TopologyNativeAdapterPool = class _TopologyNativeAdapterPool {
|
|
|
10664
10999
|
};
|
|
10665
11000
|
|
|
10666
11001
|
// src/response-map-preservation.ts
|
|
10667
|
-
import { Buffer as
|
|
11002
|
+
import { Buffer as Buffer42 } from "buffer";
|
|
10668
11003
|
function toStringKeyMapPreservingValues(value) {
|
|
10669
11004
|
if (value == null) return void 0;
|
|
10670
11005
|
const result = {};
|
|
@@ -10674,7 +11009,7 @@ function toStringKeyMapPreservingValues(value) {
|
|
|
10674
11009
|
}
|
|
10675
11010
|
return result;
|
|
10676
11011
|
}
|
|
10677
|
-
if (typeof value === "object" && !Array.isArray(value) && !
|
|
11012
|
+
if (typeof value === "object" && !Array.isArray(value) && !Buffer42.isBuffer(value) && !(value instanceof Uint8Array)) {
|
|
10678
11013
|
for (const [key, item] of Object.entries(value)) {
|
|
10679
11014
|
setOwnValue(result, text(key), normalizeMapStructurePreservingBytes(item));
|
|
10680
11015
|
}
|
|
@@ -10683,7 +11018,7 @@ function toStringKeyMapPreservingValues(value) {
|
|
|
10683
11018
|
return void 0;
|
|
10684
11019
|
}
|
|
10685
11020
|
function normalizeMapStructurePreservingBytes(value) {
|
|
10686
|
-
if (
|
|
11021
|
+
if (Buffer42.isBuffer(value) || value instanceof Uint8Array) return value;
|
|
10687
11022
|
if (value instanceof Map) {
|
|
10688
11023
|
const result = {};
|
|
10689
11024
|
for (const [key, item] of value.entries()) {
|
|
@@ -10705,7 +11040,7 @@ function normalizeMapStructurePreservingBytes(value) {
|
|
|
10705
11040
|
}
|
|
10706
11041
|
|
|
10707
11042
|
// src/native-kv-responses.ts
|
|
10708
|
-
import { Buffer as
|
|
11043
|
+
import { Buffer as Buffer43 } from "buffer";
|
|
10709
11044
|
function rateLimitResultFromResp(value) {
|
|
10710
11045
|
if (!Array.isArray(value) || value.length !== 4) {
|
|
10711
11046
|
throw new TypeError("RATELIMIT.ADD returned an unexpected response");
|
|
@@ -10762,13 +11097,13 @@ function fetchOrComputeResultFromResp(value, codec) {
|
|
|
10762
11097
|
}
|
|
10763
11098
|
function decodePayload(codec, value) {
|
|
10764
11099
|
if (value == null) return null;
|
|
10765
|
-
if (
|
|
10766
|
-
if (value instanceof Uint8Array) return codec.decode(
|
|
10767
|
-
if (typeof value === "string") return codec.decode(
|
|
11100
|
+
if (Buffer43.isBuffer(value)) return codec.decode(value);
|
|
11101
|
+
if (value instanceof Uint8Array) return codec.decode(Buffer43.from(value));
|
|
11102
|
+
if (typeof value === "string") return codec.decode(Buffer43.from(value));
|
|
10768
11103
|
return normalizeRefMeta(value);
|
|
10769
11104
|
}
|
|
10770
11105
|
function requiredResponseString(value, context) {
|
|
10771
|
-
if (typeof value !== "string" && !
|
|
11106
|
+
if (typeof value !== "string" && !Buffer43.isBuffer(value) && !(value instanceof Uint8Array)) {
|
|
10772
11107
|
throw new TypeError(`${context} returned an unexpected response`);
|
|
10773
11108
|
}
|
|
10774
11109
|
const result = text(value);
|
|
@@ -10785,7 +11120,7 @@ function requiredNonNegativeInteger(value, context) {
|
|
|
10785
11120
|
return result;
|
|
10786
11121
|
}
|
|
10787
11122
|
function responseBytes(value, context) {
|
|
10788
|
-
if (typeof value !== "string" && !
|
|
11123
|
+
if (typeof value !== "string" && !Buffer43.isBuffer(value) && !(value instanceof Uint8Array)) {
|
|
10789
11124
|
throw new TypeError(`${context} returned an unexpected response`);
|
|
10790
11125
|
}
|
|
10791
11126
|
return bytes(value);
|
|
@@ -11468,7 +11803,7 @@ function groupAutoPartitionItems(items) {
|
|
|
11468
11803
|
}
|
|
11469
11804
|
|
|
11470
11805
|
// src/client-values.ts
|
|
11471
|
-
import { Buffer as
|
|
11806
|
+
import { Buffer as Buffer44 } from "buffer";
|
|
11472
11807
|
async function valueMGetEntries(client, refs, options = {}) {
|
|
11473
11808
|
const refCount = refs.length;
|
|
11474
11809
|
if (refCount === 0) {
|
|
@@ -11503,12 +11838,12 @@ async function valueMGetEntries(client, refs, options = {}) {
|
|
|
11503
11838
|
const item = response[index];
|
|
11504
11839
|
if (item == null) {
|
|
11505
11840
|
entries[index] = { found: false };
|
|
11506
|
-
} else if (
|
|
11841
|
+
} else if (Buffer44.isBuffer(item)) {
|
|
11507
11842
|
entries[index] = { found: true, value: client.codec.decode(item) };
|
|
11508
11843
|
} else if (item instanceof Uint8Array) {
|
|
11509
|
-
entries[index] = { found: true, value: client.codec.decode(
|
|
11844
|
+
entries[index] = { found: true, value: client.codec.decode(Buffer44.from(item)) };
|
|
11510
11845
|
} else if (typeof item === "string") {
|
|
11511
|
-
entries[index] = { found: true, value: client.codec.decode(
|
|
11846
|
+
entries[index] = { found: true, value: client.codec.decode(Buffer44.from(item)) };
|
|
11512
11847
|
} else {
|
|
11513
11848
|
entries[index] = { found: true, value: item };
|
|
11514
11849
|
}
|
|
@@ -11520,7 +11855,7 @@ async function valueMGetEntries(client, refs, options = {}) {
|
|
|
11520
11855
|
import "buffer";
|
|
11521
11856
|
|
|
11522
11857
|
// src/auto-batch-ordering.ts
|
|
11523
|
-
import { Buffer as
|
|
11858
|
+
import { Buffer as Buffer45 } from "buffer";
|
|
11524
11859
|
function autoBatchOrderingPlan(batch) {
|
|
11525
11860
|
const accesses = /* @__PURE__ */ new Map();
|
|
11526
11861
|
const fallbackDependencies = [];
|
|
@@ -11635,13 +11970,13 @@ function flowManyAutoBatchIds(command, name) {
|
|
|
11635
11970
|
return fixedFlowItemIds(
|
|
11636
11971
|
command,
|
|
11637
11972
|
mixed ? 4 : 3,
|
|
11638
|
-
(itemIndex) => isAutoBatchResourceValue(command[itemIndex]) && (!mixed || isAutoBatchResourceValue(command[itemIndex + 1])) && isFencingToken(command[itemIndex + (mixed ? 2 : 1)]) &&
|
|
11973
|
+
(itemIndex) => isAutoBatchResourceValue(command[itemIndex]) && (!mixed || isAutoBatchResourceValue(command[itemIndex + 1])) && isFencingToken(command[itemIndex + (mixed ? 2 : 1)]) && Buffer45.isBuffer(command[itemIndex + (mixed ? 3 : 2)])
|
|
11639
11974
|
);
|
|
11640
11975
|
}
|
|
11641
11976
|
return fixedFlowItemIds(
|
|
11642
11977
|
command,
|
|
11643
11978
|
mixed ? 4 : 3,
|
|
11644
|
-
(itemIndex) => isAutoBatchResourceValue(command[itemIndex]) && (!mixed || isAutoBatchResourceValue(command[itemIndex + 1])) &&
|
|
11979
|
+
(itemIndex) => isAutoBatchResourceValue(command[itemIndex]) && (!mixed || isAutoBatchResourceValue(command[itemIndex + 1])) && Buffer45.isBuffer(command[itemIndex + (mixed ? 2 : 1)]) && isFencingToken(command[itemIndex + (mixed ? 3 : 2)])
|
|
11645
11980
|
);
|
|
11646
11981
|
}
|
|
11647
11982
|
function createManyAutoBatchIds(command) {
|
|
@@ -11654,7 +11989,7 @@ function createManyAutoBatchIds(command) {
|
|
|
11654
11989
|
const ids = fixedFlowItemIds(
|
|
11655
11990
|
command,
|
|
11656
11991
|
width,
|
|
11657
|
-
(itemIndex) => isAutoBatchResourceValue(command[itemIndex]) && (!mixed || isAutoBatchResourceValue(command[itemIndex + 1])) &&
|
|
11992
|
+
(itemIndex) => isAutoBatchResourceValue(command[itemIndex]) && (!mixed || isAutoBatchResourceValue(command[itemIndex + 1])) && Buffer45.isBuffer(command[itemIndex + width - 1]),
|
|
11658
11993
|
markerIndex
|
|
11659
11994
|
);
|
|
11660
11995
|
if (ids != null) return ids;
|
|
@@ -11672,7 +12007,7 @@ function extendedCreateManyAutoBatchIds(command, markerIndex) {
|
|
|
11672
12007
|
let cursor = markerIndex + 2;
|
|
11673
12008
|
for (let itemIndex = 0; itemIndex < itemCount; itemIndex += 1) {
|
|
11674
12009
|
const id = command[cursor];
|
|
11675
|
-
if (!isAutoBatchResourceValue(id) || !isAutoBatchResourceValue(command[cursor + 1]) || !
|
|
12010
|
+
if (!isAutoBatchResourceValue(id) || !isAutoBatchResourceValue(command[cursor + 1]) || !Buffer45.isBuffer(command[cursor + 2])) return void 0;
|
|
11676
12011
|
ids.push(id);
|
|
11677
12012
|
cursor += 3;
|
|
11678
12013
|
const afterValues = skipExtendedNamedItems(command, cursor, true);
|
|
@@ -11691,7 +12026,7 @@ function skipExtendedNamedItems(command, countIndex, encodedValues) {
|
|
|
11691
12026
|
for (let index = 0; index < count; index += 1) {
|
|
11692
12027
|
const name = command[firstItem + index * 2];
|
|
11693
12028
|
const value = command[firstItem + index * 2 + 1];
|
|
11694
|
-
if (!isAutoBatchResourceValue(name) || (encodedValues ? !
|
|
12029
|
+
if (!isAutoBatchResourceValue(name) || (encodedValues ? !Buffer45.isBuffer(value) : !isAutoBatchResourceValue(value))) return void 0;
|
|
11695
12030
|
}
|
|
11696
12031
|
return firstItem + count * 2;
|
|
11697
12032
|
}
|
|
@@ -11706,7 +12041,7 @@ function runStepsManyAutoBatchIds(command) {
|
|
|
11706
12041
|
ids.push(item);
|
|
11707
12042
|
continue;
|
|
11708
12043
|
}
|
|
11709
|
-
if (typeof item !== "object" || item == null || Array.isArray(item) ||
|
|
12044
|
+
if (typeof item !== "object" || item == null || Array.isArray(item) || Buffer45.isBuffer(item)) return void 0;
|
|
11710
12045
|
const id = item.id;
|
|
11711
12046
|
if (!isAutoBatchResourceValue(id)) return void 0;
|
|
11712
12047
|
ids.push(id);
|
|
@@ -11747,7 +12082,7 @@ function flowValuePutOwner(command, start) {
|
|
|
11747
12082
|
}
|
|
11748
12083
|
var flowValuePutOptionTokens = /* @__PURE__ */ new Set(["NAME", "NOW", "OVERRIDE", "OWNER_FLOW_ID", "PARTITION", "TTL", "TTL_MS"]);
|
|
11749
12084
|
function isAutoBatchResourceValue(value) {
|
|
11750
|
-
return typeof value === "string" ||
|
|
12085
|
+
return typeof value === "string" || Buffer45.isBuffer(value);
|
|
11751
12086
|
}
|
|
11752
12087
|
function isFencingToken(value) {
|
|
11753
12088
|
return typeof value === "number" && Number.isSafeInteger(value) || typeof value === "bigint";
|
|
@@ -11756,7 +12091,7 @@ function nonNegativeItemCount(value) {
|
|
|
11756
12091
|
return typeof value === "number" && Number.isSafeInteger(value) && value >= 0 ? value : void 0;
|
|
11757
12092
|
}
|
|
11758
12093
|
function autoBatchResourceKey(namespace, value) {
|
|
11759
|
-
return `${namespace}:${
|
|
12094
|
+
return `${namespace}:${Buffer45.from(value).toString("base64")}`;
|
|
11760
12095
|
}
|
|
11761
12096
|
function autoBatchCommandName(command) {
|
|
11762
12097
|
return commandView(command).name ?? null;
|
|
@@ -12168,10 +12503,10 @@ function claimFailure(error) {
|
|
|
12168
12503
|
import "buffer";
|
|
12169
12504
|
|
|
12170
12505
|
// src/flow-query-builder.ts
|
|
12171
|
-
import { Buffer as
|
|
12506
|
+
import { Buffer as Buffer48 } from "buffer";
|
|
12172
12507
|
|
|
12173
12508
|
// src/flow-query-metadata.ts
|
|
12174
|
-
import { Buffer as
|
|
12509
|
+
import { Buffer as Buffer47 } from "buffer";
|
|
12175
12510
|
var MAX_FLOW_QUERY_METADATA_KEY_BYTES = 64;
|
|
12176
12511
|
function normalizeStateMeta(value, state) {
|
|
12177
12512
|
if (value == null) return {};
|
|
@@ -12196,7 +12531,7 @@ function normalizeStateMeta(value, state) {
|
|
|
12196
12531
|
function metadataEntries(value, context) {
|
|
12197
12532
|
const entries = objectEntries(value ?? {}, context).map(([rawName, item]) => {
|
|
12198
12533
|
const name = rawName.trim();
|
|
12199
|
-
const size =
|
|
12534
|
+
const size = Buffer47.byteLength(name, "utf8");
|
|
12200
12535
|
if (size === 0 || size > MAX_FLOW_QUERY_METADATA_KEY_BYTES || name.startsWith("__")) {
|
|
12201
12536
|
throw new TypeError(`${context} key is invalid or reserved`);
|
|
12202
12537
|
}
|
|
@@ -12220,7 +12555,7 @@ function objectEntries(value, context) {
|
|
|
12220
12555
|
return keys.map((key) => [key, value[key]]);
|
|
12221
12556
|
}
|
|
12222
12557
|
function isPlainRecord(value) {
|
|
12223
|
-
if (typeof value !== "object" || value == null || Array.isArray(value) ||
|
|
12558
|
+
if (typeof value !== "object" || value == null || Array.isArray(value) || Buffer47.isBuffer(value)) {
|
|
12224
12559
|
return false;
|
|
12225
12560
|
}
|
|
12226
12561
|
const prototype = Object.getPrototypeOf(value);
|
|
@@ -12290,7 +12625,7 @@ var FlowCollectionQuery = class {
|
|
|
12290
12625
|
const states = /* @__PURE__ */ new Set();
|
|
12291
12626
|
for (const [rawState, metadata] of objectEntries(values, "stateMeta")) {
|
|
12292
12627
|
const state = requiredText(rawState, "stateMeta state").trim();
|
|
12293
|
-
const stateBytes =
|
|
12628
|
+
const stateBytes = Buffer48.byteLength(state, "utf8");
|
|
12294
12629
|
if (stateBytes === 0 || stateBytes > MAX_FLOW_QUERY_STATE_BYTES) {
|
|
12295
12630
|
throw new TypeError(
|
|
12296
12631
|
`stateMeta state names must be 1..${MAX_FLOW_QUERY_STATE_BYTES} bytes`
|
|
@@ -12469,7 +12804,7 @@ function requiredPartition(value) {
|
|
|
12469
12804
|
"FLOW.QUERY convenience methods require a partition key"
|
|
12470
12805
|
);
|
|
12471
12806
|
}
|
|
12472
|
-
const size =
|
|
12807
|
+
const size = Buffer48.byteLength(value, "utf8");
|
|
12473
12808
|
if (size === 0 || size > MAX_FLOW_QUERY_PARTITION_BYTES) {
|
|
12474
12809
|
throw new TypeError(
|
|
12475
12810
|
`FLOW.QUERY partition key must be 1..${MAX_FLOW_QUERY_PARTITION_BYTES} bytes`
|
|
@@ -12517,23 +12852,23 @@ function requiredText(value, context) {
|
|
|
12517
12852
|
return value;
|
|
12518
12853
|
}
|
|
12519
12854
|
function queryParameter(value, context) {
|
|
12520
|
-
if (typeof value === "string" || typeof value === "boolean" || typeof value === "bigint" || typeof value === "number" ||
|
|
12855
|
+
if (typeof value === "string" || typeof value === "boolean" || typeof value === "bigint" || typeof value === "number" || Buffer48.isBuffer(value)) {
|
|
12521
12856
|
return value;
|
|
12522
12857
|
}
|
|
12523
12858
|
throw new TypeError(`${context} must be a scalar FLOW.QUERY parameter`);
|
|
12524
12859
|
}
|
|
12525
12860
|
|
|
12526
12861
|
// src/flow-query-response.ts
|
|
12527
|
-
import { Buffer as
|
|
12862
|
+
import { Buffer as Buffer52 } from "buffer";
|
|
12528
12863
|
|
|
12529
12864
|
// src/flow-query-diagnostic-response.ts
|
|
12530
|
-
import { Buffer as
|
|
12865
|
+
import { Buffer as Buffer50 } from "buffer";
|
|
12531
12866
|
|
|
12532
12867
|
// src/flow-query-response-validation.ts
|
|
12533
|
-
import { Buffer as
|
|
12868
|
+
import { Buffer as Buffer49 } from "buffer";
|
|
12534
12869
|
function requiredMap2(value, context) {
|
|
12535
12870
|
if (value instanceof Map) return value;
|
|
12536
|
-
if (typeof value !== "object" || value == null || Array.isArray(value) ||
|
|
12871
|
+
if (typeof value !== "object" || value == null || Array.isArray(value) || Buffer49.isBuffer(value) || value instanceof Uint8Array) {
|
|
12537
12872
|
throw decodeError(`${context} must be a map`, value);
|
|
12538
12873
|
}
|
|
12539
12874
|
return value;
|
|
@@ -12590,7 +12925,7 @@ function normalizeMetadataValue(value, context, budget, ancestors, depth) {
|
|
|
12590
12925
|
if (!value.isWellFormed()) throw decodeError(`${context} contains invalid text`, value);
|
|
12591
12926
|
return value;
|
|
12592
12927
|
}
|
|
12593
|
-
if (
|
|
12928
|
+
if (Buffer49.isBuffer(value) || value instanceof Uint8Array) {
|
|
12594
12929
|
const decoded = strictText2(value);
|
|
12595
12930
|
if (decoded == null) throw decodeError(`${context} contains invalid UTF-8`, value);
|
|
12596
12931
|
return decoded;
|
|
@@ -12669,7 +13004,7 @@ function optionalText2(mapping2, name, context) {
|
|
|
12669
13004
|
}
|
|
12670
13005
|
function requiredBoundedText2(mapping2, name, context, maximumBytes) {
|
|
12671
13006
|
const value = requiredText2(mapping2, name, context);
|
|
12672
|
-
if (
|
|
13007
|
+
if (Buffer49.byteLength(value, "utf8") > maximumBytes) {
|
|
12673
13008
|
throw decodeError(
|
|
12674
13009
|
`${context} ${name} exceeds ${maximumBytes} bytes`,
|
|
12675
13010
|
mapping2
|
|
@@ -12682,7 +13017,7 @@ function boundedText(value, context, maximumBytes) {
|
|
|
12682
13017
|
if (decoded == null || decoded.length === 0) {
|
|
12683
13018
|
throw decodeError(`${context} must be non-empty text`, value);
|
|
12684
13019
|
}
|
|
12685
|
-
if (
|
|
13020
|
+
if (Buffer49.byteLength(decoded, "utf8") > maximumBytes) {
|
|
12686
13021
|
throw decodeError(`${context} exceeds ${maximumBytes} bytes`, value);
|
|
12687
13022
|
}
|
|
12688
13023
|
return decoded;
|
|
@@ -12736,10 +13071,10 @@ function positiveBoundedInteger(value, maximum, context) {
|
|
|
12736
13071
|
function hasKey(mapping2, name) {
|
|
12737
13072
|
if (!(mapping2 instanceof Map)) return Object.hasOwn(mapping2, name);
|
|
12738
13073
|
if (mapping2.has(name)) return true;
|
|
12739
|
-
const binaryName =
|
|
13074
|
+
const binaryName = Buffer49.from(name);
|
|
12740
13075
|
for (const key of mapping2.keys()) {
|
|
12741
|
-
if (
|
|
12742
|
-
if (key instanceof Uint8Array &&
|
|
13076
|
+
if (Buffer49.isBuffer(key) && key.equals(binaryName)) return true;
|
|
13077
|
+
if (key instanceof Uint8Array && Buffer49.from(key).equals(binaryName))
|
|
12743
13078
|
return true;
|
|
12744
13079
|
}
|
|
12745
13080
|
return false;
|
|
@@ -12750,7 +13085,7 @@ function decodeError(message, raw) {
|
|
|
12750
13085
|
function strictText2(value) {
|
|
12751
13086
|
if (typeof value === "string")
|
|
12752
13087
|
return value.isWellFormed() ? value : void 0;
|
|
12753
|
-
if (
|
|
13088
|
+
if (Buffer49.isBuffer(value) || value instanceof Uint8Array) {
|
|
12754
13089
|
try {
|
|
12755
13090
|
return new TextDecoder("utf-8", { fatal: true }).decode(value);
|
|
12756
13091
|
} catch {
|
|
@@ -12830,7 +13165,7 @@ function tryDecodeFlowQueryError(value, cause) {
|
|
|
12830
13165
|
}
|
|
12831
13166
|
function optionalDiagnosticText(mapping2, name) {
|
|
12832
13167
|
const value = optionalText2(mapping2, name, "FLOW.QUERY diagnostic");
|
|
12833
|
-
if (value != null &&
|
|
13168
|
+
if (value != null && Buffer50.byteLength(value, "utf8") > DIAGNOSTIC_TEXT_BYTES) {
|
|
12834
13169
|
throw decodeError(
|
|
12835
13170
|
`FLOW.QUERY diagnostic ${name} exceeds ${DIAGNOSTIC_TEXT_BYTES} bytes`,
|
|
12836
13171
|
mapping2
|
|
@@ -12865,7 +13200,7 @@ function validateDiagnosticContextValue(value, depth, budget) {
|
|
|
12865
13200
|
}
|
|
12866
13201
|
const text3 = diagnosticContextText(value);
|
|
12867
13202
|
if (text3 != null) {
|
|
12868
|
-
if (
|
|
13203
|
+
if (Buffer50.byteLength(text3, "utf8") <= DIAGNOSTIC_TEXT_BYTES) return;
|
|
12869
13204
|
throw decodeError("FLOW.QUERY diagnostic context contains oversized text", value);
|
|
12870
13205
|
}
|
|
12871
13206
|
if (depth <= 0) {
|
|
@@ -12891,7 +13226,7 @@ function validateDiagnosticContextValue(value, depth, budget) {
|
|
|
12891
13226
|
}
|
|
12892
13227
|
for (const [rawKey, item] of entries) {
|
|
12893
13228
|
const key = diagnosticContextText(rawKey);
|
|
12894
|
-
if (key == null || key.length === 0 ||
|
|
13229
|
+
if (key == null || key.length === 0 || Buffer50.byteLength(key, "utf8") > DIAGNOSTIC_CONTEXT_KEY_BYTES) {
|
|
12895
13230
|
throw decodeError("FLOW.QUERY diagnostic context contains an invalid key", value);
|
|
12896
13231
|
}
|
|
12897
13232
|
validateDiagnosticContextValue(item, depth - 1, budget);
|
|
@@ -12908,7 +13243,7 @@ function consumeDiagnosticContextNode(value, budget) {
|
|
|
12908
13243
|
}
|
|
12909
13244
|
function diagnosticContextText(value) {
|
|
12910
13245
|
if (typeof value === "string") return value.isWellFormed() ? value : void 0;
|
|
12911
|
-
if (!
|
|
13246
|
+
if (!Buffer50.isBuffer(value) && !(value instanceof Uint8Array)) return void 0;
|
|
12912
13247
|
try {
|
|
12913
13248
|
return new TextDecoder("utf-8", { fatal: true }).decode(value);
|
|
12914
13249
|
} catch {
|
|
@@ -12934,7 +13269,7 @@ function decodePosition(value) {
|
|
|
12934
13269
|
}
|
|
12935
13270
|
|
|
12936
13271
|
// src/flow-query-index-contract.ts
|
|
12937
|
-
import { Buffer as
|
|
13272
|
+
import { Buffer as Buffer51 } from "buffer";
|
|
12938
13273
|
var FLOW_QUERY_BUILD_PHASES = ["pending", "snapshot", "backfill", "done"];
|
|
12939
13274
|
var FLOW_QUERY_VALIDATION_PHASES = [
|
|
12940
13275
|
"pending",
|
|
@@ -13180,10 +13515,10 @@ function fieldKind(name) {
|
|
|
13180
13515
|
return void 0;
|
|
13181
13516
|
}
|
|
13182
13517
|
function validUnquoted(value) {
|
|
13183
|
-
return !value.startsWith("__") && UNQUOTED_METADATA.test(value) &&
|
|
13518
|
+
return !value.startsWith("__") && UNQUOTED_METADATA.test(value) && Buffer51.byteLength(value, "ascii") <= 64;
|
|
13184
13519
|
}
|
|
13185
13520
|
function validMetadata(value, rejectReserved) {
|
|
13186
|
-
return value.length > 0 &&
|
|
13521
|
+
return value.length > 0 && Buffer51.byteLength(value, "utf8") <= 64 && (!rejectReserved || !value.startsWith("__"));
|
|
13187
13522
|
}
|
|
13188
13523
|
function externalSelector(root, ...segments) {
|
|
13189
13524
|
return segments.every(validUnquoted) ? [root, ...segments].join(".") : root + segments.map((segment) => `['${segment.replaceAll("'", "''")}']`).join("");
|
|
@@ -14090,7 +14425,7 @@ function decodePage(value) {
|
|
|
14090
14425
|
const mapping2 = requiredMap2(value, "FLOW.QUERY page");
|
|
14091
14426
|
const hasMore = requiredBoolean(mapping2, "has_more", "FLOW.QUERY page");
|
|
14092
14427
|
const cursor = optionalText2(mapping2, "cursor", "FLOW.QUERY page");
|
|
14093
|
-
if (cursor != null && (!cursor.startsWith("fqc1_") ||
|
|
14428
|
+
if (cursor != null && (!cursor.startsWith("fqc1_") || Buffer52.byteLength(cursor) < 16 || Buffer52.byteLength(cursor) > 4096)) {
|
|
14094
14429
|
throw decodeError("FLOW.QUERY page cursor is invalid", value);
|
|
14095
14430
|
}
|
|
14096
14431
|
if (hasMore !== (cursor != null)) {
|
|
@@ -14103,9 +14438,9 @@ function decodePage(value) {
|
|
|
14103
14438
|
import "buffer";
|
|
14104
14439
|
|
|
14105
14440
|
// src/client-core-helpers.ts
|
|
14106
|
-
import { Buffer as
|
|
14441
|
+
import { Buffer as Buffer53 } from "buffer";
|
|
14107
14442
|
function bgsaveResponse(response) {
|
|
14108
|
-
if ((typeof response === "string" ||
|
|
14443
|
+
if ((typeof response === "string" || Buffer53.isBuffer(response) || response instanceof Uint8Array) && text(response) === "Background saving started") {
|
|
14109
14444
|
return true;
|
|
14110
14445
|
}
|
|
14111
14446
|
return okResponse(response);
|
|
@@ -14119,7 +14454,7 @@ function fetchOrComputeCompletionToken(options) {
|
|
|
14119
14454
|
"fetch-or-compute completion requires computeToken"
|
|
14120
14455
|
);
|
|
14121
14456
|
}
|
|
14122
|
-
if (!
|
|
14457
|
+
if (!Buffer53.isBuffer(options.computeToken)) {
|
|
14123
14458
|
throw new TypeError("fetch-or-compute computeToken must be a Buffer");
|
|
14124
14459
|
}
|
|
14125
14460
|
return options.computeToken;
|
|
@@ -14486,14 +14821,14 @@ var FerricStoreAdministrationClient = class extends FerricStoreClientBase {
|
|
|
14486
14821
|
};
|
|
14487
14822
|
|
|
14488
14823
|
// src/store-utilities.ts
|
|
14489
|
-
import { Buffer as
|
|
14824
|
+
import { Buffer as Buffer56 } from "buffer";
|
|
14490
14825
|
function encode(codec, value) {
|
|
14491
14826
|
return codec.encode(value);
|
|
14492
14827
|
}
|
|
14493
14828
|
function decode(codec, value) {
|
|
14494
14829
|
if (value == null) return null;
|
|
14495
|
-
if (
|
|
14496
|
-
if (value instanceof Uint8Array) return codec.decode(
|
|
14830
|
+
if (Buffer56.isBuffer(value)) return codec.decode(value);
|
|
14831
|
+
if (value instanceof Uint8Array) return codec.decode(Buffer56.from(value));
|
|
14497
14832
|
return value;
|
|
14498
14833
|
}
|
|
14499
14834
|
function number(value) {
|
|
@@ -17349,7 +17684,7 @@ function throwIfClosed(signal) {
|
|
|
17349
17684
|
}
|
|
17350
17685
|
|
|
17351
17686
|
// src/flow-policy.ts
|
|
17352
|
-
import { Buffer as
|
|
17687
|
+
import { Buffer as Buffer58 } from "buffer";
|
|
17353
17688
|
var MAX_FLOW_POLICY_GENERATION = Number.MAX_SAFE_INTEGER;
|
|
17354
17689
|
function assertFlowPolicyGeneration(value) {
|
|
17355
17690
|
if (typeof value !== "number" || !Number.isSafeInteger(value) || value < 0) {
|
|
@@ -17439,7 +17774,7 @@ function requiredRecord(value, context) {
|
|
|
17439
17774
|
}
|
|
17440
17775
|
return result;
|
|
17441
17776
|
}
|
|
17442
|
-
if (typeof value === "object" && value != null && !Array.isArray(value) && !
|
|
17777
|
+
if (typeof value === "object" && value != null && !Array.isArray(value) && !Buffer58.isBuffer(value) && !(value instanceof Uint8Array)) return value;
|
|
17443
17778
|
throw new TypeError(`${context} returned an unexpected response`);
|
|
17444
17779
|
}
|
|
17445
17780
|
function optionalRecord(value, context) {
|
|
@@ -17460,8 +17795,8 @@ function stringArray(value, context) {
|
|
|
17460
17795
|
}
|
|
17461
17796
|
function requiredText4(value, context) {
|
|
17462
17797
|
if (typeof value === "string") return value;
|
|
17463
|
-
if (
|
|
17464
|
-
return
|
|
17798
|
+
if (Buffer58.isBuffer(value) || value instanceof Uint8Array) {
|
|
17799
|
+
return Buffer58.from(value).toString("utf8");
|
|
17465
17800
|
}
|
|
17466
17801
|
throw new TypeError(`FLOW policy ${context} returned an unexpected response`);
|
|
17467
17802
|
}
|
|
@@ -17717,7 +18052,7 @@ var FerricStoreFlowSupportClient = class extends FerricStoreFlowQueryClient {
|
|
|
17717
18052
|
};
|
|
17718
18053
|
|
|
17719
18054
|
// src/flow-many-snapshot.ts
|
|
17720
|
-
import { Buffer as
|
|
18055
|
+
import { Buffer as Buffer60 } from "buffer";
|
|
17721
18056
|
var encodedOptionFields = ["error", "payload", "reason", "result"];
|
|
17722
18057
|
function snapshotCreateItem(item, codec) {
|
|
17723
18058
|
const snapshot = {
|
|
@@ -17757,7 +18092,7 @@ function snapshotFlowManyOptions(options, codec) {
|
|
|
17757
18092
|
}
|
|
17758
18093
|
function snapshotClaimedItem(item) {
|
|
17759
18094
|
const wire = item[CLAIMED_ITEM_WIRE];
|
|
17760
|
-
const leaseToken =
|
|
18095
|
+
const leaseToken = Buffer60.from(wire?.leaseToken ?? item.leaseToken);
|
|
17761
18096
|
const snapshot = {
|
|
17762
18097
|
...item,
|
|
17763
18098
|
fencingToken: wire?.fencingToken ?? item.fencingToken,
|
|
@@ -17774,15 +18109,15 @@ function snapshotClaimedItem(item) {
|
|
|
17774
18109
|
function snapshotFencedItem(item) {
|
|
17775
18110
|
return Object.freeze({
|
|
17776
18111
|
...item,
|
|
17777
|
-
...item.leaseToken == null ? {} : { leaseToken:
|
|
18112
|
+
...item.leaseToken == null ? {} : { leaseToken: Buffer60.from(item.leaseToken) }
|
|
17778
18113
|
});
|
|
17779
18114
|
}
|
|
17780
18115
|
function snapshotClaimedItemWire(wire, leaseToken) {
|
|
17781
18116
|
return Object.freeze({
|
|
17782
18117
|
fencingToken: wire.fencingToken,
|
|
17783
|
-
id:
|
|
18118
|
+
id: Buffer60.from(wire.id),
|
|
17784
18119
|
leaseToken,
|
|
17785
|
-
partitionKey: wire.partitionKey == null ? wire.partitionKey :
|
|
18120
|
+
partitionKey: wire.partitionKey == null ? wire.partitionKey : Buffer60.from(wire.partitionKey)
|
|
17786
18121
|
});
|
|
17787
18122
|
}
|
|
17788
18123
|
function snapshotArray(values) {
|
|
@@ -17793,7 +18128,7 @@ function snapshotArray(values) {
|
|
|
17793
18128
|
return Object.freeze(snapshot);
|
|
17794
18129
|
}
|
|
17795
18130
|
function snapshotStateMeta(stateMeta) {
|
|
17796
|
-
return snapshotRecord(stateMeta, (value) =>
|
|
18131
|
+
return snapshotRecord(stateMeta, (value) => Buffer60.isBuffer(value) ? Buffer60.from(value) : value);
|
|
17797
18132
|
}
|
|
17798
18133
|
function snapshotCommandRecord(values) {
|
|
17799
18134
|
const seen = /* @__PURE__ */ new WeakMap();
|
|
@@ -17811,7 +18146,7 @@ function snapshotRecord(values, capture) {
|
|
|
17811
18146
|
}
|
|
17812
18147
|
function snapshotCommandArgument(value, seen) {
|
|
17813
18148
|
if (typeof value !== "object" || value == null) return value;
|
|
17814
|
-
if (
|
|
18149
|
+
if (Buffer60.isBuffer(value) || value instanceof Uint8Array) return Buffer60.from(value);
|
|
17815
18150
|
const objectValue = value;
|
|
17816
18151
|
const existing = seen.get(objectValue);
|
|
17817
18152
|
if (existing != null) return existing;
|
|
@@ -18807,7 +19142,7 @@ function nativeOptionsForBootstrap(options, signal) {
|
|
|
18807
19142
|
}
|
|
18808
19143
|
|
|
18809
19144
|
// src/flow-query-projection.ts
|
|
18810
|
-
import { Buffer as
|
|
19145
|
+
import { Buffer as Buffer61 } from "buffer";
|
|
18811
19146
|
var MAX_PROJECTION_FIELDS = 32;
|
|
18812
19147
|
var MAX_DYNAMIC_NAME_BYTES = 64;
|
|
18813
19148
|
var FIELD_BRAND = /* @__PURE__ */ Symbol("FerricStoreFlowProjectionField");
|
|
@@ -18877,7 +19212,7 @@ function projectFlowQuery(query, shape, ...fields) {
|
|
|
18877
19212
|
}
|
|
18878
19213
|
const base = stripOptionalTerminator(query);
|
|
18879
19214
|
const result = `${base} RETURN ${shape.toUpperCase()} (${selectors.join(", ")})`;
|
|
18880
|
-
if (
|
|
19215
|
+
if (Buffer61.byteLength(result, "utf8") > FLOW_QUERY_MAX_BYTES) {
|
|
18881
19216
|
throw new TypeError(`FLOW.QUERY query exceeds ${FLOW_QUERY_MAX_BYTES} bytes`);
|
|
18882
19217
|
}
|
|
18883
19218
|
return result;
|
|
@@ -18937,7 +19272,7 @@ function quoteName(value, allowPrivate) {
|
|
|
18937
19272
|
throw new TypeError("Flow query projection metadata name must be text");
|
|
18938
19273
|
}
|
|
18939
19274
|
validateUnicodeScalarText2(value);
|
|
18940
|
-
const size =
|
|
19275
|
+
const size = Buffer61.byteLength(value, "utf8");
|
|
18941
19276
|
if (size === 0 || size > MAX_DYNAMIC_NAME_BYTES || !allowPrivate && value.startsWith("__")) {
|
|
18942
19277
|
throw new TypeError(
|
|
18943
19278
|
`Flow query projection metadata names must be 1..${MAX_DYNAMIC_NAME_BYTES} UTF-8 bytes`
|
|
@@ -20943,7 +21278,7 @@ var WorkflowWorker = class {
|
|
|
20943
21278
|
};
|
|
20944
21279
|
|
|
20945
21280
|
// src/version.ts
|
|
20946
|
-
var FERRICSTORE_SDK_VERSION = "0.11.
|
|
21281
|
+
var FERRICSTORE_SDK_VERSION = "0.11.11";
|
|
20947
21282
|
var FERRICSTORE_MINIMUM_SERVER_VERSION = "0.11.4";
|
|
20948
21283
|
var FERRICSTORE_NATIVE_PROTOCOL_VERSION = 1;
|
|
20949
21284
|
export {
|