@ferricstore/ferricstore 0.1.7 → 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 +17 -5
- package/dist/index.cjs +869 -548
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +29 -30
- package/dist/index.d.ts +29 -30
- package/dist/index.js +856 -537
- package/dist/index.js.map +1 -1
- package/docs/api/assets/hierarchy.js +1 -1
- package/docs/api/assets/navigation.js +1 -1
- package/docs/api/assets/search.js +1 -1
- package/docs/api/classes/ClaimHydrationError.html +5 -2
- package/docs/api/classes/ConnectionClosedError.html +6 -3
- package/docs/api/classes/FerricStoreClient.html +4 -4
- package/docs/api/classes/FerricStoreError.html +6 -3
- package/docs/api/classes/FlowAlreadyExistsError.html +6 -3
- package/docs/api/classes/FlowBatchError.html +6 -3
- package/docs/api/classes/FlowNotFoundError.html +6 -3
- package/docs/api/classes/FlowWrongStateError.html +6 -3
- package/docs/api/classes/InvalidCommandError.html +6 -3
- package/docs/api/classes/KeyValueStore.html +2 -2
- package/docs/api/classes/LeaseRenewalError.html +1 -1
- package/docs/api/classes/LockHeldError.html +6 -3
- package/docs/api/classes/LockNotOwnedError.html +6 -3
- package/docs/api/classes/NativeAdapter.html +2 -2
- package/docs/api/classes/OverloadedError.html +6 -4
- package/docs/api/classes/QueueCompletionError.html +1 -1
- package/docs/api/classes/RequestTimeoutError.html +6 -3
- package/docs/api/classes/RerouteError.html +6 -3
- package/docs/api/classes/StaleLeaseError.html +6 -3
- package/docs/api/classes/TDigestStore.html +2 -2
- package/docs/api/classes/TopKStore.html +1 -1
- package/docs/api/classes/TopologyNativeAdapterPool.html +1 -1
- package/docs/api/classes/Workflow.html +1 -1
- package/docs/api/functions/classifyServerError.html +1 -1
- package/docs/api/functions/mapException.html +1 -1
- package/docs/api/hierarchy.html +1 -1
- package/docs/api/index.html +16 -6
- package/docs/api/interfaces/AdminListOptions.html +1 -1
- package/docs/api/interfaces/CancelOptions.html +2 -2
- package/docs/api/interfaces/ClaimDueOptions.html +3 -3
- package/docs/api/interfaces/CompleteJobsAndClaimJobsResult.html +6 -6
- package/docs/api/interfaces/CompleteManyOptions.html +2 -2
- package/docs/api/interfaces/CompleteOptions.html +2 -2
- package/docs/api/interfaces/CompleteOutcome.html +1 -1
- package/docs/api/interfaces/CreateManyOptions.html +1 -1
- package/docs/api/interfaces/EffectCompensateOptions.html +1 -1
- package/docs/api/interfaces/EffectConfirmOptions.html +1 -1
- package/docs/api/interfaces/EffectFailOptions.html +1 -1
- package/docs/api/interfaces/EffectStatusOptions.html +1 -1
- package/docs/api/interfaces/ExtendLeaseOptions.html +2 -2
- package/docs/api/interfaces/FailOptions.html +2 -2
- package/docs/api/interfaces/FailOutcome.html +1 -1
- package/docs/api/interfaces/FerricStoreClientFromUrlOptions.html +1 -1
- package/docs/api/interfaces/FerricStoreClientOptions.html +1 -1
- package/docs/api/interfaces/{FetchOrComputeLegacyResult.html → FetchOrComputeComputeResult.html} +2 -2
- package/docs/api/interfaces/FlowMaxActiveFailure.html +3 -0
- package/docs/api/interfaces/FlowPolicyOptions.html +3 -3
- package/docs/api/interfaces/FlowRecord.html +4 -2
- package/docs/api/interfaces/FlowStatePolicy.html +2 -2
- package/docs/api/interfaces/HistoryOptions.html +2 -2
- package/docs/api/interfaces/InvocationCreateOptions.html +2 -2
- package/docs/api/interfaces/LeaseMutationOptions.html +2 -2
- package/docs/api/interfaces/LimitListOptions.html +1 -1
- package/docs/api/interfaces/MutateOptions.html +2 -2
- package/docs/api/interfaces/NamedValueMutation.html +1 -1
- package/docs/api/interfaces/ProtocolCommand.html +2 -2
- package/docs/api/interfaces/ReadOptions.html +2 -2
- package/docs/api/interfaces/ReclaimOptions.html +2 -2
- package/docs/api/interfaces/RequestContext.html +2 -2
- package/docs/api/interfaces/RequestContextOptions.html +2 -2
- package/docs/api/interfaces/RetryOptions.html +2 -2
- package/docs/api/interfaces/RetryOutcome.html +1 -1
- package/docs/api/interfaces/RunStepsItem.html +2 -2
- package/docs/api/interfaces/RunStepsManyOptions.html +2 -2
- package/docs/api/interfaces/SearchOptions.html +2 -2
- package/docs/api/interfaces/StartAndClaimOptions.html +4 -2
- package/docs/api/interfaces/StepContinueOptions.html +3 -3
- package/docs/api/interfaces/TDigestCreateOptions.html +1 -1
- package/docs/api/interfaces/TDigestMergeOptions.html +1 -1
- package/docs/api/interfaces/TransitionOptions.html +2 -2
- package/docs/api/interfaces/TransitionOutcome.html +1 -1
- package/docs/api/modules.html +1 -1
- package/docs/api/types/FetchOrComputeFencedResult.html +1 -0
- package/docs/api/types/FetchOrComputeResult.html +1 -1
- package/docs/api/types/FlowStateMode.html +1 -1
- package/docs/api/types/FlowStatePolicyLike.html +1 -1
- package/docs/api/types/ManagementPairs.html +1 -1
- package/docs/api/types/RequestDisposition.html +1 -1
- package/docs/api/types/SearchStateMeta.html +1 -1
- package/docs/api/types/TopKReserveOptions.html +1 -1
- package/docs/api/variables/COMMAND_OPCODES.html +1 -1
- package/docs/api/variables/FERRICSTORE_MINIMUM_SERVER_VERSION.html +2 -0
- package/docs/api/variables/FERRICSTORE_NATIVE_PROTOCOL_VERSION.html +2 -0
- package/docs/api/variables/FERRICSTORE_SDK_VERSION.html +2 -0
- package/package.json +6 -1
- package/docs/api/interfaces/FetchOrComputeFencedResult.html +0 -9
- package/docs/api/types/FetchOrComputeComputeResult.html +0 -1
- package/docs/api/variables/COMPACT_RESPONSE_OPCODES.html +0 -2
package/dist/index.cjs
CHANGED
|
@@ -33,11 +33,13 @@ __export(index_exports, {
|
|
|
33
33
|
BitmapStore: () => BitmapStore,
|
|
34
34
|
BloomFilterStore: () => BloomFilterStore,
|
|
35
35
|
COMMAND_OPCODES: () => COMMAND_OPCODES,
|
|
36
|
-
COMPACT_RESPONSE_OPCODES: () => COMPACT_RESPONSE_OPCODES,
|
|
37
36
|
ClaimHydrationError: () => ClaimHydrationError,
|
|
38
37
|
ConnectionClosedError: () => ConnectionClosedError,
|
|
39
38
|
CountMinSketchStore: () => CountMinSketchStore,
|
|
40
39
|
CuckooFilterStore: () => CuckooFilterStore,
|
|
40
|
+
FERRICSTORE_MINIMUM_SERVER_VERSION: () => FERRICSTORE_MINIMUM_SERVER_VERSION,
|
|
41
|
+
FERRICSTORE_NATIVE_PROTOCOL_VERSION: () => FERRICSTORE_NATIVE_PROTOCOL_VERSION,
|
|
42
|
+
FERRICSTORE_SDK_VERSION: () => FERRICSTORE_SDK_VERSION,
|
|
41
43
|
FerricStoreClient: () => FerricStoreClient,
|
|
42
44
|
FerricStoreError: () => FerricStoreError,
|
|
43
45
|
FlowAlreadyExistsError: () => FlowAlreadyExistsError,
|
|
@@ -100,16 +102,22 @@ function assertSafeVariadicDispatch(argumentCount, arrayCapability) {
|
|
|
100
102
|
// src/native-adapter.ts
|
|
101
103
|
var import_node_net3 = require("net");
|
|
102
104
|
var import_node_tls3 = require("tls");
|
|
103
|
-
var
|
|
105
|
+
var import_node_buffer25 = require("buffer");
|
|
104
106
|
|
|
105
107
|
// src/errors.ts
|
|
106
108
|
var FerricStoreError = class extends Error {
|
|
107
109
|
code = "ferricstore_error";
|
|
108
110
|
raw;
|
|
111
|
+
retryable;
|
|
112
|
+
safeToRetry;
|
|
113
|
+
retryAfterMs;
|
|
109
114
|
constructor(message, options = {}) {
|
|
110
115
|
super(message, { cause: options.cause });
|
|
111
116
|
this.name = new.target.name;
|
|
112
117
|
this.raw = options.raw;
|
|
118
|
+
this.retryable = options.retryable ?? structuredBooleanField(options.raw, "retryable");
|
|
119
|
+
this.safeToRetry = options.safeToRetry ?? structuredBooleanField(options.raw, "safe_to_retry");
|
|
120
|
+
this.retryAfterMs = options.retryAfterMs ?? structuredIntegerField(options.raw, "retry_after_ms");
|
|
113
121
|
}
|
|
114
122
|
};
|
|
115
123
|
var ConnectionClosedError = class extends FerricStoreError {
|
|
@@ -156,11 +164,14 @@ var InvalidCommandError = class extends FerricStoreError {
|
|
|
156
164
|
};
|
|
157
165
|
var OverloadedError = class extends FerricStoreError {
|
|
158
166
|
code = "overloaded";
|
|
159
|
-
retryAfterMs;
|
|
160
167
|
reason;
|
|
161
168
|
constructor(message, options = {}) {
|
|
162
|
-
|
|
163
|
-
|
|
169
|
+
const local = options.raw == null;
|
|
170
|
+
super(message, {
|
|
171
|
+
...options,
|
|
172
|
+
retryable: options.retryable ?? (local ? true : void 0),
|
|
173
|
+
safeToRetry: options.safeToRetry ?? (local ? true : void 0)
|
|
174
|
+
});
|
|
164
175
|
this.reason = options.reason;
|
|
165
176
|
}
|
|
166
177
|
};
|
|
@@ -178,15 +189,21 @@ function classifyServerError(message, raw, cause, status) {
|
|
|
178
189
|
const lower = message.toLowerCase();
|
|
179
190
|
const structuredCode = structuredStringField(raw, "code");
|
|
180
191
|
const code = structuredCode?.toLowerCase();
|
|
192
|
+
const retry2 = {
|
|
193
|
+
retryable: structuredBooleanField(raw, "retryable"),
|
|
194
|
+
safeToRetry: structuredBooleanField(raw, "safe_to_retry"),
|
|
195
|
+
retryAfterMs: structuredIntegerField(raw, "retry_after_ms") ?? intField(lower, "retry_after_ms")
|
|
196
|
+
};
|
|
181
197
|
if (isRerouteStatus(status) || code === "reroute") {
|
|
182
|
-
return new RerouteError(message, { cause, raw });
|
|
198
|
+
return new RerouteError(message, { cause, raw, ...definedRetryMetadata(retry2) });
|
|
183
199
|
}
|
|
184
200
|
if (isBusyStatus(status) || isOverloadCode(structuredCode) || overloadMessage(lower)) {
|
|
185
201
|
return new OverloadedError(message, {
|
|
186
202
|
cause,
|
|
187
203
|
raw,
|
|
204
|
+
...definedRetryMetadata(retry2),
|
|
188
205
|
reason: structuredStringField(raw, "reason") ?? structuredCode ?? stringField(lower, "reason"),
|
|
189
|
-
retryAfterMs:
|
|
206
|
+
retryAfterMs: retry2.retryAfterMs
|
|
190
207
|
});
|
|
191
208
|
}
|
|
192
209
|
if (code === "flow_already_exists" || lower.includes("flow") && lower.includes("already exists")) {
|
|
@@ -210,7 +227,7 @@ function classifyServerError(message, raw, cause, status) {
|
|
|
210
227
|
if (code === "invalid_command" || lower.includes("wrong number of arguments") || lower.includes("syntax error")) {
|
|
211
228
|
return new InvalidCommandError(message, { cause, raw });
|
|
212
229
|
}
|
|
213
|
-
return new FerricStoreError(message, { cause, raw });
|
|
230
|
+
return new FerricStoreError(message, { cause, raw, ...definedRetryMetadata(retry2) });
|
|
214
231
|
}
|
|
215
232
|
function mapException(error) {
|
|
216
233
|
if (error instanceof FerricStoreError) {
|
|
@@ -250,8 +267,23 @@ function structuredIntegerField(raw, name) {
|
|
|
250
267
|
if (typeof value === "bigint") {
|
|
251
268
|
return value >= 0n && value <= BigInt(Number.MAX_SAFE_INTEGER) ? Number(value) : void 0;
|
|
252
269
|
}
|
|
253
|
-
const
|
|
254
|
-
return
|
|
270
|
+
const text3 = binaryText(value);
|
|
271
|
+
return text3 == null ? void 0 : nonNegativeSafeIntegerText(text3);
|
|
272
|
+
}
|
|
273
|
+
function structuredBooleanField(raw, name) {
|
|
274
|
+
const value = structuredField(raw, name);
|
|
275
|
+
if (typeof value === "boolean") return value;
|
|
276
|
+
const text3 = binaryText(value)?.toLowerCase();
|
|
277
|
+
if (text3 === "true" || text3 === "1") return true;
|
|
278
|
+
if (text3 === "false" || text3 === "0") return false;
|
|
279
|
+
return void 0;
|
|
280
|
+
}
|
|
281
|
+
function definedRetryMetadata(metadata) {
|
|
282
|
+
return {
|
|
283
|
+
...metadata.retryable == null ? {} : { retryable: metadata.retryable },
|
|
284
|
+
...metadata.safeToRetry == null ? {} : { safeToRetry: metadata.safeToRetry },
|
|
285
|
+
...metadata.retryAfterMs == null ? {} : { retryAfterMs: metadata.retryAfterMs }
|
|
286
|
+
};
|
|
255
287
|
}
|
|
256
288
|
function nonNegativeSafeIntegerText(value) {
|
|
257
289
|
if (!/^[0-9]+$/u.test(value)) return void 0;
|
|
@@ -424,9 +456,6 @@ function mapDenseResponseArray(value, transform) {
|
|
|
424
456
|
return result;
|
|
425
457
|
}
|
|
426
458
|
|
|
427
|
-
// src/auto-partition.ts
|
|
428
|
-
var import_node_buffer2 = require("buffer");
|
|
429
|
-
|
|
430
459
|
// src/crc32.ts
|
|
431
460
|
var import_node_buffer = require("buffer");
|
|
432
461
|
var table = new Uint32Array(256);
|
|
@@ -444,12 +473,49 @@ function crc32(buffer) {
|
|
|
444
473
|
}
|
|
445
474
|
return (value ^ 4294967295) >>> 0;
|
|
446
475
|
}
|
|
476
|
+
function crc32Utf8(text3, start = 0, end = text3.length) {
|
|
477
|
+
let value = 4294967295;
|
|
478
|
+
for (let index = start; index < end; index += 1) {
|
|
479
|
+
const first = text3.charCodeAt(index);
|
|
480
|
+
let point = first;
|
|
481
|
+
if (first >= 55296 && first <= 56319) {
|
|
482
|
+
const second = index + 1 < end ? text3.charCodeAt(index + 1) : 0;
|
|
483
|
+
if (second >= 56320 && second <= 57343) {
|
|
484
|
+
point = 65536 + (first - 55296 << 10) + second - 56320;
|
|
485
|
+
index += 1;
|
|
486
|
+
} else {
|
|
487
|
+
point = 65533;
|
|
488
|
+
}
|
|
489
|
+
} else if (first >= 56320 && first <= 57343) {
|
|
490
|
+
point = 65533;
|
|
491
|
+
}
|
|
492
|
+
if (point < 128) {
|
|
493
|
+
value = updateCrc32(value, point);
|
|
494
|
+
} else if (point < 2048) {
|
|
495
|
+
value = updateCrc32(value, 192 | point >>> 6);
|
|
496
|
+
value = updateCrc32(value, 128 | point & 63);
|
|
497
|
+
} else if (point < 65536) {
|
|
498
|
+
value = updateCrc32(value, 224 | point >>> 12);
|
|
499
|
+
value = updateCrc32(value, 128 | point >>> 6 & 63);
|
|
500
|
+
value = updateCrc32(value, 128 | point & 63);
|
|
501
|
+
} else {
|
|
502
|
+
value = updateCrc32(value, 240 | point >>> 18);
|
|
503
|
+
value = updateCrc32(value, 128 | point >>> 12 & 63);
|
|
504
|
+
value = updateCrc32(value, 128 | point >>> 6 & 63);
|
|
505
|
+
value = updateCrc32(value, 128 | point & 63);
|
|
506
|
+
}
|
|
507
|
+
}
|
|
508
|
+
return (value ^ 4294967295) >>> 0;
|
|
509
|
+
}
|
|
510
|
+
function updateCrc32(value, byte) {
|
|
511
|
+
return value >>> 8 ^ (table[(value ^ byte) & 255] ?? 0);
|
|
512
|
+
}
|
|
447
513
|
|
|
448
514
|
// src/auto-partition.ts
|
|
449
515
|
var AUTO_PARTITION_PREFIX = "__flow_auto__:";
|
|
450
516
|
var AUTO_PARTITION_BUCKETS = 256;
|
|
451
517
|
function autoPartitionKeyForId(id) {
|
|
452
|
-
return `${AUTO_PARTITION_PREFIX}${
|
|
518
|
+
return `${AUTO_PARTITION_PREFIX}${crc32Utf8(id) % AUTO_PARTITION_BUCKETS}`;
|
|
453
519
|
}
|
|
454
520
|
|
|
455
521
|
// src/flow-argument-helpers.ts
|
|
@@ -842,7 +908,7 @@ function coerceDiagnosticValue(value) {
|
|
|
842
908
|
// src/native-connection.ts
|
|
843
909
|
var import_node_net = __toESM(require("net"), 1);
|
|
844
910
|
var import_node_tls = __toESM(require("tls"), 1);
|
|
845
|
-
var
|
|
911
|
+
var import_node_buffer2 = require("buffer");
|
|
846
912
|
function parseFerricUrl(value) {
|
|
847
913
|
const url = new URL(value);
|
|
848
914
|
if (url.protocol !== "ferric:" && url.protocol !== "ferrics:") {
|
|
@@ -968,7 +1034,7 @@ function nonNegativeSafeInteger(value) {
|
|
|
968
1034
|
if (typeof value === "bigint") {
|
|
969
1035
|
return value >= 0n && value <= BigInt(Number.MAX_SAFE_INTEGER) ? Number(value) : void 0;
|
|
970
1036
|
}
|
|
971
|
-
const source =
|
|
1037
|
+
const source = import_node_buffer2.Buffer.isBuffer(value) || value instanceof Uint8Array ? import_node_buffer2.Buffer.from(value).toString("utf8") : value;
|
|
972
1038
|
if (typeof source !== "number" && (typeof source !== "string" || !/^\d+$/u.test(source))) {
|
|
973
1039
|
return void 0;
|
|
974
1040
|
}
|
|
@@ -1202,10 +1268,10 @@ var NativeHeartbeat = class {
|
|
|
1202
1268
|
};
|
|
1203
1269
|
|
|
1204
1270
|
// src/protocol.ts
|
|
1205
|
-
var
|
|
1271
|
+
var import_node_buffer21 = require("buffer");
|
|
1206
1272
|
|
|
1207
1273
|
// src/command-grammar.ts
|
|
1208
|
-
var
|
|
1274
|
+
var import_node_buffer3 = require("buffer");
|
|
1209
1275
|
|
|
1210
1276
|
// src/command-metadata-flow.ts
|
|
1211
1277
|
var flowStateIdCommands = /* @__PURE__ */ new Set([
|
|
@@ -1652,8 +1718,8 @@ var secondKeySubcommands = /* @__PURE__ */ new Map([
|
|
|
1652
1718
|
]);
|
|
1653
1719
|
function commandToken(value) {
|
|
1654
1720
|
if (typeof value === "string") return value.toUpperCase();
|
|
1655
|
-
if (
|
|
1656
|
-
return
|
|
1721
|
+
if (import_node_buffer3.Buffer.isBuffer(value) || value instanceof Uint8Array) {
|
|
1722
|
+
return import_node_buffer3.Buffer.from(value).toString("utf8").toUpperCase();
|
|
1657
1723
|
}
|
|
1658
1724
|
return void 0;
|
|
1659
1725
|
}
|
|
@@ -1756,7 +1822,7 @@ function safeIntegerArgument(value) {
|
|
|
1756
1822
|
if (typeof value === "bigint") {
|
|
1757
1823
|
return value >= BigInt(Number.MIN_SAFE_INTEGER) && value <= BigInt(Number.MAX_SAFE_INTEGER) ? Number(value) : void 0;
|
|
1758
1824
|
}
|
|
1759
|
-
const source = typeof value === "string" ? value :
|
|
1825
|
+
const source = typeof value === "string" ? value : import_node_buffer3.Buffer.isBuffer(value) || value instanceof Uint8Array ? import_node_buffer3.Buffer.from(value).toString("utf8") : void 0;
|
|
1760
1826
|
if (source == null || !/^[+-]?\d+$/u.test(source)) return void 0;
|
|
1761
1827
|
const parsed = BigInt(source);
|
|
1762
1828
|
return parsed >= BigInt(Number.MIN_SAFE_INTEGER) && parsed <= BigInt(Number.MAX_SAFE_INTEGER) ? Number(parsed) : void 0;
|
|
@@ -1809,10 +1875,10 @@ function hasOwnCommandArgument(args, index, end, section) {
|
|
|
1809
1875
|
}
|
|
1810
1876
|
|
|
1811
1877
|
// src/protocol-core.ts
|
|
1812
|
-
var
|
|
1878
|
+
var import_node_buffer7 = require("buffer");
|
|
1813
1879
|
|
|
1814
1880
|
// src/protocol-constants.ts
|
|
1815
|
-
var
|
|
1881
|
+
var import_node_buffer4 = require("buffer");
|
|
1816
1882
|
|
|
1817
1883
|
// src/native-protocol-manifest.json
|
|
1818
1884
|
var native_protocol_manifest_default = {
|
|
@@ -2017,6 +2083,7 @@ var OPCODES = {
|
|
|
2017
2083
|
flowFail: COMMAND_OPCODES["FLOW.FAIL"],
|
|
2018
2084
|
flowValuePut: COMMAND_OPCODES["FLOW.VALUE.PUT"],
|
|
2019
2085
|
flowValueMGet: COMMAND_OPCODES["FLOW.VALUE.MGET"],
|
|
2086
|
+
flowSignal: COMMAND_OPCODES["FLOW.SIGNAL"],
|
|
2020
2087
|
flowCreateMany: COMMAND_OPCODES["FLOW.CREATE_MANY"],
|
|
2021
2088
|
flowCompleteMany: COMMAND_OPCODES["FLOW.COMPLETE_MANY"],
|
|
2022
2089
|
flowTransitionMany: COMMAND_OPCODES["FLOW.TRANSITION_MANY"],
|
|
@@ -2029,68 +2096,15 @@ var OPCODES = {
|
|
|
2029
2096
|
flowRunStepsMany: COMMAND_OPCODES["FLOW.RUN_STEPS_MANY"],
|
|
2030
2097
|
flowSearch: COMMAND_OPCODES["FLOW.SEARCH"]
|
|
2031
2098
|
};
|
|
2032
|
-
var COMPACT_RESPONSE_OPCODES = {
|
|
2033
|
-
flow_claim_jobs_v1: [COMMAND_OPCODES["FLOW.CLAIM_DUE"]],
|
|
2034
|
-
flow_record_list_v1: [
|
|
2035
|
-
COMMAND_OPCODES["FLOW.LIST"],
|
|
2036
|
-
COMMAND_OPCODES["FLOW.TERMINALS"],
|
|
2037
|
-
COMMAND_OPCODES["FLOW.FAILURES"],
|
|
2038
|
-
COMMAND_OPCODES["FLOW.BY_PARENT"],
|
|
2039
|
-
COMMAND_OPCODES["FLOW.BY_ROOT"],
|
|
2040
|
-
COMMAND_OPCODES["FLOW.BY_CORRELATION"],
|
|
2041
|
-
COMMAND_OPCODES["FLOW.STUCK"]
|
|
2042
|
-
],
|
|
2043
|
-
flow_record_v1: [COMMAND_OPCODES["FLOW.GET"]],
|
|
2044
|
-
kv_get_v1: [COMMAND_OPCODES.GET],
|
|
2045
|
-
kv_mget_v1: [COMMAND_OPCODES.MGET, COMMAND_OPCODES["FLOW.VALUE.MGET"]],
|
|
2046
|
-
ok_list_v1: [
|
|
2047
|
-
COMMAND_OPCODES.SET,
|
|
2048
|
-
COMMAND_OPCODES.MSET,
|
|
2049
|
-
COMMAND_OPCODES["FLOW.CREATE_MANY"],
|
|
2050
|
-
COMMAND_OPCODES["FLOW.COMPLETE_MANY"],
|
|
2051
|
-
COMMAND_OPCODES["FLOW.RETRY_MANY"],
|
|
2052
|
-
COMMAND_OPCODES["FLOW.FAIL_MANY"],
|
|
2053
|
-
COMMAND_OPCODES["FLOW.CANCEL_MANY"]
|
|
2054
|
-
],
|
|
2055
|
-
pipeline_v1: [COMMAND_OPCODES.PIPELINE]
|
|
2056
|
-
};
|
|
2057
|
-
var COMPACT_KIND_FLOW_CLAIM_JOBS = 1 << 0;
|
|
2058
|
-
var COMPACT_KIND_FLOW_RECORD = 1 << 1;
|
|
2059
|
-
var COMPACT_KIND_FLOW_RECORD_LIST = 1 << 2;
|
|
2060
|
-
var COMPACT_KIND_KV_GET = 1 << 3;
|
|
2061
|
-
var COMPACT_KIND_KV_MGET = 1 << 4;
|
|
2062
|
-
var COMPACT_KIND_OK_LIST = 1 << 5;
|
|
2063
|
-
var COMPACT_KIND_PIPELINE = 1 << 6;
|
|
2064
|
-
var compactResponseOpcodeKinds = new Uint8Array(
|
|
2065
|
-
Math.max(...Object.values(COMPACT_RESPONSE_OPCODES).flat()) + 1
|
|
2066
|
-
);
|
|
2067
|
-
registerCompactResponseOpcodes(COMPACT_KIND_FLOW_CLAIM_JOBS, COMPACT_RESPONSE_OPCODES.flow_claim_jobs_v1);
|
|
2068
|
-
registerCompactResponseOpcodes(COMPACT_KIND_FLOW_RECORD, COMPACT_RESPONSE_OPCODES.flow_record_v1);
|
|
2069
|
-
registerCompactResponseOpcodes(COMPACT_KIND_FLOW_RECORD_LIST, COMPACT_RESPONSE_OPCODES.flow_record_list_v1);
|
|
2070
|
-
registerCompactResponseOpcodes(COMPACT_KIND_KV_GET, COMPACT_RESPONSE_OPCODES.kv_get_v1);
|
|
2071
|
-
registerCompactResponseOpcodes(COMPACT_KIND_KV_MGET, [
|
|
2072
|
-
...COMPACT_RESPONSE_OPCODES.kv_mget_v1,
|
|
2073
|
-
COMMAND_OPCODES.PIPELINE
|
|
2074
|
-
]);
|
|
2075
|
-
registerCompactResponseOpcodes(COMPACT_KIND_OK_LIST, [
|
|
2076
|
-
...COMPACT_RESPONSE_OPCODES.ok_list_v1,
|
|
2077
|
-
COMMAND_OPCODES.PIPELINE
|
|
2078
|
-
]);
|
|
2079
|
-
registerCompactResponseOpcodes(COMPACT_KIND_PIPELINE, COMPACT_RESPONSE_OPCODES.pipeline_v1);
|
|
2080
|
-
function registerCompactResponseOpcodes(kind, opcodes) {
|
|
2081
|
-
for (const opcode of opcodes) {
|
|
2082
|
-
compactResponseOpcodeKinds[opcode] = (compactResponseOpcodeKinds[opcode] ?? 0) | kind;
|
|
2083
|
-
}
|
|
2084
|
-
}
|
|
2085
|
-
function compactResponseOpcodeSupports(opcode, kind) {
|
|
2086
|
-
return ((compactResponseOpcodeKinds[opcode] ?? 0) & kind) !== 0;
|
|
2087
|
-
}
|
|
2088
2099
|
var COMPACT_FLOW_CLAIM_JOBS = 128;
|
|
2089
2100
|
var COMPACT_OK_LIST = 129;
|
|
2090
2101
|
var COMPACT_KV_GET = 130;
|
|
2091
2102
|
var COMPACT_KV_MGET = 131;
|
|
2092
2103
|
var COMPACT_FLOW_RECORD = 132;
|
|
2093
2104
|
var COMPACT_FLOW_RECORD_LIST = 133;
|
|
2105
|
+
var COMPACT_BINARY_LIST_LIST = 134;
|
|
2106
|
+
var COMPACT_BINARY_MAP_LIST = 135;
|
|
2107
|
+
var COMPACT_INTEGER_LIST = 136;
|
|
2094
2108
|
var COMPACT_KV_MGET_FIXED = 137;
|
|
2095
2109
|
var COMPACT_FLOW_CREATE_MANY_REQUEST = 144;
|
|
2096
2110
|
var COMPACT_FLOW_CLAIM_DUE_REQUEST = 145;
|
|
@@ -2160,16 +2174,16 @@ var FLOW_RECORD_FIELD_KEYS = [
|
|
|
2160
2174
|
];
|
|
2161
2175
|
|
|
2162
2176
|
// src/protocol-text.ts
|
|
2163
|
-
var
|
|
2177
|
+
var import_node_buffer5 = require("buffer");
|
|
2164
2178
|
function toBuffer(value) {
|
|
2165
|
-
if (
|
|
2166
|
-
if (value instanceof Uint8Array) return
|
|
2167
|
-
if (typeof value === "string") return
|
|
2179
|
+
if (import_node_buffer5.Buffer.isBuffer(value)) return value;
|
|
2180
|
+
if (value instanceof Uint8Array) return import_node_buffer5.Buffer.from(value);
|
|
2181
|
+
if (typeof value === "string") return import_node_buffer5.Buffer.from(value);
|
|
2168
2182
|
if (typeof value === "number" || typeof value === "bigint" || typeof value === "boolean") {
|
|
2169
|
-
return
|
|
2183
|
+
return import_node_buffer5.Buffer.from(String(value));
|
|
2170
2184
|
}
|
|
2171
|
-
if (typeof value === "symbol") return
|
|
2172
|
-
if (value == null) return
|
|
2185
|
+
if (typeof value === "symbol") return import_node_buffer5.Buffer.from(value.description ?? value.toString());
|
|
2186
|
+
if (value == null) return import_node_buffer5.Buffer.alloc(0);
|
|
2173
2187
|
throw new FerricStoreError(`unsupported binary command argument type: ${typeof value}`);
|
|
2174
2188
|
}
|
|
2175
2189
|
function asText(value) {
|
|
@@ -2177,14 +2191,14 @@ function asText(value) {
|
|
|
2177
2191
|
}
|
|
2178
2192
|
function optionalText(value) {
|
|
2179
2193
|
if (value == null || value === "") return void 0;
|
|
2180
|
-
if (typeof value === "string" || typeof value === "number" || typeof value === "bigint" || typeof value === "boolean" ||
|
|
2194
|
+
if (typeof value === "string" || typeof value === "number" || typeof value === "bigint" || typeof value === "boolean" || import_node_buffer5.Buffer.isBuffer(value) || value instanceof Uint8Array) {
|
|
2181
2195
|
return asText(value);
|
|
2182
2196
|
}
|
|
2183
2197
|
return void 0;
|
|
2184
2198
|
}
|
|
2185
2199
|
function commandTokenIs(value, expected) {
|
|
2186
2200
|
if (typeof value === "string") return value.toUpperCase() === expected;
|
|
2187
|
-
if (
|
|
2201
|
+
if (import_node_buffer5.Buffer.isBuffer(value) || value instanceof Uint8Array) {
|
|
2188
2202
|
return asText(value).toUpperCase() === expected;
|
|
2189
2203
|
}
|
|
2190
2204
|
return false;
|
|
@@ -2198,7 +2212,7 @@ function commandNameIs(value, expected) {
|
|
|
2198
2212
|
}
|
|
2199
2213
|
|
|
2200
2214
|
// src/request-context.ts
|
|
2201
|
-
var
|
|
2215
|
+
var import_node_buffer6 = require("buffer");
|
|
2202
2216
|
var requestContextCommands = /* @__PURE__ */ new Set([
|
|
2203
2217
|
"INVOCATION.CREATE",
|
|
2204
2218
|
"INVOCATION.DEFINITION.GET",
|
|
@@ -2253,9 +2267,9 @@ function requestContextCommandToken(value) {
|
|
|
2253
2267
|
const upper = value.toUpperCase();
|
|
2254
2268
|
return isRequestContextCommand(upper) ? upper : void 0;
|
|
2255
2269
|
}
|
|
2256
|
-
if (
|
|
2270
|
+
if (import_node_buffer6.Buffer.isBuffer(value) || value instanceof Uint8Array) {
|
|
2257
2271
|
if (value[0] !== 73 && value[0] !== 105) return void 0;
|
|
2258
|
-
const command =
|
|
2272
|
+
const command = import_node_buffer6.Buffer.from(value).toString("utf8").toUpperCase();
|
|
2259
2273
|
return isRequestContextCommand(command) ? command : void 0;
|
|
2260
2274
|
}
|
|
2261
2275
|
return void 0;
|
|
@@ -2286,12 +2300,12 @@ function requestContextText(context, fieldName) {
|
|
|
2286
2300
|
return value;
|
|
2287
2301
|
}
|
|
2288
2302
|
function isPlainObject(value) {
|
|
2289
|
-
return typeof value === "object" && value != null && !Array.isArray(value) && !
|
|
2303
|
+
return typeof value === "object" && value != null && !Array.isArray(value) && !import_node_buffer6.Buffer.isBuffer(value) && !(value instanceof Uint8Array);
|
|
2290
2304
|
}
|
|
2291
2305
|
function commandToken2(value) {
|
|
2292
2306
|
if (typeof value === "string") return value.toUpperCase();
|
|
2293
|
-
if (
|
|
2294
|
-
return
|
|
2307
|
+
if (import_node_buffer6.Buffer.isBuffer(value) || value instanceof Uint8Array) {
|
|
2308
|
+
return import_node_buffer6.Buffer.from(value).toString("utf8").toUpperCase();
|
|
2295
2309
|
}
|
|
2296
2310
|
return "";
|
|
2297
2311
|
}
|
|
@@ -2381,17 +2395,17 @@ function requestFrameTooLarge(maxBytes) {
|
|
|
2381
2395
|
);
|
|
2382
2396
|
}
|
|
2383
2397
|
function binaryValueByteLength(value) {
|
|
2384
|
-
if (
|
|
2385
|
-
if (typeof value === "string") return
|
|
2398
|
+
if (import_node_buffer7.Buffer.isBuffer(value) || value instanceof Uint8Array) return value.byteLength;
|
|
2399
|
+
if (typeof value === "string") return import_node_buffer7.Buffer.byteLength(value);
|
|
2386
2400
|
if (typeof value === "number" || typeof value === "bigint" || typeof value === "boolean") {
|
|
2387
|
-
return
|
|
2401
|
+
return import_node_buffer7.Buffer.byteLength(String(value));
|
|
2388
2402
|
}
|
|
2389
|
-
if (typeof value === "symbol") return
|
|
2403
|
+
if (typeof value === "symbol") return import_node_buffer7.Buffer.byteLength(value.description ?? value.toString());
|
|
2390
2404
|
if (value == null) return 0;
|
|
2391
2405
|
return toBuffer(value).byteLength;
|
|
2392
2406
|
}
|
|
2393
2407
|
function writeCustomPayload(output, offset, value, knownByteLength) {
|
|
2394
|
-
if (
|
|
2408
|
+
if (import_node_buffer7.Buffer.isBuffer(value)) {
|
|
2395
2409
|
value.copy(output, offset);
|
|
2396
2410
|
return;
|
|
2397
2411
|
}
|
|
@@ -2400,17 +2414,17 @@ function writeCustomPayload(output, offset, value, knownByteLength) {
|
|
|
2400
2414
|
return;
|
|
2401
2415
|
}
|
|
2402
2416
|
if (value == null) return;
|
|
2403
|
-
let
|
|
2417
|
+
let text3;
|
|
2404
2418
|
if (typeof value === "string") {
|
|
2405
|
-
|
|
2419
|
+
text3 = value;
|
|
2406
2420
|
} else if (typeof value === "number" || typeof value === "bigint" || typeof value === "boolean") {
|
|
2407
|
-
|
|
2421
|
+
text3 = String(value);
|
|
2408
2422
|
} else if (typeof value === "symbol") {
|
|
2409
|
-
|
|
2423
|
+
text3 = value.description ?? value.toString();
|
|
2410
2424
|
} else {
|
|
2411
2425
|
throw new FerricStoreError(`unsupported binary command argument type: ${typeof value}`);
|
|
2412
2426
|
}
|
|
2413
|
-
output.write(
|
|
2427
|
+
output.write(text3, offset, knownByteLength ?? import_node_buffer7.Buffer.byteLength(text3), "utf8");
|
|
2414
2428
|
}
|
|
2415
2429
|
function compactBinaryEncodedLength(value) {
|
|
2416
2430
|
return 4 + compactBinaryByteLength(value);
|
|
@@ -2423,10 +2437,10 @@ function compactBinaryByteLength(value) {
|
|
|
2423
2437
|
return byteLength;
|
|
2424
2438
|
}
|
|
2425
2439
|
function isCompactBinaryArgument(value) {
|
|
2426
|
-
return typeof value === "string" ||
|
|
2440
|
+
return typeof value === "string" || import_node_buffer7.Buffer.isBuffer(value) || value instanceof Uint8Array;
|
|
2427
2441
|
}
|
|
2428
2442
|
function isCompactBinaryScalar(value) {
|
|
2429
|
-
return value == null || typeof value === "string" || typeof value === "number" || typeof value === "bigint" || typeof value === "boolean" || typeof value === "symbol" ||
|
|
2443
|
+
return value == null || typeof value === "string" || typeof value === "number" || typeof value === "bigint" || typeof value === "boolean" || typeof value === "symbol" || import_node_buffer7.Buffer.isBuffer(value) || value instanceof Uint8Array;
|
|
2430
2444
|
}
|
|
2431
2445
|
function compactOptionalBinaryEncodedLength(value) {
|
|
2432
2446
|
return value == null ? 4 : compactBinaryEncodedLength(value);
|
|
@@ -2509,13 +2523,13 @@ function i64Arg(value) {
|
|
|
2509
2523
|
}
|
|
2510
2524
|
function boolArg(value) {
|
|
2511
2525
|
if (typeof value === "boolean") return value;
|
|
2512
|
-
const
|
|
2513
|
-
return
|
|
2526
|
+
const text3 = asText(value).toUpperCase();
|
|
2527
|
+
return text3 === "1" || text3 === "TRUE" || text3 === "YES" || text3 === "ON";
|
|
2514
2528
|
}
|
|
2515
2529
|
function isBoolToken(value) {
|
|
2516
2530
|
if (typeof value === "boolean") return true;
|
|
2517
|
-
const
|
|
2518
|
-
return
|
|
2531
|
+
const text3 = asText(value).toUpperCase();
|
|
2532
|
+
return text3 === "1" || text3 === "0" || text3 === "TRUE" || text3 === "FALSE" || text3 === "YES" || text3 === "NO" || text3 === "ON" || text3 === "OFF";
|
|
2519
2533
|
}
|
|
2520
2534
|
function independentMode(value) {
|
|
2521
2535
|
if (value === true) return 2;
|
|
@@ -2557,7 +2571,23 @@ function setOwnValue2(target, key, value) {
|
|
|
2557
2571
|
}
|
|
2558
2572
|
|
|
2559
2573
|
// src/protocol-flow-options.ts
|
|
2560
|
-
var
|
|
2574
|
+
var import_node_buffer8 = require("buffer");
|
|
2575
|
+
|
|
2576
|
+
// src/protocol-flow-option-value.ts
|
|
2577
|
+
function setFlowOptionValue(payload, field2, value, repeat) {
|
|
2578
|
+
if (!repeat || !Object.hasOwn(payload, field2)) {
|
|
2579
|
+
setOwnValue2(payload, field2, value);
|
|
2580
|
+
return;
|
|
2581
|
+
}
|
|
2582
|
+
const previous = payload[field2];
|
|
2583
|
+
setOwnValue2(
|
|
2584
|
+
payload,
|
|
2585
|
+
field2,
|
|
2586
|
+
Array.isArray(previous) ? [...previous, value] : [previous, value]
|
|
2587
|
+
);
|
|
2588
|
+
}
|
|
2589
|
+
|
|
2590
|
+
// src/protocol-flow-options.ts
|
|
2561
2591
|
var OPTION_FIELDS = {
|
|
2562
2592
|
CONSISTENT_PROJECTION: "consistent_projection",
|
|
2563
2593
|
COUNT: "count",
|
|
@@ -2632,7 +2662,7 @@ function normalizeFlowSearchStateMeta(payload) {
|
|
|
2632
2662
|
payload.state_meta = { [asText(state)]: stateMeta };
|
|
2633
2663
|
}
|
|
2634
2664
|
function isPlainObject2(value) {
|
|
2635
|
-
return typeof value === "object" && value != null && !Array.isArray(value) && !
|
|
2665
|
+
return typeof value === "object" && value != null && !Array.isArray(value) && !import_node_buffer8.Buffer.isBuffer(value) && !(value instanceof Uint8Array);
|
|
2636
2666
|
}
|
|
2637
2667
|
function parseFlowOptions(args, start, end, config) {
|
|
2638
2668
|
const payload = {};
|
|
@@ -2726,8 +2756,9 @@ function parseFlowOptions(args, start, end, config) {
|
|
|
2726
2756
|
case "TRANSITION_TO":
|
|
2727
2757
|
case "TO_EVENT":
|
|
2728
2758
|
case "EXPECT_STATE": {
|
|
2729
|
-
const field2 = token.toLowerCase();
|
|
2730
|
-
if (!
|
|
2759
|
+
const field2 = token === "IDEMPOTENCY" ? "idempotency_key" : token.toLowerCase();
|
|
2760
|
+
if (!hasOwnCommandArgument(args, index + 1, end, "Flow options")) return void 0;
|
|
2761
|
+
setFlowOptionValue(payload, field2, args[index + 1], token === "IF_STATE");
|
|
2731
2762
|
index += 2;
|
|
2732
2763
|
break;
|
|
2733
2764
|
}
|
|
@@ -3017,6 +3048,7 @@ var FLOW_ADMIN_FIELDS = {
|
|
|
3017
3048
|
LEASE_MS: "lease_ms",
|
|
3018
3049
|
LEASE_TOKEN: "lease_token",
|
|
3019
3050
|
LIMIT: "limit",
|
|
3051
|
+
MAX_ACTIVE_MS: "max_active_ms",
|
|
3020
3052
|
MAX_FIRES: "max_fires",
|
|
3021
3053
|
MAXBYTES: "payload_max_bytes",
|
|
3022
3054
|
NOW: "now_ms",
|
|
@@ -3026,7 +3058,6 @@ var FLOW_ADMIN_FIELDS = {
|
|
|
3026
3058
|
OVERLAP_RETRY_MS: "overlap_retry_ms",
|
|
3027
3059
|
OVERWRITE: "overwrite",
|
|
3028
3060
|
PARENT_FLOW_ID: "parent_flow_id",
|
|
3029
|
-
PARENT_ID: "parent_id",
|
|
3030
3061
|
PARTITION: "partition_key",
|
|
3031
3062
|
PAYLOAD: "payload",
|
|
3032
3063
|
PAYLOAD_MAX_BYTES: "payload_max_bytes",
|
|
@@ -3041,7 +3072,6 @@ var FLOW_ADMIN_FIELDS = {
|
|
|
3041
3072
|
REV: "rev",
|
|
3042
3073
|
RETURN: "return",
|
|
3043
3074
|
ROOT_FLOW_ID: "root_flow_id",
|
|
3044
|
-
ROOT_ID: "root_id",
|
|
3045
3075
|
SCOPE: "scope",
|
|
3046
3076
|
SHARD_ID: "shard_id",
|
|
3047
3077
|
START_AT_MS: "start_at_ms",
|
|
@@ -3178,7 +3208,7 @@ function flowAdminPayload(opcode, args, leadingFields = []) {
|
|
|
3178
3208
|
}
|
|
3179
3209
|
|
|
3180
3210
|
// src/protocol-flow-compact.ts
|
|
3181
|
-
var
|
|
3211
|
+
var import_node_buffer10 = require("buffer");
|
|
3182
3212
|
|
|
3183
3213
|
// src/protocol-flow-compact-common.ts
|
|
3184
3214
|
function compactManyRequestTag(value, regularTag, okOnSuccessTag) {
|
|
@@ -3287,7 +3317,7 @@ function parseNamedCountMap(values, start) {
|
|
|
3287
3317
|
}
|
|
3288
3318
|
|
|
3289
3319
|
// src/protocol-flow-compact-transition.ts
|
|
3290
|
-
var
|
|
3320
|
+
var import_node_buffer9 = require("buffer");
|
|
3291
3321
|
function compactFlowTransitionManyPayload(partition, fromState, toState, rawItems, mixed, options, maxBodyBytes) {
|
|
3292
3322
|
if ("payload" in options || "priority" in options || "state_meta" in options || "values" in options || "value_refs" in options || "drop_values" in options || "override_values" in options || "attributes_merge" in options || "attributes_delete" in options || typeof options.now_ms !== "number" || !Number.isSafeInteger(options.now_ms) || options.now_ms < 0) {
|
|
3293
3323
|
return void 0;
|
|
@@ -3339,7 +3369,7 @@ function compactFlowTransitionManyPayload(partition, fromState, toState, rawItem
|
|
|
3339
3369
|
total += 4 + idLength + 4 + itemPartitionLength + 8 + 4 + leaseLength;
|
|
3340
3370
|
}
|
|
3341
3371
|
assertCompactPayloadFits(total, maxBodyBytes);
|
|
3342
|
-
const out =
|
|
3372
|
+
const out = import_node_buffer9.Buffer.allocUnsafe(total);
|
|
3343
3373
|
let offset = 0;
|
|
3344
3374
|
out.writeUInt8(tag, offset);
|
|
3345
3375
|
offset += 1;
|
|
@@ -3397,7 +3427,7 @@ function compactFlowCreateManyPayload(partition, rawItems, mixed, auto, options,
|
|
|
3397
3427
|
}
|
|
3398
3428
|
assertCompactPayloadFits(total, maxBodyBytes);
|
|
3399
3429
|
const tag = mixed ? COMPACT_FLOW_CREATE_MANY_MIXED_REQUEST : auto ? COMPACT_FLOW_CREATE_MANY_REQUEST : COMPACT_FLOW_CREATE_MANY_PARTITION_REQUEST;
|
|
3400
|
-
const out =
|
|
3430
|
+
const out = import_node_buffer10.Buffer.allocUnsafe(total);
|
|
3401
3431
|
let offset = 0;
|
|
3402
3432
|
out.writeUInt8(tag, offset++);
|
|
3403
3433
|
offset = writeBinary(out, offset, toBuffer(options.type));
|
|
@@ -3442,7 +3472,7 @@ function compactFlowClaimDuePayload(type, options, maxBodyBytes) {
|
|
|
3442
3472
|
total += 1;
|
|
3443
3473
|
}
|
|
3444
3474
|
assertCompactPayloadFits(total, maxBodyBytes);
|
|
3445
|
-
const out =
|
|
3475
|
+
const out = import_node_buffer10.Buffer.allocUnsafe(total);
|
|
3446
3476
|
let offset = 0;
|
|
3447
3477
|
out.writeUInt8(COMPACT_FLOW_CLAIM_DUE_REQUEST, offset++);
|
|
3448
3478
|
offset = writeBinary(out, offset, toBuffer(type));
|
|
@@ -3496,7 +3526,7 @@ function compactFlowCompleteManyPayload(opcode, partition, rawItems, mixed, auto
|
|
|
3496
3526
|
total += compactBinaryEncodedLength(rawItems[rawIndex]) + compactOptionalBinaryEncodedLength(mixed ? rawItems[rawIndex + 1] : null) + compactBinaryEncodedLength(rawItems[rawIndex + width - 2]) + 8;
|
|
3497
3527
|
}
|
|
3498
3528
|
assertCompactPayloadFits(total, maxBodyBytes);
|
|
3499
|
-
const out =
|
|
3529
|
+
const out = import_node_buffer10.Buffer.allocUnsafe(total);
|
|
3500
3530
|
let offset = 0;
|
|
3501
3531
|
out.writeUInt8(
|
|
3502
3532
|
returnMode === "OK_ON_SUCCESS" ? COMPACT_FLOW_COMPLETE_MANY_OK_REQUEST : COMPACT_FLOW_COMPLETE_MANY_REQUEST,
|
|
@@ -3543,7 +3573,7 @@ function compactFlowRetryManyPayload(partition, rawItems, mixed, auto, options,
|
|
|
3543
3573
|
total += compactBinaryEncodedLength(rawItems[rawIndex]) + compactOptionalBinaryEncodedLength(mixed ? rawItems[rawIndex + 1] : null) + compactBinaryEncodedLength(rawItems[rawIndex + width - 2]) + 8;
|
|
3544
3574
|
}
|
|
3545
3575
|
assertCompactPayloadFits(total, maxBodyBytes);
|
|
3546
|
-
const out =
|
|
3576
|
+
const out = import_node_buffer10.Buffer.allocUnsafe(total);
|
|
3547
3577
|
let offset = 0;
|
|
3548
3578
|
out.writeUInt8(
|
|
3549
3579
|
returnMode === "OK_ON_SUCCESS" ? COMPACT_FLOW_RETRY_MANY_OK_REQUEST : COMPACT_FLOW_RETRY_MANY_REQUEST,
|
|
@@ -3631,7 +3661,7 @@ function compactFlowCancelManyPayload(args, maxBodyBytes) {
|
|
|
3631
3661
|
total += 4 + idLength + 4 + itemPartitionLength + 8;
|
|
3632
3662
|
}
|
|
3633
3663
|
assertCompactPayloadFits(total, maxBodyBytes);
|
|
3634
|
-
const out =
|
|
3664
|
+
const out = import_node_buffer10.Buffer.allocUnsafe(total);
|
|
3635
3665
|
let offset = 0;
|
|
3636
3666
|
out.writeUInt8(tag, offset);
|
|
3637
3667
|
offset += 1;
|
|
@@ -3667,7 +3697,7 @@ function isOptionalSafeIntegerNumber(value) {
|
|
|
3667
3697
|
}
|
|
3668
3698
|
|
|
3669
3699
|
// src/protocol-flow-compact-single.ts
|
|
3670
|
-
var
|
|
3700
|
+
var import_node_buffer11 = require("buffer");
|
|
3671
3701
|
function compactFlowValueMGetPayload(refs, maxBytes, maxBodyBytes) {
|
|
3672
3702
|
if (refs.length > 4294967295 || maxBytes != null && (typeof maxBytes !== "number" || !Number.isSafeInteger(maxBytes) || maxBytes < 0)) return void 0;
|
|
3673
3703
|
const minimum = 13 + refs.length * 4;
|
|
@@ -3684,7 +3714,7 @@ function compactFlowValueMGetPayload(refs, maxBytes, maxBodyBytes) {
|
|
|
3684
3714
|
total += 4 + byteLength;
|
|
3685
3715
|
}
|
|
3686
3716
|
assertCompactPayloadFits(total, maxBodyBytes);
|
|
3687
|
-
const out =
|
|
3717
|
+
const out = import_node_buffer11.Buffer.allocUnsafe(total);
|
|
3688
3718
|
let offset = 0;
|
|
3689
3719
|
out.writeUInt8(COMPACT_FLOW_VALUE_MGET_REQUEST, offset);
|
|
3690
3720
|
offset += 1;
|
|
@@ -3727,7 +3757,7 @@ function compactFlowListPayload(args, maxBodyBytes) {
|
|
|
3727
3757
|
const stateLength = state == null ? 0 : compactBinaryByteLength(state);
|
|
3728
3758
|
const total = 1 + 4 + typeLength + 4 + stateLength + 8 + 1;
|
|
3729
3759
|
assertCompactPayloadFits(total, maxBodyBytes);
|
|
3730
|
-
const out =
|
|
3760
|
+
const out = import_node_buffer11.Buffer.allocUnsafe(total);
|
|
3731
3761
|
let offset = 0;
|
|
3732
3762
|
out.writeUInt8(COMPACT_FLOW_LIST_REQUEST, offset);
|
|
3733
3763
|
offset += 1;
|
|
@@ -4170,6 +4200,7 @@ function flowSpawnChildrenPayload(args) {
|
|
|
4170
4200
|
"FROM_STATE",
|
|
4171
4201
|
"ON_CHILD_FAILED",
|
|
4172
4202
|
"ON_PARENT_CLOSED",
|
|
4203
|
+
"MAX_ACTIVE_MS",
|
|
4173
4204
|
"VALUE",
|
|
4174
4205
|
"VALUE_REF"
|
|
4175
4206
|
])
|
|
@@ -4200,6 +4231,29 @@ function flowSearchPayload(args) {
|
|
|
4200
4231
|
return { opcode: OPCODES.flowSearch, payload: { type: args[0], ...payload } };
|
|
4201
4232
|
}
|
|
4202
4233
|
|
|
4234
|
+
// src/protocol-flow-signal.ts
|
|
4235
|
+
function flowSignalPayload(args) {
|
|
4236
|
+
if (args.length < 3) return void 0;
|
|
4237
|
+
const options = parseFlowOptions(args, 1, args.length, {
|
|
4238
|
+
allowed: /* @__PURE__ */ new Set([
|
|
4239
|
+
"SIGNAL",
|
|
4240
|
+
"PARTITION",
|
|
4241
|
+
"IDEMPOTENCY",
|
|
4242
|
+
"IF_STATE",
|
|
4243
|
+
"TRANSITION_TO",
|
|
4244
|
+
"RUN_AT",
|
|
4245
|
+
"NOW",
|
|
4246
|
+
"VALUE",
|
|
4247
|
+
"VALUE_REF",
|
|
4248
|
+
"DROP_VALUE",
|
|
4249
|
+
"OVERRIDE_VALUE"
|
|
4250
|
+
]),
|
|
4251
|
+
required: /* @__PURE__ */ new Set(["SIGNAL"])
|
|
4252
|
+
});
|
|
4253
|
+
if (options == null) return void 0;
|
|
4254
|
+
return { opcode: OPCODES.flowSignal, payload: { id: args[0], ...options } };
|
|
4255
|
+
}
|
|
4256
|
+
|
|
4203
4257
|
// src/protocol-connection-policy.ts
|
|
4204
4258
|
function assertCommandDoesNotRequirePinnedConnection(args) {
|
|
4205
4259
|
const outer = commandName(args[0]);
|
|
@@ -4247,7 +4301,7 @@ function commandRequiresOrderedPipelineExecution(args) {
|
|
|
4247
4301
|
}
|
|
4248
4302
|
|
|
4249
4303
|
// src/protocol-compact-request.ts
|
|
4250
|
-
var
|
|
4304
|
+
var import_node_buffer12 = require("buffer");
|
|
4251
4305
|
function compactMsetPayload(args, maxBodyBytes) {
|
|
4252
4306
|
if (args.length % 2 !== 0) throw new FerricStoreError("MSET requires key/value pairs");
|
|
4253
4307
|
const minimum = 6 + args.length * 4;
|
|
@@ -4266,7 +4320,7 @@ function compactMsetPayload(args, maxBodyBytes) {
|
|
|
4266
4320
|
total += 4 + byteLength;
|
|
4267
4321
|
}
|
|
4268
4322
|
assertCompactPayloadFits(total, maxBodyBytes);
|
|
4269
|
-
const out =
|
|
4323
|
+
const out = import_node_buffer12.Buffer.allocUnsafe(total);
|
|
4270
4324
|
let offset = writeCompactPipelineHeader(out, 1, args.length / 2);
|
|
4271
4325
|
for (let index = 0; index < args.length; index += 1) {
|
|
4272
4326
|
offset = writeBinaryValue(out, offset, args[index], byteLengths[index] ?? 0);
|
|
@@ -4290,7 +4344,7 @@ function compactKeyPipelinePayload(opcode, args, mode, maxBodyBytes) {
|
|
|
4290
4344
|
total += 4 + byteLength;
|
|
4291
4345
|
}
|
|
4292
4346
|
assertCompactPayloadFits(total, maxBodyBytes);
|
|
4293
|
-
const out =
|
|
4347
|
+
const out = import_node_buffer12.Buffer.allocUnsafe(total);
|
|
4294
4348
|
let offset = writeCompactPipelineHeader(out, mode, args.length);
|
|
4295
4349
|
for (let index = 0; index < args.length; index += 1) {
|
|
4296
4350
|
offset = writeBinaryValue(out, offset, args[index], byteLengths[index] ?? 0);
|
|
@@ -4300,7 +4354,7 @@ function compactKeyPipelinePayload(opcode, args, mode, maxBodyBytes) {
|
|
|
4300
4354
|
function compactPipelinePayload(commands, maxBodyBytes) {
|
|
4301
4355
|
if (commands.length === 0) {
|
|
4302
4356
|
assertCompactPayloadFits(6, maxBodyBytes);
|
|
4303
|
-
const out =
|
|
4357
|
+
const out = import_node_buffer12.Buffer.allocUnsafe(6);
|
|
4304
4358
|
writeCompactPipelineHeader(out, 128 | 2, 0);
|
|
4305
4359
|
return out;
|
|
4306
4360
|
}
|
|
@@ -4342,7 +4396,7 @@ function compactSetPipelinePayload(commands, maxBodyBytes) {
|
|
|
4342
4396
|
total += 8 + keyByteLength + valueByteLength;
|
|
4343
4397
|
}
|
|
4344
4398
|
assertCompactPayloadFits(total, maxBodyBytes);
|
|
4345
|
-
const out =
|
|
4399
|
+
const out = import_node_buffer12.Buffer.allocUnsafe(total);
|
|
4346
4400
|
let offset = writeCompactPipelineHeader(out, 128 | 1, commands.length);
|
|
4347
4401
|
for (let index = 0; index < commands.length; index += 1) {
|
|
4348
4402
|
offset = writeBinaryValue(out, offset, argumentValues[index * 2], argumentByteLengths[index * 2] ?? 0);
|
|
@@ -4377,7 +4431,7 @@ function compactGetPipelinePayload(commands, maxBodyBytes) {
|
|
|
4377
4431
|
total += 4 + keyByteLength;
|
|
4378
4432
|
}
|
|
4379
4433
|
assertCompactPayloadFits(total, maxBodyBytes);
|
|
4380
|
-
const out =
|
|
4434
|
+
const out = import_node_buffer12.Buffer.allocUnsafe(total);
|
|
4381
4435
|
let offset = writeCompactPipelineHeader(out, 128 | 2, commands.length);
|
|
4382
4436
|
for (let index = 0; index < commands.length; index += 1) {
|
|
4383
4437
|
offset = writeBinaryValue(out, offset, keys[index], keyByteLengths[index] ?? 0);
|
|
@@ -4418,7 +4472,7 @@ function writeCompactPipelineHeader(out, mode, count) {
|
|
|
4418
4472
|
}
|
|
4419
4473
|
|
|
4420
4474
|
// src/protocol-kv.ts
|
|
4421
|
-
var
|
|
4475
|
+
var import_node_buffer13 = require("buffer");
|
|
4422
4476
|
function collectionProtocolCommand(command, args) {
|
|
4423
4477
|
switch (command) {
|
|
4424
4478
|
case "CAS":
|
|
@@ -4566,15 +4620,20 @@ function fetchOrComputeCommand(args) {
|
|
|
4566
4620
|
};
|
|
4567
4621
|
}
|
|
4568
4622
|
function fetchOrComputeResultCommand(args) {
|
|
4569
|
-
if (args.length !== 4 || !isBinaryCommandArgument(args[0]) || !isBinaryCommandArgument(args[1]))
|
|
4623
|
+
if (args.length !== 4 || !isBinaryCommandArgument(args[0]) || !isBinaryCommandArgument(args[1])) {
|
|
4624
|
+
throw new FerricStoreError("FETCH_OR_COMPUTE_RESULT requires key, ownership token, value, and ttl_ms");
|
|
4625
|
+
}
|
|
4570
4626
|
const ttlMs = positiveSafeInteger2(args[3]);
|
|
4571
|
-
|
|
4627
|
+
if (ttlMs == null) throw new FerricStoreError("FETCH_OR_COMPUTE_RESULT ttl_ms must be positive");
|
|
4628
|
+
return {
|
|
4572
4629
|
opcode: COMMAND_OPCODES.FETCH_OR_COMPUTE_RESULT,
|
|
4573
4630
|
payload: { key: args[0], token: args[1], ttl_ms: ttlMs, value: args[2] }
|
|
4574
4631
|
};
|
|
4575
4632
|
}
|
|
4576
4633
|
function fetchOrComputeErrorCommand(args) {
|
|
4577
|
-
if (args.length !== 3 || !isBinaryCommandArgument(args[0]) || !isBinaryCommandArgument(args[1]) || !isBinaryCommandArgument(args[2]))
|
|
4634
|
+
if (args.length !== 3 || !isBinaryCommandArgument(args[0]) || !isBinaryCommandArgument(args[1]) || !isBinaryCommandArgument(args[2])) {
|
|
4635
|
+
throw new FerricStoreError("FETCH_OR_COMPUTE_ERROR requires key, ownership token, and message");
|
|
4636
|
+
}
|
|
4578
4637
|
return {
|
|
4579
4638
|
opcode: COMMAND_OPCODES.FETCH_OR_COMPUTE_ERROR,
|
|
4580
4639
|
payload: { key: args[0], message: args[2], token: args[1] }
|
|
@@ -4660,17 +4719,17 @@ function parsedNumber(value) {
|
|
|
4660
4719
|
}
|
|
4661
4720
|
}
|
|
4662
4721
|
function isBinaryCommandArgument(value) {
|
|
4663
|
-
return typeof value === "string" ||
|
|
4722
|
+
return typeof value === "string" || import_node_buffer13.Buffer.isBuffer(value);
|
|
4664
4723
|
}
|
|
4665
4724
|
function isDirectKvValueArgument(value) {
|
|
4666
4725
|
return isBinaryCommandArgument(value) || typeof value === "object" && value != null;
|
|
4667
4726
|
}
|
|
4668
4727
|
function binaryToken(value) {
|
|
4669
|
-
return typeof value === "string" ? value.toUpperCase() :
|
|
4728
|
+
return typeof value === "string" ? value.toUpperCase() : import_node_buffer13.Buffer.isBuffer(value) ? value.toString("utf8").toUpperCase() : void 0;
|
|
4670
4729
|
}
|
|
4671
4730
|
|
|
4672
4731
|
// src/protocol-value.ts
|
|
4673
|
-
var
|
|
4732
|
+
var import_node_buffer14 = require("buffer");
|
|
4674
4733
|
function planValueWithLimit(value, maxBytes) {
|
|
4675
4734
|
const budget = {
|
|
4676
4735
|
maxBytes,
|
|
@@ -4725,7 +4784,7 @@ function planContainerValue(value, budget, ancestors, depth) {
|
|
|
4725
4784
|
let byteLength = 5;
|
|
4726
4785
|
let index = 0;
|
|
4727
4786
|
for (const [key, item] of entries) {
|
|
4728
|
-
const keyByteLength =
|
|
4787
|
+
const keyByteLength = import_node_buffer14.Buffer.byteLength(key);
|
|
4729
4788
|
consumeEncodeBytes(budget, 4 + keyByteLength);
|
|
4730
4789
|
const valuePlan = planValueAt(item, budget, ancestors, depth + 1);
|
|
4731
4790
|
entryPlans[index] = { key, keyByteLength, value: valuePlan };
|
|
@@ -4774,7 +4833,7 @@ function planScalarValue(value, budget) {
|
|
|
4774
4833
|
consumeEncodeBytes(budget, 9);
|
|
4775
4834
|
return { byteLength: 9, tag: 7, value };
|
|
4776
4835
|
}
|
|
4777
|
-
if (typeof value === "string" ||
|
|
4836
|
+
if (typeof value === "string" || import_node_buffer14.Buffer.isBuffer(value) || value instanceof Uint8Array) {
|
|
4778
4837
|
const valueByteLength = binaryValueByteLength(value);
|
|
4779
4838
|
const byteLength = 5 + valueByteLength;
|
|
4780
4839
|
consumeEncodeBytes(budget, byteLength);
|
|
@@ -4798,7 +4857,7 @@ function writeValuePlan(output, start, plan) {
|
|
|
4798
4857
|
offset += 4;
|
|
4799
4858
|
if (typeof plan.value === "string") {
|
|
4800
4859
|
output.write(plan.value, offset, plan.valueByteLength, "utf8");
|
|
4801
|
-
} else if (
|
|
4860
|
+
} else if (import_node_buffer14.Buffer.isBuffer(plan.value)) {
|
|
4802
4861
|
plan.value.copy(output, offset);
|
|
4803
4862
|
} else {
|
|
4804
4863
|
output.set(plan.value, offset);
|
|
@@ -4931,58 +4990,458 @@ function requireAvailable(data, offset, size) {
|
|
|
4931
4990
|
}
|
|
4932
4991
|
}
|
|
4933
4992
|
|
|
4993
|
+
// src/key-slot-validation.ts
|
|
4994
|
+
var import_node_buffer16 = require("buffer");
|
|
4995
|
+
|
|
4996
|
+
// src/topology-utilities.ts
|
|
4997
|
+
var import_node_buffer15 = require("buffer");
|
|
4998
|
+
function isPlainObject3(value) {
|
|
4999
|
+
return typeof value === "object" && value != null && !Array.isArray(value) && !import_node_buffer15.Buffer.isBuffer(value);
|
|
5000
|
+
}
|
|
5001
|
+
function getField(source, ...keys) {
|
|
5002
|
+
if (source instanceof Map) {
|
|
5003
|
+
for (const key of keys) {
|
|
5004
|
+
if (source.has(key)) return source.get(key);
|
|
5005
|
+
const bufferKey = import_node_buffer15.Buffer.from(key);
|
|
5006
|
+
for (const [itemKey, value] of source.entries()) {
|
|
5007
|
+
if (import_node_buffer15.Buffer.isBuffer(itemKey) && itemKey.equals(bufferKey)) return value;
|
|
5008
|
+
}
|
|
5009
|
+
}
|
|
5010
|
+
return void 0;
|
|
5011
|
+
}
|
|
5012
|
+
if (isPlainObject3(source)) {
|
|
5013
|
+
for (const key of keys) {
|
|
5014
|
+
if (Object.hasOwn(source, key)) return source[key];
|
|
5015
|
+
}
|
|
5016
|
+
}
|
|
5017
|
+
return void 0;
|
|
5018
|
+
}
|
|
5019
|
+
function textOrUndefined(value) {
|
|
5020
|
+
if (typeof value === "string") return value;
|
|
5021
|
+
if (import_node_buffer15.Buffer.isBuffer(value)) return value.toString("utf8");
|
|
5022
|
+
return void 0;
|
|
5023
|
+
}
|
|
5024
|
+
function numberOrUndefined(value) {
|
|
5025
|
+
return typeof value === "number" && Number.isSafeInteger(value) ? value : void 0;
|
|
5026
|
+
}
|
|
5027
|
+
function nativeEventName(event) {
|
|
5028
|
+
return textOrUndefined(getField(event.value, "event"))?.toUpperCase();
|
|
5029
|
+
}
|
|
5030
|
+
function endpointFromRange(item) {
|
|
5031
|
+
const endpointValue = getField(item, "endpoint");
|
|
5032
|
+
if (endpointValue != null && !isPlainObject3(endpointValue) && !(endpointValue instanceof Map)) {
|
|
5033
|
+
throw new FerricStoreError("invalid SHARDS endpoint", { raw: item });
|
|
5034
|
+
}
|
|
5035
|
+
const raw = endpointValue ?? item;
|
|
5036
|
+
const host = textOrUndefined(getField(raw, "host", "native_host"));
|
|
5037
|
+
const nativePort = numberOrUndefined(getField(raw, "native_port"));
|
|
5038
|
+
if (host == null || !validEndpointHost(host) || nativePort == null || nativePort <= 0 || nativePort > 65535) {
|
|
5039
|
+
throw new FerricStoreError("invalid SHARDS endpoint", { raw: item });
|
|
5040
|
+
}
|
|
5041
|
+
const nativeTlsPortValue = getField(raw, "native_tls_port");
|
|
5042
|
+
const nativeTlsPort = numberOrUndefined(nativeTlsPortValue);
|
|
5043
|
+
if (nativeTlsPortValue != null && (nativeTlsPort == null || nativeTlsPort <= 0 || nativeTlsPort > 65535)) {
|
|
5044
|
+
throw new FerricStoreError("invalid SHARDS endpoint", { raw: item });
|
|
5045
|
+
}
|
|
5046
|
+
return {
|
|
5047
|
+
host,
|
|
5048
|
+
nativePort,
|
|
5049
|
+
node: textOrUndefined(getField(raw, "node", "leader_node", "owner_node")) ?? host,
|
|
5050
|
+
...nativeTlsPort == null ? {} : { nativeTlsPort }
|
|
5051
|
+
};
|
|
5052
|
+
}
|
|
5053
|
+
function validEndpointHost(host) {
|
|
5054
|
+
if (host.length === 0 || host.trim() !== host || /[\s\\/?#@]/u.test(host)) return false;
|
|
5055
|
+
const authorityHost = host.includes(":") && !host.startsWith("[") ? `[${host}]` : host;
|
|
5056
|
+
try {
|
|
5057
|
+
const url = new URL(`ferric://${authorityHost}:6388`);
|
|
5058
|
+
return url.hostname !== "" && url.port === "6388" && url.username === "" && url.password === "";
|
|
5059
|
+
} catch {
|
|
5060
|
+
return false;
|
|
5061
|
+
}
|
|
5062
|
+
}
|
|
5063
|
+
function sameEndpoint(left, right) {
|
|
5064
|
+
return normalizedEndpointHost(left.host) === normalizedEndpointHost(right.host) && left.nativePort === right.nativePort && left.nativeTlsPort === right.nativeTlsPort && left.node === right.node;
|
|
5065
|
+
}
|
|
5066
|
+
function parseFerricUrl2(value) {
|
|
5067
|
+
const url = new URL(value);
|
|
5068
|
+
if (url.protocol !== "ferric:" && url.protocol !== "ferrics:") {
|
|
5069
|
+
throw new FerricStoreError(`unsupported FerricStore URL scheme: ${url.protocol}`);
|
|
5070
|
+
}
|
|
5071
|
+
return {
|
|
5072
|
+
host: normalizeFerricUrlHost(url.hostname),
|
|
5073
|
+
...url.password === "" ? {} : { password: decodeURIComponent(url.password) },
|
|
5074
|
+
port: Number(url.port || (url.protocol === "ferrics:" ? 6389 : 6388)),
|
|
5075
|
+
tls: url.protocol === "ferrics:",
|
|
5076
|
+
...url.username === "" ? {} : { username: decodeURIComponent(url.username) }
|
|
5077
|
+
};
|
|
5078
|
+
}
|
|
5079
|
+
function endpointKeyFor(endpoint) {
|
|
5080
|
+
return `${normalizedEndpointHost(endpoint.host)}:${endpoint.nativePort}`;
|
|
5081
|
+
}
|
|
5082
|
+
function connectionKeyForEndpoint(endpoint, useTls) {
|
|
5083
|
+
const port = useTls && endpoint.nativeTlsPort != null ? endpoint.nativeTlsPort : endpoint.nativePort;
|
|
5084
|
+
return `${useTls ? "ferrics" : "ferric"}://${normalizedEndpointHost(endpoint.host)}:${port}`;
|
|
5085
|
+
}
|
|
5086
|
+
function connectionKeyFromUrl(url) {
|
|
5087
|
+
const parsed = parseFerricUrl2(url);
|
|
5088
|
+
return `${parsed.tls ? "ferrics" : "ferric"}://${normalizedEndpointHost(parsed.host)}:${parsed.port}`;
|
|
5089
|
+
}
|
|
5090
|
+
function normalizedEndpointHost(host) {
|
|
5091
|
+
const lower = host.toLowerCase();
|
|
5092
|
+
return lower.startsWith("[") && lower.endsWith("]") ? lower.slice(1, -1) : lower;
|
|
5093
|
+
}
|
|
5094
|
+
function urlFromEndpoint(endpoint, useTls) {
|
|
5095
|
+
const port = useTls && endpoint.nativeTlsPort != null ? endpoint.nativeTlsPort : endpoint.nativePort;
|
|
5096
|
+
const host = endpoint.host.includes(":") && !endpoint.host.startsWith("[") ? `[${endpoint.host}]` : endpoint.host;
|
|
5097
|
+
return `${useTls ? "ferrics" : "ferric"}://${host}:${port}`;
|
|
5098
|
+
}
|
|
5099
|
+
async function mapSettledWithConcurrency(items, concurrency, operation) {
|
|
5100
|
+
const results = new Array(items.length);
|
|
5101
|
+
let nextIndex = 0;
|
|
5102
|
+
const worker = async () => {
|
|
5103
|
+
while (nextIndex < items.length) {
|
|
5104
|
+
const index = nextIndex++;
|
|
5105
|
+
const item = items[index];
|
|
5106
|
+
try {
|
|
5107
|
+
results[index] = { status: "fulfilled", value: await operation(item, index) };
|
|
5108
|
+
} catch (reason) {
|
|
5109
|
+
results[index] = { status: "rejected", reason };
|
|
5110
|
+
}
|
|
5111
|
+
}
|
|
5112
|
+
};
|
|
5113
|
+
await Promise.all(Array.from(
|
|
5114
|
+
{ length: Math.min(concurrency, items.length) },
|
|
5115
|
+
async () => await worker()
|
|
5116
|
+
));
|
|
5117
|
+
return results;
|
|
5118
|
+
}
|
|
5119
|
+
function throwFirstRejected(results) {
|
|
5120
|
+
for (const result of results) {
|
|
5121
|
+
if (result.status === "rejected") throw result.reason;
|
|
5122
|
+
}
|
|
5123
|
+
}
|
|
5124
|
+
var TaskConcurrencyLimiter = class {
|
|
5125
|
+
constructor(concurrency) {
|
|
5126
|
+
this.concurrency = concurrency;
|
|
5127
|
+
}
|
|
5128
|
+
concurrency;
|
|
5129
|
+
active = 0;
|
|
5130
|
+
head = 0;
|
|
5131
|
+
pending = [];
|
|
5132
|
+
async run(operation) {
|
|
5133
|
+
await this.acquire();
|
|
5134
|
+
try {
|
|
5135
|
+
return await operation();
|
|
5136
|
+
} finally {
|
|
5137
|
+
this.release();
|
|
5138
|
+
}
|
|
5139
|
+
}
|
|
5140
|
+
acquire() {
|
|
5141
|
+
if (this.active < this.concurrency) {
|
|
5142
|
+
this.active += 1;
|
|
5143
|
+
return Promise.resolve();
|
|
5144
|
+
}
|
|
5145
|
+
return new Promise((resolve) => this.pending.push(resolve));
|
|
5146
|
+
}
|
|
5147
|
+
release() {
|
|
5148
|
+
const next = this.pending[this.head];
|
|
5149
|
+
if (next == null) {
|
|
5150
|
+
this.active -= 1;
|
|
5151
|
+
return;
|
|
5152
|
+
}
|
|
5153
|
+
this.head += 1;
|
|
5154
|
+
next();
|
|
5155
|
+
if (this.head === this.pending.length) {
|
|
5156
|
+
this.pending.length = 0;
|
|
5157
|
+
this.head = 0;
|
|
5158
|
+
} else if (this.head >= 1024 && this.head * 2 >= this.pending.length) {
|
|
5159
|
+
this.pending.splice(0, this.head);
|
|
5160
|
+
this.head = 0;
|
|
5161
|
+
}
|
|
5162
|
+
}
|
|
5163
|
+
};
|
|
5164
|
+
function normalizedHostSet(hosts) {
|
|
5165
|
+
return new Set(
|
|
5166
|
+
hosts.filter((host) => host != null && host !== "").map((host) => normalizedEndpointHost(host))
|
|
5167
|
+
);
|
|
5168
|
+
}
|
|
5169
|
+
var OPEN_BRACE = "{".charCodeAt(0);
|
|
5170
|
+
var CLOSE_BRACE = "}".charCodeAt(0);
|
|
5171
|
+
function hashTagOrKey(key) {
|
|
5172
|
+
const start = key.indexOf(OPEN_BRACE);
|
|
5173
|
+
if (start < 0) return key;
|
|
5174
|
+
const end = key.indexOf(CLOSE_BRACE, start + 1);
|
|
5175
|
+
return end > start + 1 ? key.subarray(start + 1, end) : key;
|
|
5176
|
+
}
|
|
5177
|
+
var ROUTE_SLOT_MASK = 1023;
|
|
5178
|
+
function routingSlotForKey(key) {
|
|
5179
|
+
if (typeof key === "string") {
|
|
5180
|
+
const [start, end] = stringHashRange(key);
|
|
5181
|
+
return crc32Utf8(key, start, end) & ROUTE_SLOT_MASK;
|
|
5182
|
+
}
|
|
5183
|
+
const keyBytes = key;
|
|
5184
|
+
return crc32(hashTagOrKey(keyBytes)) & ROUTE_SLOT_MASK;
|
|
5185
|
+
}
|
|
5186
|
+
function stringHashRange(key) {
|
|
5187
|
+
const startBrace = key.indexOf("{");
|
|
5188
|
+
const endBrace = startBrace < 0 ? -1 : key.indexOf("}", startBrace + 1);
|
|
5189
|
+
return endBrace > startBrace + 1 ? [startBrace + 1, endBrace] : [0, key.length];
|
|
5190
|
+
}
|
|
5191
|
+
|
|
5192
|
+
// src/key-slot-validation.ts
|
|
5193
|
+
var validatedCommands = /* @__PURE__ */ new WeakSet();
|
|
5194
|
+
function assertAtomicKeyValueCommandSharesSlot(args) {
|
|
5195
|
+
const value = args[0];
|
|
5196
|
+
const command = (typeof value === "string" ? value : import_node_buffer16.Buffer.isBuffer(value) ? value.toString("utf8") : "").toUpperCase();
|
|
5197
|
+
if (command === "MSET" || command === "MSETNX") {
|
|
5198
|
+
assertKeyValueCommandSharesSlot(args, command);
|
|
5199
|
+
}
|
|
5200
|
+
}
|
|
5201
|
+
function assertKeyValueCommandSharesSlot(args, command) {
|
|
5202
|
+
if (validatedCommands.has(args) || args.length < 3 || args.length % 2 === 0) return;
|
|
5203
|
+
let expectedSlot;
|
|
5204
|
+
for (let index = 1; index < args.length; index += 2) {
|
|
5205
|
+
const key = args[index];
|
|
5206
|
+
if (typeof key !== "string" && !import_node_buffer16.Buffer.isBuffer(key)) return;
|
|
5207
|
+
const slot = routingSlotForKey(key);
|
|
5208
|
+
expectedSlot ??= slot;
|
|
5209
|
+
if (slot !== expectedSlot) {
|
|
5210
|
+
throw new TypeError(`${command} keys must share a slot`);
|
|
5211
|
+
}
|
|
5212
|
+
}
|
|
5213
|
+
validatedCommands.add(args);
|
|
5214
|
+
}
|
|
5215
|
+
|
|
4934
5216
|
// src/protocol-response.ts
|
|
5217
|
+
var import_node_buffer20 = require("buffer");
|
|
5218
|
+
|
|
5219
|
+
// src/protocol-compact-response.ts
|
|
5220
|
+
var import_node_buffer19 = require("buffer");
|
|
5221
|
+
|
|
5222
|
+
// src/native-negotiation.ts
|
|
4935
5223
|
var import_node_buffer17 = require("buffer");
|
|
5224
|
+
var EMPTY_COMPACT_RESPONSE_OPCODES = /* @__PURE__ */ new Map();
|
|
5225
|
+
function nativeNegotiation(value) {
|
|
5226
|
+
const capabilities = field(value, "capabilities") ?? value;
|
|
5227
|
+
const limits = field(capabilities, "limits");
|
|
5228
|
+
const responseCodecs = field(capabilities, "response_codecs");
|
|
5229
|
+
const maxResponseBytes = positiveSafeInteger3(field(limits, "max_response_bytes"));
|
|
5230
|
+
return {
|
|
5231
|
+
compactResponseOpcodes: parseCompactResponseOpcodes(
|
|
5232
|
+
field(responseCodecs, "compact_response_opcodes")
|
|
5233
|
+
),
|
|
5234
|
+
...maxResponseBytes == null ? {} : { maxResponseBytes }
|
|
5235
|
+
};
|
|
5236
|
+
}
|
|
5237
|
+
function compactResponseOpcodeSupports(capabilities, codec, opcode) {
|
|
5238
|
+
return capabilities?.get(codec)?.has(opcode) === true;
|
|
5239
|
+
}
|
|
5240
|
+
function parseCompactResponseOpcodes(value) {
|
|
5241
|
+
const entries = mapEntries(value);
|
|
5242
|
+
if (entries == null) return EMPTY_COMPACT_RESPONSE_OPCODES;
|
|
5243
|
+
const result = /* @__PURE__ */ new Map();
|
|
5244
|
+
for (const [rawName, rawOpcodes] of entries) {
|
|
5245
|
+
const name = text2(rawName);
|
|
5246
|
+
if (name == null || name.length === 0 || !Array.isArray(rawOpcodes)) continue;
|
|
5247
|
+
const opcodes = /* @__PURE__ */ new Set();
|
|
5248
|
+
let valid = true;
|
|
5249
|
+
for (let index = 0; index < rawOpcodes.length; index += 1) {
|
|
5250
|
+
if (!Object.hasOwn(rawOpcodes, index)) {
|
|
5251
|
+
valid = false;
|
|
5252
|
+
break;
|
|
5253
|
+
}
|
|
5254
|
+
const opcode = unsigned16(rawOpcodes[index]);
|
|
5255
|
+
if (opcode == null) {
|
|
5256
|
+
valid = false;
|
|
5257
|
+
break;
|
|
5258
|
+
}
|
|
5259
|
+
opcodes.add(opcode);
|
|
5260
|
+
}
|
|
5261
|
+
if (valid) result.set(name, opcodes);
|
|
5262
|
+
}
|
|
5263
|
+
return result;
|
|
5264
|
+
}
|
|
5265
|
+
function mapEntries(value) {
|
|
5266
|
+
if (value instanceof Map) return [...value.entries()];
|
|
5267
|
+
if (typeof value !== "object" || value == null || Array.isArray(value)) return void 0;
|
|
5268
|
+
return Object.entries(value);
|
|
5269
|
+
}
|
|
5270
|
+
function unsigned16(value) {
|
|
5271
|
+
const parsed = nonNegativeSafeInteger2(value);
|
|
5272
|
+
return parsed != null && parsed <= 65535 ? parsed : void 0;
|
|
5273
|
+
}
|
|
5274
|
+
function positiveSafeInteger3(value) {
|
|
5275
|
+
const parsed = nonNegativeSafeInteger2(value);
|
|
5276
|
+
return parsed != null && parsed > 0 ? parsed : void 0;
|
|
5277
|
+
}
|
|
5278
|
+
function nonNegativeSafeInteger2(value) {
|
|
5279
|
+
if (typeof value === "bigint") {
|
|
5280
|
+
return value >= 0n && value <= BigInt(Number.MAX_SAFE_INTEGER) ? Number(value) : void 0;
|
|
5281
|
+
}
|
|
5282
|
+
const source = text2(value) ?? value;
|
|
5283
|
+
if (typeof source !== "number" && (typeof source !== "string" || !/^\d+$/u.test(source))) {
|
|
5284
|
+
return void 0;
|
|
5285
|
+
}
|
|
5286
|
+
const parsed = Number(source);
|
|
5287
|
+
return Number.isSafeInteger(parsed) && parsed >= 0 ? parsed : void 0;
|
|
5288
|
+
}
|
|
5289
|
+
function text2(value) {
|
|
5290
|
+
if (typeof value === "string") return value;
|
|
5291
|
+
if (import_node_buffer17.Buffer.isBuffer(value) || value instanceof Uint8Array) {
|
|
5292
|
+
return import_node_buffer17.Buffer.from(value).toString("utf8");
|
|
5293
|
+
}
|
|
5294
|
+
return void 0;
|
|
5295
|
+
}
|
|
5296
|
+
|
|
5297
|
+
// src/protocol-compact-collections.ts
|
|
5298
|
+
var import_node_buffer18 = require("buffer");
|
|
5299
|
+
function decodeCompactIntegerList(data, budget) {
|
|
5300
|
+
requireAvailable(data, 0, 5);
|
|
5301
|
+
const count = data.readUInt32BE(1);
|
|
5302
|
+
requireCompactContainer(count, budget);
|
|
5303
|
+
if (data.byteLength !== 5 + count * 8) {
|
|
5304
|
+
throw new FerricStoreError("invalid compact integer list response");
|
|
5305
|
+
}
|
|
5306
|
+
const values = new Array(count);
|
|
5307
|
+
for (let index = 0, offset = 5; index < count; index += 1, offset += 8) {
|
|
5308
|
+
const value = data.readBigInt64BE(offset);
|
|
5309
|
+
values[index] = value <= MAX_SAFE_INTEGER_BIGINT && value >= MIN_SAFE_INTEGER_BIGINT ? Number(value) : value;
|
|
5310
|
+
}
|
|
5311
|
+
return values;
|
|
5312
|
+
}
|
|
5313
|
+
function decodeCompactBinaryListList(data, budget) {
|
|
5314
|
+
requireAvailable(data, 0, 5);
|
|
5315
|
+
const count = data.readUInt32BE(1);
|
|
5316
|
+
requireCompactContainer(count, budget);
|
|
5317
|
+
let offset = 5;
|
|
5318
|
+
const values = new Array(count);
|
|
5319
|
+
for (let index = 0; index < count; index += 1) {
|
|
5320
|
+
const read = readCompactBinaryList(data, offset, budget);
|
|
5321
|
+
values[index] = read.value;
|
|
5322
|
+
offset = read.offset;
|
|
5323
|
+
}
|
|
5324
|
+
if (offset !== data.byteLength) throw new FerricStoreError("trailing compact binary list-list bytes");
|
|
5325
|
+
return values;
|
|
5326
|
+
}
|
|
5327
|
+
function decodeCompactBinaryMapList(data, budget) {
|
|
5328
|
+
requireAvailable(data, 0, 5);
|
|
5329
|
+
const count = data.readUInt32BE(1);
|
|
5330
|
+
requireCompactContainer(count, budget);
|
|
5331
|
+
let offset = 5;
|
|
5332
|
+
const values = new Array(count);
|
|
5333
|
+
for (let index = 0; index < count; index += 1) {
|
|
5334
|
+
const read = readCompactBinaryMap(data, offset, budget);
|
|
5335
|
+
values[index] = read.value;
|
|
5336
|
+
offset = read.offset;
|
|
5337
|
+
}
|
|
5338
|
+
if (offset !== data.byteLength) throw new FerricStoreError("trailing compact binary map-list bytes");
|
|
5339
|
+
return values;
|
|
5340
|
+
}
|
|
5341
|
+
function readCompactBinaryList(data, offset, budget) {
|
|
5342
|
+
requireAvailable(data, offset, 4);
|
|
5343
|
+
const count = data.readUInt32BE(offset);
|
|
5344
|
+
requireCompactContainer(count, budget);
|
|
5345
|
+
offset += 4;
|
|
5346
|
+
const values = new Array(count);
|
|
5347
|
+
for (let index = 0; index < count; index += 1) {
|
|
5348
|
+
const read = readBinary(data, offset);
|
|
5349
|
+
values[index] = read.value;
|
|
5350
|
+
offset = read.offset;
|
|
5351
|
+
}
|
|
5352
|
+
return { value: values, offset };
|
|
5353
|
+
}
|
|
5354
|
+
function readCompactBinaryMap(data, offset, budget) {
|
|
5355
|
+
requireAvailable(data, offset, 4);
|
|
5356
|
+
const count = data.readUInt32BE(offset);
|
|
5357
|
+
requireCompactContainer(count, budget);
|
|
5358
|
+
offset += 4;
|
|
5359
|
+
const values = {};
|
|
5360
|
+
for (let index = 0; index < count; index += 1) {
|
|
5361
|
+
const key = readBinary(data, offset);
|
|
5362
|
+
const value = readBinary(data, key.offset);
|
|
5363
|
+
setOwnValue2(values, key.value.toString("utf8"), value.value);
|
|
5364
|
+
offset = value.offset;
|
|
5365
|
+
}
|
|
5366
|
+
return { value: values, offset };
|
|
5367
|
+
}
|
|
5368
|
+
function markCompactPipelineDecoded(values) {
|
|
5369
|
+
Object.defineProperty(values, COMPACT_PIPELINE_DECODED, { value: true });
|
|
5370
|
+
return values;
|
|
5371
|
+
}
|
|
5372
|
+
function requireCompactContainer(count, budget) {
|
|
5373
|
+
if (count > DEFAULT_MAX_VALUE_ITEMS) {
|
|
5374
|
+
throw new FerricStoreError("native compact response container exceeds max items");
|
|
5375
|
+
}
|
|
5376
|
+
consumeDecodeItems(count, budget);
|
|
5377
|
+
}
|
|
4936
5378
|
|
|
4937
5379
|
// src/protocol-compact-response.ts
|
|
4938
|
-
var import_node_buffer16 = require("buffer");
|
|
4939
5380
|
function tryDecodeCompactResponse(opcode, body, hints) {
|
|
4940
5381
|
if (body.byteLength === 0) return { found: false, value: void 0 };
|
|
4941
5382
|
const budget = { remainingItems: DEFAULT_MAX_VALUE_ITEMS };
|
|
4942
5383
|
const tag = body.readUInt8(0);
|
|
4943
|
-
|
|
5384
|
+
const pipelineValues = opcode === OPCODES.pipeline && supports(hints, "pipeline_v1", opcode);
|
|
5385
|
+
if (tag === COMPACT_OK_LIST && (supports(hints, "ok_list_v1", opcode) || pipelineValues)) {
|
|
4944
5386
|
const values = decodeCompactOkList(body, budget);
|
|
4945
|
-
return {
|
|
5387
|
+
return {
|
|
5388
|
+
found: true,
|
|
5389
|
+
value: opcode === OPCODES.pipeline ? markCompactPipelineDecoded(values) : values.length === 1 ? "OK" : values
|
|
5390
|
+
};
|
|
4946
5391
|
}
|
|
4947
|
-
if (tag === COMPACT_KV_GET &&
|
|
5392
|
+
if (tag === COMPACT_KV_GET && supports(hints, "kv_get_v1", opcode)) {
|
|
4948
5393
|
return { found: true, value: decodeCompactKvGet(body) };
|
|
4949
5394
|
}
|
|
4950
|
-
if ((tag === COMPACT_KV_MGET || tag === COMPACT_KV_MGET_FIXED) &&
|
|
5395
|
+
if ((tag === COMPACT_KV_MGET || tag === COMPACT_KV_MGET_FIXED) && (supports(hints, "kv_mget_v1", opcode) || pipelineValues)) {
|
|
5396
|
+
const values = tag === COMPACT_KV_MGET ? decodeCompactMget(body, budget) : decodeCompactMgetFixed(body, budget);
|
|
4951
5397
|
return {
|
|
4952
5398
|
found: true,
|
|
4953
|
-
value:
|
|
5399
|
+
value: opcode === OPCODES.pipeline ? markCompactPipelineDecoded(values) : values
|
|
4954
5400
|
};
|
|
4955
5401
|
}
|
|
4956
|
-
if (tag ===
|
|
5402
|
+
if (tag === COMPACT_INTEGER_LIST && pipelineValues) {
|
|
5403
|
+
return { found: true, value: markCompactPipelineDecoded(decodeCompactIntegerList(body, budget)) };
|
|
5404
|
+
}
|
|
5405
|
+
if (tag === COMPACT_BINARY_LIST_LIST && pipelineValues) {
|
|
5406
|
+
return { found: true, value: markCompactPipelineDecoded(decodeCompactBinaryListList(body, budget)) };
|
|
5407
|
+
}
|
|
5408
|
+
if (tag === COMPACT_BINARY_MAP_LIST && pipelineValues) {
|
|
5409
|
+
return { found: true, value: markCompactPipelineDecoded(decodeCompactBinaryMapList(body, budget)) };
|
|
5410
|
+
}
|
|
5411
|
+
if (tag === COMPACT_PIPELINE_RESPONSE && pipelineValues) {
|
|
4957
5412
|
return { found: true, value: decodeCompactPipeline(body, budget, hints.pipelineClaimModes) };
|
|
4958
5413
|
}
|
|
4959
|
-
if (tag === COMPACT_FLOW_CLAIM_JOBS &&
|
|
4960
|
-
|
|
5414
|
+
if (tag === COMPACT_FLOW_CLAIM_JOBS && (supports(hints, "flow_claim_jobs_v1", opcode) || pipelineValues)) {
|
|
5415
|
+
const values = decodeCompactClaimJobs(body, budget, hints.compactClaimMode);
|
|
5416
|
+
return {
|
|
5417
|
+
found: true,
|
|
5418
|
+
value: opcode === OPCODES.pipeline ? markCompactPipelineDecoded(values) : values
|
|
5419
|
+
};
|
|
4961
5420
|
}
|
|
4962
|
-
if (tag === COMPACT_FLOW_RECORD &&
|
|
5421
|
+
if (tag === COMPACT_FLOW_RECORD && supports(hints, "flow_record_v1", opcode)) {
|
|
4963
5422
|
const read = readCompactFlowRecord(body, 0, budget);
|
|
4964
5423
|
if (read.offset !== body.byteLength) throw new FerricStoreError("trailing compact Flow record bytes");
|
|
4965
5424
|
return { found: true, value: read.value };
|
|
4966
5425
|
}
|
|
4967
|
-
if (tag === COMPACT_FLOW_RECORD_LIST &&
|
|
5426
|
+
if (tag === COMPACT_FLOW_RECORD_LIST && (supports(hints, "flow_record_list_v1", opcode) || pipelineValues)) {
|
|
4968
5427
|
const read = readCompactFlowRecordList(body, 0, budget);
|
|
4969
5428
|
if (read.offset !== body.byteLength) throw new FerricStoreError("trailing compact Flow record list bytes");
|
|
4970
|
-
return {
|
|
5429
|
+
return {
|
|
5430
|
+
found: true,
|
|
5431
|
+
value: opcode === OPCODES.pipeline ? markCompactPipelineDecoded(read.value) : read.value
|
|
5432
|
+
};
|
|
4971
5433
|
}
|
|
4972
5434
|
return { found: false, value: void 0 };
|
|
4973
5435
|
}
|
|
4974
|
-
function
|
|
4975
|
-
return compactResponseOpcodeSupports(
|
|
4976
|
-
}
|
|
4977
|
-
function isFlowRecordListOpcode(opcode) {
|
|
4978
|
-
return compactResponseOpcodeSupports(opcode, COMPACT_KIND_FLOW_RECORD_LIST);
|
|
5436
|
+
function supports(hints, codec, opcode) {
|
|
5437
|
+
return compactResponseOpcodeSupports(hints.compactResponseOpcodes, codec, opcode);
|
|
4979
5438
|
}
|
|
4980
5439
|
function decodeCompactOkList(data, budget) {
|
|
4981
5440
|
requireAvailable(data, 0, 5);
|
|
4982
5441
|
const count = data.readUInt32BE(1);
|
|
4983
|
-
|
|
5442
|
+
requireCompactContainer2(count, budget);
|
|
4984
5443
|
if (data.byteLength !== 5) throw new FerricStoreError("invalid compact OK list response");
|
|
4985
|
-
return Array.from({ length: count }, () =>
|
|
5444
|
+
return Array.from({ length: count }, () => import_node_buffer19.Buffer.from("OK"));
|
|
4986
5445
|
}
|
|
4987
5446
|
function decodeCompactKvGet(data) {
|
|
4988
5447
|
requireAvailable(data, 0, 2);
|
|
@@ -4999,7 +5458,7 @@ function decodeCompactKvGet(data) {
|
|
|
4999
5458
|
function decodeCompactMget(data, budget) {
|
|
5000
5459
|
requireAvailable(data, 0, 5);
|
|
5001
5460
|
const count = data.readUInt32BE(1);
|
|
5002
|
-
|
|
5461
|
+
requireCompactContainer2(count, budget);
|
|
5003
5462
|
let offset = 5;
|
|
5004
5463
|
const values = [];
|
|
5005
5464
|
for (let index = 0; index < count; index += 1) {
|
|
@@ -5023,12 +5482,12 @@ function decodeCompactMgetFixed(data, budget) {
|
|
|
5023
5482
|
requireAvailable(data, 0, 9);
|
|
5024
5483
|
const count = data.readUInt32BE(1);
|
|
5025
5484
|
const size = data.readUInt32BE(5);
|
|
5026
|
-
|
|
5485
|
+
requireCompactContainer2(count, budget);
|
|
5027
5486
|
const expected = 9 + count * size;
|
|
5028
5487
|
if (size === NULL_U32 || data.byteLength !== expected) {
|
|
5029
5488
|
throw new FerricStoreError("invalid compact fixed MGET response");
|
|
5030
5489
|
}
|
|
5031
|
-
if (size === 0) return new Array(count).fill(
|
|
5490
|
+
if (size === 0) return new Array(count).fill(import_node_buffer19.Buffer.alloc(0));
|
|
5032
5491
|
const values = new Array(count);
|
|
5033
5492
|
for (let index = 0, offset = 9; index < count; index += 1, offset += size) {
|
|
5034
5493
|
values[index] = data.subarray(offset, offset + size);
|
|
@@ -5038,7 +5497,7 @@ function decodeCompactMgetFixed(data, budget) {
|
|
|
5038
5497
|
function decodeCompactPipeline(data, budget, claimModes) {
|
|
5039
5498
|
requireAvailable(data, 0, 5);
|
|
5040
5499
|
const count = data.readUInt32BE(1);
|
|
5041
|
-
|
|
5500
|
+
requireCompactContainer2(count, budget);
|
|
5042
5501
|
if (count > Math.floor((data.byteLength - 5) / 2)) {
|
|
5043
5502
|
throw new FerricStoreError("compact pipeline item count exceeds response bytes");
|
|
5044
5503
|
}
|
|
@@ -5100,13 +5559,12 @@ function decodeCompactPipeline(data, budget, claimModes) {
|
|
|
5100
5559
|
}
|
|
5101
5560
|
}
|
|
5102
5561
|
if (offset !== data.byteLength) throw new FerricStoreError("trailing compact pipeline bytes");
|
|
5103
|
-
|
|
5104
|
-
return values;
|
|
5562
|
+
return markCompactPipelineDecoded(values);
|
|
5105
5563
|
}
|
|
5106
5564
|
function decodeCompactClaimJobs(data, budget, mode) {
|
|
5107
5565
|
requireAvailable(data, 0, 5);
|
|
5108
5566
|
const count = data.readUInt32BE(1);
|
|
5109
|
-
|
|
5567
|
+
requireCompactContainer2(count, budget);
|
|
5110
5568
|
if (mode != null) {
|
|
5111
5569
|
const values = [];
|
|
5112
5570
|
let offset = 5;
|
|
@@ -5190,7 +5648,7 @@ function readCompactFlowRecord(data, offset, budget = { remainingItems: DEFAULT_
|
|
|
5190
5648
|
if (data.readUInt8(offset) !== COMPACT_FLOW_RECORD) throw new FerricStoreError("expected compact Flow record");
|
|
5191
5649
|
offset += 1;
|
|
5192
5650
|
const count = data.readUInt32BE(offset);
|
|
5193
|
-
|
|
5651
|
+
requireCompactContainer2(count, budget);
|
|
5194
5652
|
offset += 4;
|
|
5195
5653
|
const record = {};
|
|
5196
5654
|
for (let index = 0; index < count; index += 1) {
|
|
@@ -5218,7 +5676,7 @@ function readCompactFlowRecordList(data, offset, budget = { remainingItems: DEFA
|
|
|
5218
5676
|
}
|
|
5219
5677
|
offset += 1;
|
|
5220
5678
|
const count = data.readUInt32BE(offset);
|
|
5221
|
-
|
|
5679
|
+
requireCompactContainer2(count, budget);
|
|
5222
5680
|
offset += 4;
|
|
5223
5681
|
const records = [];
|
|
5224
5682
|
for (let index = 0; index < count; index += 1) {
|
|
@@ -5228,33 +5686,6 @@ function readCompactFlowRecordList(data, offset, budget = { remainingItems: DEFA
|
|
|
5228
5686
|
}
|
|
5229
5687
|
return { value: records, offset };
|
|
5230
5688
|
}
|
|
5231
|
-
function readCompactBinaryList(data, offset, budget) {
|
|
5232
|
-
requireAvailable(data, offset, 4);
|
|
5233
|
-
const count = data.readUInt32BE(offset);
|
|
5234
|
-
requireCompactContainer(count, budget);
|
|
5235
|
-
offset += 4;
|
|
5236
|
-
const values = [];
|
|
5237
|
-
for (let index = 0; index < count; index += 1) {
|
|
5238
|
-
const read = readBinary(data, offset);
|
|
5239
|
-
values.push(read.value);
|
|
5240
|
-
offset = read.offset;
|
|
5241
|
-
}
|
|
5242
|
-
return { value: values, offset };
|
|
5243
|
-
}
|
|
5244
|
-
function readCompactBinaryMap(data, offset, budget) {
|
|
5245
|
-
requireAvailable(data, offset, 4);
|
|
5246
|
-
const count = data.readUInt32BE(offset);
|
|
5247
|
-
requireCompactContainer(count, budget);
|
|
5248
|
-
offset += 4;
|
|
5249
|
-
const values = {};
|
|
5250
|
-
for (let index = 0; index < count; index += 1) {
|
|
5251
|
-
const key = readBinary(data, offset);
|
|
5252
|
-
const value = readBinary(data, key.offset);
|
|
5253
|
-
setOwnValue2(values, key.value.toString("utf8"), value.value);
|
|
5254
|
-
offset = value.offset;
|
|
5255
|
-
}
|
|
5256
|
-
return { value: values, offset };
|
|
5257
|
-
}
|
|
5258
5689
|
function readOptionalBinary(data, offset) {
|
|
5259
5690
|
requireAvailable(data, offset, 4);
|
|
5260
5691
|
const size = data.readUInt32BE(offset);
|
|
@@ -5263,7 +5694,7 @@ function readOptionalBinary(data, offset) {
|
|
|
5263
5694
|
requireAvailable(data, offset, size);
|
|
5264
5695
|
return { value: data.subarray(offset, offset + size), offset: offset + size };
|
|
5265
5696
|
}
|
|
5266
|
-
function
|
|
5697
|
+
function requireCompactContainer2(count, budget) {
|
|
5267
5698
|
if (count > DEFAULT_MAX_VALUE_ITEMS) {
|
|
5268
5699
|
throw new FerricStoreError("native compact response container exceeds max items");
|
|
5269
5700
|
}
|
|
@@ -5271,7 +5702,7 @@ function requireCompactContainer(count, budget) {
|
|
|
5271
5702
|
}
|
|
5272
5703
|
function errorMessage(status, value) {
|
|
5273
5704
|
if (typeof value === "string") return value;
|
|
5274
|
-
if (
|
|
5705
|
+
if (import_node_buffer19.Buffer.isBuffer(value)) return value.toString("utf8");
|
|
5275
5706
|
if (typeof value === "object" && value != null && Object.hasOwn(value, "message")) {
|
|
5276
5707
|
const message = value.message;
|
|
5277
5708
|
return typeof message === "string" ? message : String(message);
|
|
@@ -5351,7 +5782,7 @@ function unwrapPipelineResponse(value, options = {}, expectedItems) {
|
|
|
5351
5782
|
return out;
|
|
5352
5783
|
}
|
|
5353
5784
|
function pipelineStatus(value) {
|
|
5354
|
-
if (typeof value !== "string" && !
|
|
5785
|
+
if (typeof value !== "string" && !import_node_buffer20.Buffer.isBuffer(value) && !(value instanceof Uint8Array)) return null;
|
|
5355
5786
|
const status = asText(value).toLowerCase();
|
|
5356
5787
|
return status === "ok" || status === "busy" || status === "error" ? status : null;
|
|
5357
5788
|
}
|
|
@@ -5366,7 +5797,7 @@ function decodeResponseValue(opcode, body, hints) {
|
|
|
5366
5797
|
}
|
|
5367
5798
|
function errorMessage2(status, value) {
|
|
5368
5799
|
if (typeof value === "string") return value;
|
|
5369
|
-
if (
|
|
5800
|
+
if (import_node_buffer20.Buffer.isBuffer(value)) return value.toString("utf8");
|
|
5370
5801
|
if (typeof value === "object" && value != null && Object.hasOwn(value, "message")) {
|
|
5371
5802
|
const message = value.message;
|
|
5372
5803
|
return typeof message === "string" ? message : String(message);
|
|
@@ -5382,7 +5813,7 @@ function encodeRequest(command, requestId, maxBodyBytes = Number.MAX_SAFE_INTEGE
|
|
|
5382
5813
|
const bodyLength = customPayload ? binaryValueByteLength(command.payload) : plan?.byteLength ?? 0;
|
|
5383
5814
|
if (bodyLength > bodyLimit) throw requestFrameTooLarge(bodyLimit);
|
|
5384
5815
|
const flags = command.flags ?? 0;
|
|
5385
|
-
const frame =
|
|
5816
|
+
const frame = import_node_buffer21.Buffer.allocUnsafe(HEADER_SIZE + bodyLength);
|
|
5386
5817
|
frame.write(MAGIC, 0, "ascii");
|
|
5387
5818
|
frame.writeUInt8(REQUEST_VERSION, 4);
|
|
5388
5819
|
frame.writeUInt8(flags, 5);
|
|
@@ -5433,6 +5864,9 @@ function buildProtocolCommand(args, maxBodyBytes = Number.MAX_SAFE_INTEGER, allo
|
|
|
5433
5864
|
}
|
|
5434
5865
|
const command = asText(args[0]).toUpperCase();
|
|
5435
5866
|
assertNormalizedCommandDoesNotRequirePinnedConnection(args, command);
|
|
5867
|
+
if (command === "MSET" || command === "MSETNX") {
|
|
5868
|
+
assertKeyValueCommandSharesSlot(args, command);
|
|
5869
|
+
}
|
|
5436
5870
|
const commandArgs2 = args.slice(1);
|
|
5437
5871
|
if (command === "COMMAND_EXEC" && commandArgs2.length >= 1) {
|
|
5438
5872
|
return commandExec(commandArgs2);
|
|
@@ -5570,20 +6004,7 @@ function buildProtocolCommand(args, maxBodyBytes = Number.MAX_SAFE_INTEGER, allo
|
|
|
5570
6004
|
])) ?? commandExec(args);
|
|
5571
6005
|
}
|
|
5572
6006
|
if (command === "FLOW.SIGNAL") {
|
|
5573
|
-
return
|
|
5574
|
-
"SIGNAL",
|
|
5575
|
-
"PARTITION",
|
|
5576
|
-
"IDEMPOTENCY",
|
|
5577
|
-
"IF_STATE",
|
|
5578
|
-
"TRANSITION_TO",
|
|
5579
|
-
"RUN_AT",
|
|
5580
|
-
"NOW",
|
|
5581
|
-
"PRIORITY",
|
|
5582
|
-
"VALUE",
|
|
5583
|
-
"VALUE_REF",
|
|
5584
|
-
"DROP_VALUE",
|
|
5585
|
-
"OVERRIDE_VALUE"
|
|
5586
|
-
]));
|
|
6007
|
+
return flowSignalPayload(commandArgs2) ?? commandExec(args);
|
|
5587
6008
|
}
|
|
5588
6009
|
if (command === "FLOW.CANCEL") {
|
|
5589
6010
|
return flowCommandExecWithRouting(command, commandArgs2, 1, /* @__PURE__ */ new Set([
|
|
@@ -5752,6 +6173,7 @@ var DEFAULT_MAX_PENDING_CONTROL_REQUESTS = 4096;
|
|
|
5752
6173
|
var DEFAULT_MAX_RESPONSE_BYTES = 64 * 1024 * 1024;
|
|
5753
6174
|
var DEFAULT_MAX_QUEUED_REQUESTS = 65536;
|
|
5754
6175
|
var DEFAULT_MAX_QUEUED_WRITE_BYTES = 64 * 1024 * 1024;
|
|
6176
|
+
var UNAUTHENTICATED_MAX_FRAME_BYTES = 64 * 1024;
|
|
5755
6177
|
function assertNativeAdapterOptions(options) {
|
|
5756
6178
|
const supplied = options;
|
|
5757
6179
|
for (const name of ["autoReconnect", "haRouting", "seeds"]) {
|
|
@@ -5771,7 +6193,7 @@ var import_node_net2 = require("net");
|
|
|
5771
6193
|
var import_node_tls2 = require("tls");
|
|
5772
6194
|
|
|
5773
6195
|
// src/client-native-options.ts
|
|
5774
|
-
var
|
|
6196
|
+
var import_node_buffer22 = require("buffer");
|
|
5775
6197
|
|
|
5776
6198
|
// src/string-array-snapshot.ts
|
|
5777
6199
|
function snapshotOwnStringArray(values, name) {
|
|
@@ -5854,7 +6276,7 @@ function snapshotTlsOptions(options) {
|
|
|
5854
6276
|
return Object.freeze(snapshot);
|
|
5855
6277
|
}
|
|
5856
6278
|
function snapshotTlsValue(value, name) {
|
|
5857
|
-
if (
|
|
6279
|
+
if (import_node_buffer22.Buffer.isBuffer(value)) return import_node_buffer22.Buffer.from(value);
|
|
5858
6280
|
if (value instanceof Uint8Array) return value.slice();
|
|
5859
6281
|
if (Array.isArray(value)) {
|
|
5860
6282
|
const snapshot = new Array(value.length);
|
|
@@ -6324,6 +6746,9 @@ var NativeChunkAssembler = class {
|
|
|
6324
6746
|
framesByKey = /* @__PURE__ */ new Map();
|
|
6325
6747
|
totalBytes = 0;
|
|
6326
6748
|
totalFrames = 0;
|
|
6749
|
+
updateMaxResponseBytes(limit) {
|
|
6750
|
+
this.maxResponseBytes = Math.min(this.maxResponseBytes, limit);
|
|
6751
|
+
}
|
|
6327
6752
|
assemble(frame) {
|
|
6328
6753
|
const key = `${frame.requestId}:${frame.opcode}:${frame.laneId}`;
|
|
6329
6754
|
const previous = this.chunks.get(key);
|
|
@@ -6406,7 +6831,7 @@ var NativeChunkAssembler = class {
|
|
|
6406
6831
|
};
|
|
6407
6832
|
|
|
6408
6833
|
// src/native-response-handler.ts
|
|
6409
|
-
var
|
|
6834
|
+
var import_node_buffer23 = require("buffer");
|
|
6410
6835
|
|
|
6411
6836
|
// src/native-receive-buffer.ts
|
|
6412
6837
|
var FRAME_ASSEMBLY_PAGE_BYTES = 64 * 1024;
|
|
@@ -6568,12 +6993,18 @@ var NativeReceiveBuffer = class {
|
|
|
6568
6993
|
var NativeResponseHandler = class {
|
|
6569
6994
|
constructor(options) {
|
|
6570
6995
|
this.options = options;
|
|
6996
|
+
this.maxResponseBytes = options.maxResponseBytes;
|
|
6571
6997
|
}
|
|
6572
6998
|
options;
|
|
6573
6999
|
receiveBuffer = new NativeReceiveBuffer();
|
|
6574
7000
|
drainScheduled = false;
|
|
6575
7001
|
paused = false;
|
|
6576
7002
|
stopped = false;
|
|
7003
|
+
maxResponseBytes;
|
|
7004
|
+
updateMaxResponseBytes(limit) {
|
|
7005
|
+
this.maxResponseBytes = Math.min(this.maxResponseBytes, limit);
|
|
7006
|
+
this.options.chunkAssembler.updateMaxResponseBytes(this.maxResponseBytes);
|
|
7007
|
+
}
|
|
6577
7008
|
onData(chunk) {
|
|
6578
7009
|
if (this.stopped) return;
|
|
6579
7010
|
try {
|
|
@@ -6655,15 +7086,18 @@ var NativeResponseHandler = class {
|
|
|
6655
7086
|
}
|
|
6656
7087
|
const completeFrame = this.options.chunkAssembler.assemble(frame);
|
|
6657
7088
|
if (completeFrame == null) return;
|
|
6658
|
-
if (completeFrame.body.byteLength > this.
|
|
7089
|
+
if (completeFrame.body.byteLength > this.maxResponseBytes) {
|
|
6659
7090
|
throw new FerricStoreError(
|
|
6660
|
-
`native protocol response exceeded ${this.
|
|
7091
|
+
`native protocol response exceeded ${this.maxResponseBytes} bytes`
|
|
6661
7092
|
);
|
|
6662
7093
|
}
|
|
6663
7094
|
let value;
|
|
6664
7095
|
let responseError;
|
|
6665
7096
|
try {
|
|
6666
|
-
value = decodeResponse(completeFrame, pending.opcode,
|
|
7097
|
+
value = decodeResponse(completeFrame, pending.opcode, {
|
|
7098
|
+
...pending,
|
|
7099
|
+
compactResponseOpcodes: this.options.compactResponseOpcodes?.() ?? EMPTY_COMPACT_RESPONSE_OPCODES
|
|
7100
|
+
});
|
|
6667
7101
|
if (pending.opcode === OPCODES.windowUpdate) this.options.applyFlowControlLimits(value);
|
|
6668
7102
|
} catch (error) {
|
|
6669
7103
|
responseError = error;
|
|
@@ -6679,7 +7113,7 @@ var NativeResponseHandler = class {
|
|
|
6679
7113
|
pending.discardedResponseBytes = discardedResponseBytes;
|
|
6680
7114
|
pending.discardedResponseFrames = discardedResponseFrames;
|
|
6681
7115
|
const chunked = discardedResponseFrames > 1 || (frame.flags & FLAG_MORE_CHUNKS) !== 0;
|
|
6682
|
-
if (discardedResponseBytes > this.
|
|
7116
|
+
if (discardedResponseBytes > this.maxResponseBytes || chunked && discardedResponseBytes > this.options.maxChunkBytes) {
|
|
6683
7117
|
throw new FerricStoreError("native protocol discarded response exceeded configured byte limits");
|
|
6684
7118
|
}
|
|
6685
7119
|
if (discardedResponseFrames > this.options.maxChunkFrames) {
|
|
@@ -6688,12 +7122,14 @@ var NativeResponseHandler = class {
|
|
|
6688
7122
|
if ((frame.flags & FLAG_MORE_CHUNKS) === 0) this.options.takePending(frame.requestId);
|
|
6689
7123
|
}
|
|
6690
7124
|
handleManagementFrame(frame) {
|
|
6691
|
-
if (frame.body.byteLength > this.
|
|
7125
|
+
if (frame.body.byteLength > this.maxResponseBytes) {
|
|
6692
7126
|
throw new FerricStoreError(
|
|
6693
|
-
`native protocol response exceeded ${this.
|
|
7127
|
+
`native protocol response exceeded ${this.maxResponseBytes} bytes`
|
|
6694
7128
|
);
|
|
6695
7129
|
}
|
|
6696
|
-
const value = decodeResponse(frame, frame.opcode
|
|
7130
|
+
const value = decodeResponse(frame, frame.opcode, {
|
|
7131
|
+
compactResponseOpcodes: this.options.compactResponseOpcodes?.() ?? EMPTY_COMPACT_RESPONSE_OPCODES
|
|
7132
|
+
});
|
|
6697
7133
|
if (frame.opcode === OPCODES.windowUpdate) this.options.applyFlowControlLimits(value);
|
|
6698
7134
|
const event = {
|
|
6699
7135
|
flags: frame.flags,
|
|
@@ -6730,7 +7166,7 @@ var NativeRequestScheduler = class {
|
|
|
6730
7166
|
};
|
|
6731
7167
|
|
|
6732
7168
|
// src/native-write-queue.ts
|
|
6733
|
-
var
|
|
7169
|
+
var import_node_buffer24 = require("buffer");
|
|
6734
7170
|
var NativeWriteQueue = class {
|
|
6735
7171
|
constructor(socket, maxQueuedWriteBytes, isClosed, hasPending, rejectPending) {
|
|
6736
7172
|
this.socket = socket;
|
|
@@ -6858,6 +7294,40 @@ var NativeWriteQueue = class {
|
|
|
6858
7294
|
}
|
|
6859
7295
|
};
|
|
6860
7296
|
|
|
7297
|
+
// src/native-connection-capabilities.ts
|
|
7298
|
+
var NativeConnectionCapabilities = class {
|
|
7299
|
+
constructor(configuredRequestFrameBytes) {
|
|
7300
|
+
this.configuredRequestFrameBytes = configuredRequestFrameBytes;
|
|
7301
|
+
this.negotiatedRequestFrameBytes = configuredRequestFrameBytes;
|
|
7302
|
+
this.requestFrameBytes = Math.min(configuredRequestFrameBytes, UNAUTHENTICATED_MAX_FRAME_BYTES);
|
|
7303
|
+
}
|
|
7304
|
+
configuredRequestFrameBytes;
|
|
7305
|
+
compactResponseOpcodes = EMPTY_COMPACT_RESPONSE_OPCODES;
|
|
7306
|
+
requestFrameBytes;
|
|
7307
|
+
negotiatedRequestFrameBytes;
|
|
7308
|
+
apply(value) {
|
|
7309
|
+
const limits = startupLimits(value);
|
|
7310
|
+
const negotiation = nativeNegotiation(value);
|
|
7311
|
+
this.compactResponseOpcodes = negotiation.compactResponseOpcodes;
|
|
7312
|
+
if (limits.frameBytes != null) {
|
|
7313
|
+
this.negotiatedRequestFrameBytes = Math.min(
|
|
7314
|
+
this.configuredRequestFrameBytes,
|
|
7315
|
+
limits.frameBytes
|
|
7316
|
+
);
|
|
7317
|
+
this.requestFrameBytes = Math.min(this.requestFrameBytes, this.negotiatedRequestFrameBytes);
|
|
7318
|
+
}
|
|
7319
|
+
return {
|
|
7320
|
+
...limits.laneQueue == null ? {} : { laneQueue: limits.laneQueue },
|
|
7321
|
+
...limits.lanes == null ? {} : { lanes: limits.lanes },
|
|
7322
|
+
...negotiation.maxResponseBytes == null ? {} : { maxResponseBytes: negotiation.maxResponseBytes },
|
|
7323
|
+
...limits.pipelineCommands == null ? {} : { pipelineCommands: limits.pipelineCommands }
|
|
7324
|
+
};
|
|
7325
|
+
}
|
|
7326
|
+
activateAuthenticated() {
|
|
7327
|
+
this.requestFrameBytes = this.negotiatedRequestFrameBytes;
|
|
7328
|
+
}
|
|
7329
|
+
};
|
|
7330
|
+
|
|
6861
7331
|
// src/native-adapter.ts
|
|
6862
7332
|
var NativeAdapter = class _NativeAdapter {
|
|
6863
7333
|
socket;
|
|
@@ -6866,9 +7336,9 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
6866
7336
|
closedWaiters = /* @__PURE__ */ new Set();
|
|
6867
7337
|
chunkAssembler;
|
|
6868
7338
|
closed = false;
|
|
7339
|
+
capabilities;
|
|
6869
7340
|
protocolLanes;
|
|
6870
7341
|
maxPipelineCommands = Number.MAX_SAFE_INTEGER;
|
|
6871
|
-
maxRequestFrameBytes;
|
|
6872
7342
|
pendingControlRequests = 0;
|
|
6873
7343
|
maxPendingControlRequests;
|
|
6874
7344
|
heartbeat;
|
|
@@ -6883,7 +7353,7 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
6883
7353
|
const normalizedMaxChunkBytes = normalizePositiveLimit(maxChunkBytes, DEFAULT_MAX_CHUNK_BYTES);
|
|
6884
7354
|
const normalizedMaxChunkFrames = normalizePositiveLimit(maxChunkFrames, DEFAULT_MAX_CHUNK_FRAMES);
|
|
6885
7355
|
const normalizedMaxFrameBytes = normalizePositiveLimit(maxFrameBytes, DEFAULT_MAX_FRAME_BYTES);
|
|
6886
|
-
this.
|
|
7356
|
+
this.capabilities = new NativeConnectionCapabilities(normalizedMaxFrameBytes);
|
|
6887
7357
|
const normalizedMaxResponseBytes = normalizePositiveLimit(maxResponseBytes, DEFAULT_MAX_RESPONSE_BYTES);
|
|
6888
7358
|
this.chunkAssembler = new NativeChunkAssembler(
|
|
6889
7359
|
normalizedMaxChunkBytes,
|
|
@@ -6910,7 +7380,7 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
6910
7380
|
this.heartbeat = new NativeHeartbeat(
|
|
6911
7381
|
this.heartbeatIntervalMs,
|
|
6912
7382
|
async () => {
|
|
6913
|
-
await this.request(buildProtocolCommand(["PING"], this.
|
|
7383
|
+
await this.request(buildProtocolCommand(["PING"], this.capabilities.requestFrameBytes), true);
|
|
6914
7384
|
},
|
|
6915
7385
|
(error) => {
|
|
6916
7386
|
this.failAll(new FerricStoreError("FerricStore protocol heartbeat failed", { cause: error }), true);
|
|
@@ -6921,6 +7391,7 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
6921
7391
|
applyFlowControlLimits: (value) => this.applyFlowControlLimits(value),
|
|
6922
7392
|
beginDraining: () => this.beginDraining(),
|
|
6923
7393
|
chunkAssembler: this.chunkAssembler,
|
|
7394
|
+
compactResponseOpcodes: () => this.capabilities.compactResponseOpcodes,
|
|
6924
7395
|
destroy: (error) => this.socket.destroy(error),
|
|
6925
7396
|
failAll: (reason, connectionClosed, message) => this.failAll(reason, connectionClosed, message),
|
|
6926
7397
|
heartbeat: this.heartbeat,
|
|
@@ -6946,6 +7417,7 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
6946
7417
|
adapter,
|
|
6947
7418
|
auth: async (username, password) => {
|
|
6948
7419
|
await adapter.request({ laneId: 0, opcode: OPCODES.auth, payload: { password, username } });
|
|
7420
|
+
adapter.capabilities.activateAuthenticated();
|
|
6949
7421
|
},
|
|
6950
7422
|
close: async () => {
|
|
6951
7423
|
await adapter.close();
|
|
@@ -6963,13 +7435,13 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
6963
7435
|
return await this.executeCommandArgs(args);
|
|
6964
7436
|
}
|
|
6965
7437
|
async executeCommandArgs(args) {
|
|
6966
|
-
const command = buildProtocolCommand(args, this.
|
|
7438
|
+
const command = buildProtocolCommand(args, this.capabilities.requestFrameBytes);
|
|
6967
7439
|
return await this.request(command);
|
|
6968
7440
|
}
|
|
6969
7441
|
/** @internal Execute raw command arguments on a topology-selected lane. */
|
|
6970
7442
|
async executeCommandOnLane(args, laneId) {
|
|
6971
7443
|
return await this.executeProtocolCommand(
|
|
6972
|
-
buildProtocolCommand(args, this.
|
|
7444
|
+
buildProtocolCommand(args, this.capabilities.requestFrameBytes),
|
|
6973
7445
|
laneId
|
|
6974
7446
|
);
|
|
6975
7447
|
}
|
|
@@ -6991,7 +7463,7 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
6991
7463
|
laneId,
|
|
6992
7464
|
options,
|
|
6993
7465
|
this.maxPipelineCommands,
|
|
6994
|
-
this.
|
|
7466
|
+
this.capabilities.requestFrameBytes
|
|
6995
7467
|
);
|
|
6996
7468
|
}
|
|
6997
7469
|
/** @internal Execute an ordered pipeline on a topology-selected lane. */
|
|
@@ -7002,13 +7474,11 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
7002
7474
|
laneId,
|
|
7003
7475
|
options,
|
|
7004
7476
|
this.maxPipelineCommands,
|
|
7005
|
-
this.
|
|
7477
|
+
this.capabilities.requestFrameBytes
|
|
7006
7478
|
);
|
|
7007
7479
|
}
|
|
7008
7480
|
async close() {
|
|
7009
|
-
if (this.closed)
|
|
7010
|
-
return;
|
|
7011
|
-
}
|
|
7481
|
+
if (this.closed) return;
|
|
7012
7482
|
this.failAll(new FerricStoreError("FerricStore connection closed"), true);
|
|
7013
7483
|
this.socket.destroy();
|
|
7014
7484
|
}
|
|
@@ -7026,7 +7496,9 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
7026
7496
|
});
|
|
7027
7497
|
this.applyStartupLimits(response);
|
|
7028
7498
|
const authRequired = field(response, "auth_required");
|
|
7029
|
-
|
|
7499
|
+
const required = authRequired == null ? false : booleanResponse(authRequired);
|
|
7500
|
+
if (authRequired != null && !required) this.capabilities.activateAuthenticated();
|
|
7501
|
+
return required;
|
|
7030
7502
|
}
|
|
7031
7503
|
request(command, allowWhileDraining = false) {
|
|
7032
7504
|
if (this.closed || this.draining && !allowWhileDraining) {
|
|
@@ -7067,7 +7539,7 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
7067
7539
|
let frame;
|
|
7068
7540
|
try {
|
|
7069
7541
|
requestId = this.requestScheduler.nextRequestId();
|
|
7070
|
-
frame = encodeRequest(command, requestId, this.
|
|
7542
|
+
frame = encodeRequest(command, requestId, this.capabilities.requestFrameBytes);
|
|
7071
7543
|
} catch (error) {
|
|
7072
7544
|
if (hasFlowControlCredit) this.flowControl.release(laneId);
|
|
7073
7545
|
return Promise.reject(error instanceof Error ? error : new FerricStoreError(String(error), { raw: error }));
|
|
@@ -7121,9 +7593,7 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
7121
7593
|
this.resolveClosedWaiters();
|
|
7122
7594
|
}
|
|
7123
7595
|
failAll(reason, connectionClosed = false, dispatchedMessage) {
|
|
7124
|
-
if (this.closed)
|
|
7125
|
-
return;
|
|
7126
|
-
}
|
|
7596
|
+
if (this.closed) return;
|
|
7127
7597
|
this.closed = true;
|
|
7128
7598
|
this.responseHandler.stop();
|
|
7129
7599
|
this.resolveClosedWaiters();
|
|
@@ -7189,18 +7659,18 @@ var NativeAdapter = class _NativeAdapter {
|
|
|
7189
7659
|
}
|
|
7190
7660
|
applyStartupLimits(value) {
|
|
7191
7661
|
this.applyFlowControlLimits(value);
|
|
7192
|
-
const
|
|
7193
|
-
if (
|
|
7194
|
-
this.
|
|
7662
|
+
const capabilities = this.capabilities.apply(value);
|
|
7663
|
+
if (capabilities.maxResponseBytes != null) {
|
|
7664
|
+
this.responseHandler.updateMaxResponseBytes(capabilities.maxResponseBytes);
|
|
7195
7665
|
}
|
|
7196
|
-
if (
|
|
7197
|
-
this.
|
|
7666
|
+
if (capabilities.laneQueue != null) {
|
|
7667
|
+
this.flowControl.updateLaneQueueLimit(capabilities.laneQueue);
|
|
7198
7668
|
}
|
|
7199
|
-
if (
|
|
7200
|
-
this.
|
|
7669
|
+
if (capabilities.lanes != null) {
|
|
7670
|
+
this.protocolLanes = Math.min(this.protocolLanes, capabilities.lanes);
|
|
7201
7671
|
}
|
|
7202
|
-
if (
|
|
7203
|
-
this.
|
|
7672
|
+
if (capabilities.pipelineCommands != null) {
|
|
7673
|
+
this.maxPipelineCommands = capabilities.pipelineCommands;
|
|
7204
7674
|
}
|
|
7205
7675
|
}
|
|
7206
7676
|
};
|
|
@@ -7213,7 +7683,7 @@ function executeCommandArgs(executor, args) {
|
|
|
7213
7683
|
}
|
|
7214
7684
|
|
|
7215
7685
|
// src/reconnecting-executor.ts
|
|
7216
|
-
var
|
|
7686
|
+
var import_node_buffer26 = require("buffer");
|
|
7217
7687
|
var ReconnectingExecutor = class {
|
|
7218
7688
|
constructor(createExecutor, options = {}) {
|
|
7219
7689
|
this.createExecutor = createExecutor;
|
|
@@ -7408,217 +7878,11 @@ function normalizeNonNegativeInteger2(value, fallback) {
|
|
|
7408
7878
|
}
|
|
7409
7879
|
|
|
7410
7880
|
// src/topology.ts
|
|
7411
|
-
var
|
|
7881
|
+
var import_node_buffer28 = require("buffer");
|
|
7412
7882
|
|
|
7413
7883
|
// src/topology-routing.ts
|
|
7414
|
-
var
|
|
7884
|
+
var import_node_buffer27 = require("buffer");
|
|
7415
7885
|
var import_node_crypto = require("crypto");
|
|
7416
|
-
|
|
7417
|
-
// src/topology-utilities.ts
|
|
7418
|
-
var import_node_buffer24 = require("buffer");
|
|
7419
|
-
function isPlainObject3(value) {
|
|
7420
|
-
return typeof value === "object" && value != null && !Array.isArray(value) && !import_node_buffer24.Buffer.isBuffer(value);
|
|
7421
|
-
}
|
|
7422
|
-
function getField(source, ...keys) {
|
|
7423
|
-
if (source instanceof Map) {
|
|
7424
|
-
for (const key of keys) {
|
|
7425
|
-
if (source.has(key)) return source.get(key);
|
|
7426
|
-
const bufferKey = import_node_buffer24.Buffer.from(key);
|
|
7427
|
-
for (const [itemKey, value] of source.entries()) {
|
|
7428
|
-
if (import_node_buffer24.Buffer.isBuffer(itemKey) && itemKey.equals(bufferKey)) return value;
|
|
7429
|
-
}
|
|
7430
|
-
}
|
|
7431
|
-
return void 0;
|
|
7432
|
-
}
|
|
7433
|
-
if (isPlainObject3(source)) {
|
|
7434
|
-
for (const key of keys) {
|
|
7435
|
-
if (Object.hasOwn(source, key)) return source[key];
|
|
7436
|
-
}
|
|
7437
|
-
}
|
|
7438
|
-
return void 0;
|
|
7439
|
-
}
|
|
7440
|
-
function textOrUndefined(value) {
|
|
7441
|
-
if (typeof value === "string") return value;
|
|
7442
|
-
if (import_node_buffer24.Buffer.isBuffer(value)) return value.toString("utf8");
|
|
7443
|
-
return void 0;
|
|
7444
|
-
}
|
|
7445
|
-
function numberOrUndefined(value) {
|
|
7446
|
-
return typeof value === "number" && Number.isSafeInteger(value) ? value : void 0;
|
|
7447
|
-
}
|
|
7448
|
-
function nativeEventName(event) {
|
|
7449
|
-
return textOrUndefined(getField(event.value, "event"))?.toUpperCase();
|
|
7450
|
-
}
|
|
7451
|
-
function endpointFromRange(item) {
|
|
7452
|
-
const endpointValue = getField(item, "endpoint");
|
|
7453
|
-
if (endpointValue != null && !isPlainObject3(endpointValue) && !(endpointValue instanceof Map)) {
|
|
7454
|
-
throw new FerricStoreError("invalid SHARDS endpoint", { raw: item });
|
|
7455
|
-
}
|
|
7456
|
-
const raw = endpointValue ?? item;
|
|
7457
|
-
const host = textOrUndefined(getField(raw, "host", "native_host"));
|
|
7458
|
-
const nativePort = numberOrUndefined(getField(raw, "native_port"));
|
|
7459
|
-
if (host == null || !validEndpointHost(host) || nativePort == null || nativePort <= 0 || nativePort > 65535) {
|
|
7460
|
-
throw new FerricStoreError("invalid SHARDS endpoint", { raw: item });
|
|
7461
|
-
}
|
|
7462
|
-
const nativeTlsPortValue = getField(raw, "native_tls_port");
|
|
7463
|
-
const nativeTlsPort = numberOrUndefined(nativeTlsPortValue);
|
|
7464
|
-
if (nativeTlsPortValue != null && (nativeTlsPort == null || nativeTlsPort <= 0 || nativeTlsPort > 65535)) {
|
|
7465
|
-
throw new FerricStoreError("invalid SHARDS endpoint", { raw: item });
|
|
7466
|
-
}
|
|
7467
|
-
return {
|
|
7468
|
-
host,
|
|
7469
|
-
nativePort,
|
|
7470
|
-
node: textOrUndefined(getField(raw, "node", "leader_node", "owner_node")) ?? host,
|
|
7471
|
-
...nativeTlsPort == null ? {} : { nativeTlsPort }
|
|
7472
|
-
};
|
|
7473
|
-
}
|
|
7474
|
-
function validEndpointHost(host) {
|
|
7475
|
-
if (host.length === 0 || host.trim() !== host || /[\s\\/?#@]/u.test(host)) return false;
|
|
7476
|
-
const authorityHost = host.includes(":") && !host.startsWith("[") ? `[${host}]` : host;
|
|
7477
|
-
try {
|
|
7478
|
-
const url = new URL(`ferric://${authorityHost}:6388`);
|
|
7479
|
-
return url.hostname !== "" && url.port === "6388" && url.username === "" && url.password === "";
|
|
7480
|
-
} catch {
|
|
7481
|
-
return false;
|
|
7482
|
-
}
|
|
7483
|
-
}
|
|
7484
|
-
function sameEndpoint(left, right) {
|
|
7485
|
-
return normalizedEndpointHost(left.host) === normalizedEndpointHost(right.host) && left.nativePort === right.nativePort && left.nativeTlsPort === right.nativeTlsPort && left.node === right.node;
|
|
7486
|
-
}
|
|
7487
|
-
function parseFerricUrl2(value) {
|
|
7488
|
-
const url = new URL(value);
|
|
7489
|
-
if (url.protocol !== "ferric:" && url.protocol !== "ferrics:") {
|
|
7490
|
-
throw new FerricStoreError(`unsupported FerricStore URL scheme: ${url.protocol}`);
|
|
7491
|
-
}
|
|
7492
|
-
return {
|
|
7493
|
-
host: normalizeFerricUrlHost(url.hostname),
|
|
7494
|
-
...url.password === "" ? {} : { password: decodeURIComponent(url.password) },
|
|
7495
|
-
port: Number(url.port || (url.protocol === "ferrics:" ? 6389 : 6388)),
|
|
7496
|
-
tls: url.protocol === "ferrics:",
|
|
7497
|
-
...url.username === "" ? {} : { username: decodeURIComponent(url.username) }
|
|
7498
|
-
};
|
|
7499
|
-
}
|
|
7500
|
-
function endpointKeyFor(endpoint) {
|
|
7501
|
-
return `${normalizedEndpointHost(endpoint.host)}:${endpoint.nativePort}`;
|
|
7502
|
-
}
|
|
7503
|
-
function connectionKeyForEndpoint(endpoint, useTls) {
|
|
7504
|
-
const port = useTls && endpoint.nativeTlsPort != null ? endpoint.nativeTlsPort : endpoint.nativePort;
|
|
7505
|
-
return `${useTls ? "ferrics" : "ferric"}://${normalizedEndpointHost(endpoint.host)}:${port}`;
|
|
7506
|
-
}
|
|
7507
|
-
function connectionKeyFromUrl(url) {
|
|
7508
|
-
const parsed = parseFerricUrl2(url);
|
|
7509
|
-
return `${parsed.tls ? "ferrics" : "ferric"}://${normalizedEndpointHost(parsed.host)}:${parsed.port}`;
|
|
7510
|
-
}
|
|
7511
|
-
function normalizedEndpointHost(host) {
|
|
7512
|
-
const lower = host.toLowerCase();
|
|
7513
|
-
return lower.startsWith("[") && lower.endsWith("]") ? lower.slice(1, -1) : lower;
|
|
7514
|
-
}
|
|
7515
|
-
function urlFromEndpoint(endpoint, useTls) {
|
|
7516
|
-
const port = useTls && endpoint.nativeTlsPort != null ? endpoint.nativeTlsPort : endpoint.nativePort;
|
|
7517
|
-
const host = endpoint.host.includes(":") && !endpoint.host.startsWith("[") ? `[${endpoint.host}]` : endpoint.host;
|
|
7518
|
-
return `${useTls ? "ferrics" : "ferric"}://${host}:${port}`;
|
|
7519
|
-
}
|
|
7520
|
-
async function mapSettledWithConcurrency(items, concurrency, operation) {
|
|
7521
|
-
const results = new Array(items.length);
|
|
7522
|
-
let nextIndex = 0;
|
|
7523
|
-
const worker = async () => {
|
|
7524
|
-
while (nextIndex < items.length) {
|
|
7525
|
-
const index = nextIndex++;
|
|
7526
|
-
const item = items[index];
|
|
7527
|
-
try {
|
|
7528
|
-
results[index] = { status: "fulfilled", value: await operation(item, index) };
|
|
7529
|
-
} catch (reason) {
|
|
7530
|
-
results[index] = { status: "rejected", reason };
|
|
7531
|
-
}
|
|
7532
|
-
}
|
|
7533
|
-
};
|
|
7534
|
-
await Promise.all(Array.from(
|
|
7535
|
-
{ length: Math.min(concurrency, items.length) },
|
|
7536
|
-
async () => await worker()
|
|
7537
|
-
));
|
|
7538
|
-
return results;
|
|
7539
|
-
}
|
|
7540
|
-
function throwFirstRejected(results) {
|
|
7541
|
-
for (const result of results) {
|
|
7542
|
-
if (result.status === "rejected") throw result.reason;
|
|
7543
|
-
}
|
|
7544
|
-
}
|
|
7545
|
-
var TaskConcurrencyLimiter = class {
|
|
7546
|
-
constructor(concurrency) {
|
|
7547
|
-
this.concurrency = concurrency;
|
|
7548
|
-
}
|
|
7549
|
-
concurrency;
|
|
7550
|
-
active = 0;
|
|
7551
|
-
head = 0;
|
|
7552
|
-
pending = [];
|
|
7553
|
-
async run(operation) {
|
|
7554
|
-
await this.acquire();
|
|
7555
|
-
try {
|
|
7556
|
-
return await operation();
|
|
7557
|
-
} finally {
|
|
7558
|
-
this.release();
|
|
7559
|
-
}
|
|
7560
|
-
}
|
|
7561
|
-
acquire() {
|
|
7562
|
-
if (this.active < this.concurrency) {
|
|
7563
|
-
this.active += 1;
|
|
7564
|
-
return Promise.resolve();
|
|
7565
|
-
}
|
|
7566
|
-
return new Promise((resolve) => this.pending.push(resolve));
|
|
7567
|
-
}
|
|
7568
|
-
release() {
|
|
7569
|
-
const next = this.pending[this.head];
|
|
7570
|
-
if (next == null) {
|
|
7571
|
-
this.active -= 1;
|
|
7572
|
-
return;
|
|
7573
|
-
}
|
|
7574
|
-
this.head += 1;
|
|
7575
|
-
next();
|
|
7576
|
-
if (this.head === this.pending.length) {
|
|
7577
|
-
this.pending.length = 0;
|
|
7578
|
-
this.head = 0;
|
|
7579
|
-
} else if (this.head >= 1024 && this.head * 2 >= this.pending.length) {
|
|
7580
|
-
this.pending.splice(0, this.head);
|
|
7581
|
-
this.head = 0;
|
|
7582
|
-
}
|
|
7583
|
-
}
|
|
7584
|
-
};
|
|
7585
|
-
function normalizedHostSet(hosts) {
|
|
7586
|
-
return new Set(
|
|
7587
|
-
hosts.filter((host) => host != null && host !== "").map((host) => normalizedEndpointHost(host))
|
|
7588
|
-
);
|
|
7589
|
-
}
|
|
7590
|
-
function bufferStartsWith(value, prefix) {
|
|
7591
|
-
return value.byteLength >= prefix.byteLength && value.subarray(0, prefix.byteLength).equals(prefix);
|
|
7592
|
-
}
|
|
7593
|
-
var OPEN_BRACE = "{".charCodeAt(0);
|
|
7594
|
-
var CLOSE_BRACE = "}".charCodeAt(0);
|
|
7595
|
-
function hashTagOrKey(key) {
|
|
7596
|
-
const start = key.indexOf(OPEN_BRACE);
|
|
7597
|
-
if (start < 0) return key;
|
|
7598
|
-
const end = key.indexOf(CLOSE_BRACE, start + 1);
|
|
7599
|
-
return end > start + 1 ? key.subarray(start + 1, end) : key;
|
|
7600
|
-
}
|
|
7601
|
-
function flowHashTag(rest, fallbackKey) {
|
|
7602
|
-
const end = rest.indexOf(CLOSE_BRACE);
|
|
7603
|
-
return end > 0 ? rest.subarray(0, end) : hashTagOrKey(fallbackKey);
|
|
7604
|
-
}
|
|
7605
|
-
var ROUTE_SLOT_MASK = 1023;
|
|
7606
|
-
var FLOW_KEY_PREFIX = import_node_buffer24.Buffer.from("f:{");
|
|
7607
|
-
var VALUE_REF_FLOW_KEY_PREFIX = import_node_buffer24.Buffer.from("X:f:{");
|
|
7608
|
-
function routingSlotForKey(key) {
|
|
7609
|
-
const keyBytes = import_node_buffer24.Buffer.isBuffer(key) ? key : import_node_buffer24.Buffer.from(key);
|
|
7610
|
-
let hashInput;
|
|
7611
|
-
if (bufferStartsWith(keyBytes, FLOW_KEY_PREFIX)) {
|
|
7612
|
-
hashInput = flowHashTag(keyBytes.subarray(FLOW_KEY_PREFIX.byteLength), keyBytes);
|
|
7613
|
-
} else if (bufferStartsWith(keyBytes, VALUE_REF_FLOW_KEY_PREFIX)) {
|
|
7614
|
-
hashInput = flowHashTag(keyBytes.subarray(VALUE_REF_FLOW_KEY_PREFIX.byteLength), keyBytes);
|
|
7615
|
-
} else {
|
|
7616
|
-
hashInput = hashTagOrKey(keyBytes);
|
|
7617
|
-
}
|
|
7618
|
-
return crc32(hashInput) & ROUTE_SLOT_MASK;
|
|
7619
|
-
}
|
|
7620
|
-
|
|
7621
|
-
// src/topology-routing.ts
|
|
7622
7886
|
var FLOW_PARTITION_ROUTE_CACHE_MAX = 1024;
|
|
7623
7887
|
var flowPartitionRouteCache = /* @__PURE__ */ new Map();
|
|
7624
7888
|
function routingKeyFromProtocolPayload(name, command) {
|
|
@@ -7626,9 +7890,18 @@ function routingKeyFromProtocolPayload(name, command) {
|
|
|
7626
7890
|
return void 0;
|
|
7627
7891
|
}
|
|
7628
7892
|
if (isPlainObject3(command.payload)) {
|
|
7629
|
-
for (const field2 of [
|
|
7893
|
+
for (const field2 of [
|
|
7894
|
+
"key",
|
|
7895
|
+
"partition_key",
|
|
7896
|
+
"id",
|
|
7897
|
+
"owner_flow_id",
|
|
7898
|
+
"parent_flow_id",
|
|
7899
|
+
"root_flow_id",
|
|
7900
|
+
"correlation_id",
|
|
7901
|
+
"scope"
|
|
7902
|
+
]) {
|
|
7630
7903
|
const value = getField(command.payload, field2);
|
|
7631
|
-
if (typeof value === "string" ||
|
|
7904
|
+
if (typeof value === "string" || import_node_buffer27.Buffer.isBuffer(value)) {
|
|
7632
7905
|
return value;
|
|
7633
7906
|
}
|
|
7634
7907
|
}
|
|
@@ -7675,9 +7948,9 @@ function flowRoutingData(name, args) {
|
|
|
7675
7948
|
if (typeof partition === "string" && partition.toUpperCase() !== "AUTO" && partition.toUpperCase() !== "MIXED") {
|
|
7676
7949
|
return flowRoutingResult(flowLogicalPartitionRoutingKey(partition));
|
|
7677
7950
|
}
|
|
7678
|
-
if (
|
|
7679
|
-
const
|
|
7680
|
-
if (
|
|
7951
|
+
if (import_node_buffer27.Buffer.isBuffer(partition)) {
|
|
7952
|
+
const text3 = partition.toString("utf8").toUpperCase();
|
|
7953
|
+
if (text3 !== "AUTO" && text3 !== "MIXED") {
|
|
7681
7954
|
return flowRoutingResult(flowLogicalPartitionRoutingKey(partition));
|
|
7682
7955
|
}
|
|
7683
7956
|
}
|
|
@@ -7766,22 +8039,22 @@ function flowPartitionRoutingKeyFromCommand(command, claim) {
|
|
|
7766
8039
|
return { handled: false };
|
|
7767
8040
|
}
|
|
7768
8041
|
function isRoutingKey(value) {
|
|
7769
|
-
return typeof value === "string" ||
|
|
8042
|
+
return typeof value === "string" || import_node_buffer27.Buffer.isBuffer(value);
|
|
7770
8043
|
}
|
|
7771
8044
|
function flowLogicalPartitionRoutingKey(value) {
|
|
7772
|
-
if (typeof value !== "string" && !
|
|
8045
|
+
if (typeof value !== "string" && !import_node_buffer27.Buffer.isBuffer(value)) {
|
|
7773
8046
|
return void 0;
|
|
7774
8047
|
}
|
|
7775
|
-
const bytes2 =
|
|
7776
|
-
const
|
|
7777
|
-
const autoMatch = /^__flow_auto__:(0|[1-9]\d{0,2})$/u.exec(
|
|
8048
|
+
const bytes2 = import_node_buffer27.Buffer.isBuffer(value) ? value : import_node_buffer27.Buffer.from(value);
|
|
8049
|
+
const text3 = bytes2.toString("utf8");
|
|
8050
|
+
const autoMatch = /^__flow_auto__:(0|[1-9]\d{0,2})$/u.exec(text3);
|
|
7778
8051
|
if (autoMatch != null) {
|
|
7779
8052
|
const bucket = Number(autoMatch[1]);
|
|
7780
8053
|
if (bucket < 256) {
|
|
7781
|
-
return `
|
|
8054
|
+
return `{fa:${bucket}}`;
|
|
7782
8055
|
}
|
|
7783
8056
|
}
|
|
7784
|
-
const cacheKey = `${
|
|
8057
|
+
const cacheKey = `${import_node_buffer27.Buffer.isBuffer(value) ? "b" : "s"}:${bytes2.toString("base64")}`;
|
|
7785
8058
|
const cached = flowPartitionRouteCache.get(cacheKey);
|
|
7786
8059
|
if (cached != null) {
|
|
7787
8060
|
flowPartitionRouteCache.delete(cacheKey);
|
|
@@ -7789,7 +8062,7 @@ function flowLogicalPartitionRoutingKey(value) {
|
|
|
7789
8062
|
return cached;
|
|
7790
8063
|
}
|
|
7791
8064
|
const digest = (0, import_node_crypto.createHash)("sha256").update(bytes2).digest("base64url");
|
|
7792
|
-
const routeKey = `
|
|
8065
|
+
const routeKey = `{f:${digest}}`;
|
|
7793
8066
|
if (flowPartitionRouteCache.size >= FLOW_PARTITION_ROUTE_CACHE_MAX) {
|
|
7794
8067
|
const oldest = flowPartitionRouteCache.keys().next().value;
|
|
7795
8068
|
if (oldest != null) flowPartitionRouteCache.delete(oldest);
|
|
@@ -7798,18 +8071,17 @@ function flowLogicalPartitionRoutingKey(value) {
|
|
|
7798
8071
|
return routeKey;
|
|
7799
8072
|
}
|
|
7800
8073
|
function flowAutoIdRoutingKey(value) {
|
|
7801
|
-
if (typeof value !== "string" && !
|
|
8074
|
+
if (typeof value !== "string" && !import_node_buffer27.Buffer.isBuffer(value)) {
|
|
7802
8075
|
return void 0;
|
|
7803
8076
|
}
|
|
7804
|
-
const
|
|
7805
|
-
|
|
7806
|
-
return `f:{fa:${bucket}}:route`;
|
|
8077
|
+
const bucket = (import_node_buffer27.Buffer.isBuffer(value) ? crc32(value) : crc32Utf8(value)) & 255;
|
|
8078
|
+
return `{fa:${bucket}}`;
|
|
7807
8079
|
}
|
|
7808
8080
|
function flowClaimLogicalPartitionRoutingKey(value) {
|
|
7809
|
-
if (typeof value !== "string" && !
|
|
8081
|
+
if (typeof value !== "string" && !import_node_buffer27.Buffer.isBuffer(value)) return void 0;
|
|
7810
8082
|
const selector = commandPart(value);
|
|
7811
8083
|
if (selector === "AUTO" || selector === "ANY") return void 0;
|
|
7812
|
-
if (selector === "GLOBAL") return "
|
|
8084
|
+
if (selector === "GLOBAL") return "{f}";
|
|
7813
8085
|
return flowLogicalPartitionRoutingKey(value);
|
|
7814
8086
|
}
|
|
7815
8087
|
function singleShardFlowPartitionKey(values) {
|
|
@@ -7821,7 +8093,7 @@ function singleShardFlowClaimPartitionKey(values) {
|
|
|
7821
8093
|
return keys.some((key) => key == null) ? void 0 : singleShardKey(keys);
|
|
7822
8094
|
}
|
|
7823
8095
|
function singleShardKey(keys) {
|
|
7824
|
-
if (keys.length === 0 || keys.some((key) => typeof key !== "string" && !
|
|
8096
|
+
if (keys.length === 0 || keys.some((key) => typeof key !== "string" && !import_node_buffer27.Buffer.isBuffer(key))) {
|
|
7825
8097
|
return void 0;
|
|
7826
8098
|
}
|
|
7827
8099
|
const usable = keys;
|
|
@@ -7854,7 +8126,7 @@ function routedKeyGroups(keys, routeKey) {
|
|
|
7854
8126
|
const groups = /* @__PURE__ */ new Map();
|
|
7855
8127
|
for (let index = 0; index < keys.length; index += 1) {
|
|
7856
8128
|
const key = keys[index];
|
|
7857
|
-
if (typeof key !== "string" && !
|
|
8129
|
+
if (typeof key !== "string" && !import_node_buffer27.Buffer.isBuffer(key)) return void 0;
|
|
7858
8130
|
const route = routeKey(key);
|
|
7859
8131
|
const groupKey = `${route.endpointKey}\0${route.laneId}`;
|
|
7860
8132
|
const group = groups.get(groupKey);
|
|
@@ -8095,7 +8367,16 @@ function isExplicitlySafeReroute(error) {
|
|
|
8095
8367
|
if (error instanceof ConnectionClosedError) {
|
|
8096
8368
|
return error.requestDisposition === "unsent";
|
|
8097
8369
|
}
|
|
8098
|
-
return error instanceof RerouteError &&
|
|
8370
|
+
return error instanceof RerouteError && error.retryable === true && error.safeToRetry === true;
|
|
8371
|
+
}
|
|
8372
|
+
function retryAfterMs(error) {
|
|
8373
|
+
return error instanceof FerricStoreError ? error.retryAfterMs ?? 0 : 0;
|
|
8374
|
+
}
|
|
8375
|
+
async function waitForExplicitlySafeReroute(error) {
|
|
8376
|
+
if (!isExplicitlySafeReroute(error)) return false;
|
|
8377
|
+
const delayMs = retryAfterMs(error);
|
|
8378
|
+
if (delayMs > 0) await sleep(delayMs);
|
|
8379
|
+
return true;
|
|
8099
8380
|
}
|
|
8100
8381
|
|
|
8101
8382
|
// src/topology-endpoint-trust.ts
|
|
@@ -8829,7 +9110,9 @@ var TopologyNativeAdapterPool = class _TopologyNativeAdapterPool {
|
|
|
8829
9110
|
() => true,
|
|
8830
9111
|
() => false
|
|
8831
9112
|
);
|
|
8832
|
-
|
|
9113
|
+
if (!refreshed || !await waitForExplicitlySafeReroute(error)) return false;
|
|
9114
|
+
this.assertOpen();
|
|
9115
|
+
return true;
|
|
8833
9116
|
}
|
|
8834
9117
|
async executePipelineOnRoute(commands, route, options) {
|
|
8835
9118
|
const adapter = await this.adapterForCurrentRoute(route);
|
|
@@ -8919,7 +9202,7 @@ var TopologyNativeAdapterPool = class _TopologyNativeAdapterPool {
|
|
|
8919
9202
|
};
|
|
8920
9203
|
|
|
8921
9204
|
// src/response-map-preservation.ts
|
|
8922
|
-
var
|
|
9205
|
+
var import_node_buffer29 = require("buffer");
|
|
8923
9206
|
function toStringKeyMapPreservingValues(value) {
|
|
8924
9207
|
if (value == null) return void 0;
|
|
8925
9208
|
const result = {};
|
|
@@ -8929,7 +9212,7 @@ function toStringKeyMapPreservingValues(value) {
|
|
|
8929
9212
|
}
|
|
8930
9213
|
return result;
|
|
8931
9214
|
}
|
|
8932
|
-
if (typeof value === "object" && !Array.isArray(value) && !
|
|
9215
|
+
if (typeof value === "object" && !Array.isArray(value) && !import_node_buffer29.Buffer.isBuffer(value) && !(value instanceof Uint8Array)) {
|
|
8933
9216
|
for (const [key, item] of Object.entries(value)) {
|
|
8934
9217
|
setOwnValue(result, text(key), normalizeMapStructurePreservingBytes(item));
|
|
8935
9218
|
}
|
|
@@ -8938,7 +9221,7 @@ function toStringKeyMapPreservingValues(value) {
|
|
|
8938
9221
|
return void 0;
|
|
8939
9222
|
}
|
|
8940
9223
|
function normalizeMapStructurePreservingBytes(value) {
|
|
8941
|
-
if (
|
|
9224
|
+
if (import_node_buffer29.Buffer.isBuffer(value) || value instanceof Uint8Array) return value;
|
|
8942
9225
|
if (value instanceof Map) {
|
|
8943
9226
|
const result = {};
|
|
8944
9227
|
for (const [key, item] of value.entries()) {
|
|
@@ -8960,7 +9243,7 @@ function normalizeMapStructurePreservingBytes(value) {
|
|
|
8960
9243
|
}
|
|
8961
9244
|
|
|
8962
9245
|
// src/native-kv-responses.ts
|
|
8963
|
-
var
|
|
9246
|
+
var import_node_buffer30 = require("buffer");
|
|
8964
9247
|
function rateLimitResultFromResp(value) {
|
|
8965
9248
|
if (!Array.isArray(value) || value.length !== 4) {
|
|
8966
9249
|
throw new TypeError("RATELIMIT.ADD returned an unexpected response");
|
|
@@ -9003,30 +9286,27 @@ function fetchOrComputeResultFromResp(value, codec) {
|
|
|
9003
9286
|
shouldCompute: false
|
|
9004
9287
|
};
|
|
9005
9288
|
}
|
|
9006
|
-
if (status !== "compute"
|
|
9289
|
+
if (status !== "compute" || value.length !== 3) {
|
|
9290
|
+
throw new TypeError("FETCH_OR_COMPUTE returned an unexpected response");
|
|
9291
|
+
}
|
|
9007
9292
|
return {
|
|
9008
9293
|
status,
|
|
9009
9294
|
computeHint: responseBytes(value[1], "FETCH_OR_COMPUTE"),
|
|
9010
|
-
|
|
9011
|
-
|
|
9012
|
-
computeToken: responseBytes(value[2], "FETCH_OR_COMPUTE")
|
|
9013
|
-
} : {
|
|
9014
|
-
computeMode: "legacy",
|
|
9015
|
-
computeToken: null
|
|
9016
|
-
},
|
|
9295
|
+
computeMode: "fenced",
|
|
9296
|
+
computeToken: responseBytes(value[2], "FETCH_OR_COMPUTE"),
|
|
9017
9297
|
hit: false,
|
|
9018
9298
|
shouldCompute: true
|
|
9019
9299
|
};
|
|
9020
9300
|
}
|
|
9021
9301
|
function decodePayload(codec, value) {
|
|
9022
9302
|
if (value == null) return null;
|
|
9023
|
-
if (
|
|
9024
|
-
if (value instanceof Uint8Array) return codec.decode(
|
|
9025
|
-
if (typeof value === "string") return codec.decode(
|
|
9303
|
+
if (import_node_buffer30.Buffer.isBuffer(value)) return codec.decode(value);
|
|
9304
|
+
if (value instanceof Uint8Array) return codec.decode(import_node_buffer30.Buffer.from(value));
|
|
9305
|
+
if (typeof value === "string") return codec.decode(import_node_buffer30.Buffer.from(value));
|
|
9026
9306
|
return normalizeRefMeta(value);
|
|
9027
9307
|
}
|
|
9028
9308
|
function requiredResponseString(value, context) {
|
|
9029
|
-
if (typeof value !== "string" && !
|
|
9309
|
+
if (typeof value !== "string" && !import_node_buffer30.Buffer.isBuffer(value) && !(value instanceof Uint8Array)) {
|
|
9030
9310
|
throw new TypeError(`${context} returned an unexpected response`);
|
|
9031
9311
|
}
|
|
9032
9312
|
const result = text(value);
|
|
@@ -9043,7 +9323,7 @@ function requiredNonNegativeInteger(value, context) {
|
|
|
9043
9323
|
return result;
|
|
9044
9324
|
}
|
|
9045
9325
|
function responseBytes(value, context) {
|
|
9046
|
-
if (typeof value !== "string" && !
|
|
9326
|
+
if (typeof value !== "string" && !import_node_buffer30.Buffer.isBuffer(value) && !(value instanceof Uint8Array)) {
|
|
9047
9327
|
throw new TypeError(`${context} returned an unexpected response`);
|
|
9048
9328
|
}
|
|
9049
9329
|
return bytes(value);
|
|
@@ -9128,6 +9408,9 @@ function flowRecordFromResp(value, codec) {
|
|
|
9128
9408
|
field(value, "max_active_ms"),
|
|
9129
9409
|
"FLOW record max_active_ms"
|
|
9130
9410
|
);
|
|
9411
|
+
const rawError = field(value, "error");
|
|
9412
|
+
const error = flowError(rawError, codec);
|
|
9413
|
+
const failureReason = optionalResponseString(field(rawError, "reason"), "FLOW record error reason");
|
|
9131
9414
|
return {
|
|
9132
9415
|
id: requiredTextField(value, "id", "FLOW record"),
|
|
9133
9416
|
type: requiredTextField(value, "type", "FLOW record"),
|
|
@@ -9142,6 +9425,8 @@ function flowRecordFromResp(value, codec) {
|
|
|
9142
9425
|
rootFlowId: optionalResponseString(field(value, "root_flow_id"), "FLOW record root_flow_id"),
|
|
9143
9426
|
correlationId: optionalResponseString(field(value, "correlation_id"), "FLOW record correlation_id"),
|
|
9144
9427
|
...maxActiveMs == null ? {} : { maxActiveMs },
|
|
9428
|
+
...error == null ? {} : { error },
|
|
9429
|
+
...failureReason == null ? {} : { failureReason },
|
|
9145
9430
|
valueRefs: optionalMapField(value, "value_refs", "FLOW record"),
|
|
9146
9431
|
values,
|
|
9147
9432
|
valueSizes: optionalMapField(value, "value_sizes", "FLOW record"),
|
|
@@ -9153,6 +9438,21 @@ function flowRecordFromResp(value, codec) {
|
|
|
9153
9438
|
raw: value
|
|
9154
9439
|
};
|
|
9155
9440
|
}
|
|
9441
|
+
function flowError(value, codec) {
|
|
9442
|
+
if (value == null) return void 0;
|
|
9443
|
+
const reason = optionalResponseString(field(value, "reason"), "FLOW record error reason");
|
|
9444
|
+
if (reason === "max_active_ms") {
|
|
9445
|
+
const maxActiveMs = optionalPositiveResponseInteger(
|
|
9446
|
+
field(value, "max_active_ms"),
|
|
9447
|
+
"FLOW record error max_active_ms"
|
|
9448
|
+
);
|
|
9449
|
+
if (maxActiveMs == null) {
|
|
9450
|
+
throw new TypeError("FLOW record error max_active_ms returned an unexpected response");
|
|
9451
|
+
}
|
|
9452
|
+
return { maxActiveMs, reason };
|
|
9453
|
+
}
|
|
9454
|
+
return decodePayload2(codec, value);
|
|
9455
|
+
}
|
|
9156
9456
|
function decodePayload2(codec, value) {
|
|
9157
9457
|
if (value == null) {
|
|
9158
9458
|
return null;
|
|
@@ -9733,7 +10033,7 @@ function groupAutoPartitionItems(items) {
|
|
|
9733
10033
|
}
|
|
9734
10034
|
|
|
9735
10035
|
// src/client-values.ts
|
|
9736
|
-
var
|
|
10036
|
+
var import_node_buffer31 = require("buffer");
|
|
9737
10037
|
async function valueMGetEntries(client, refs, options = {}) {
|
|
9738
10038
|
const refCount = refs.length;
|
|
9739
10039
|
if (refCount === 0) {
|
|
@@ -9768,12 +10068,12 @@ async function valueMGetEntries(client, refs, options = {}) {
|
|
|
9768
10068
|
const item = response[index];
|
|
9769
10069
|
if (item == null) {
|
|
9770
10070
|
entries[index] = { found: false };
|
|
9771
|
-
} else if (
|
|
10071
|
+
} else if (import_node_buffer31.Buffer.isBuffer(item)) {
|
|
9772
10072
|
entries[index] = { found: true, value: client.codec.decode(item) };
|
|
9773
10073
|
} else if (item instanceof Uint8Array) {
|
|
9774
|
-
entries[index] = { found: true, value: client.codec.decode(
|
|
10074
|
+
entries[index] = { found: true, value: client.codec.decode(import_node_buffer31.Buffer.from(item)) };
|
|
9775
10075
|
} else if (typeof item === "string") {
|
|
9776
|
-
entries[index] = { found: true, value: client.codec.decode(
|
|
10076
|
+
entries[index] = { found: true, value: client.codec.decode(import_node_buffer31.Buffer.from(item)) };
|
|
9777
10077
|
} else {
|
|
9778
10078
|
entries[index] = { found: true, value: item };
|
|
9779
10079
|
}
|
|
@@ -9782,10 +10082,10 @@ async function valueMGetEntries(client, refs, options = {}) {
|
|
|
9782
10082
|
}
|
|
9783
10083
|
|
|
9784
10084
|
// src/auto-batch.ts
|
|
9785
|
-
var
|
|
10085
|
+
var import_node_buffer33 = require("buffer");
|
|
9786
10086
|
|
|
9787
10087
|
// src/auto-batch-ordering.ts
|
|
9788
|
-
var
|
|
10088
|
+
var import_node_buffer32 = require("buffer");
|
|
9789
10089
|
function autoBatchOrderingPlan(batch) {
|
|
9790
10090
|
const accesses = /* @__PURE__ */ new Map();
|
|
9791
10091
|
const fallbackDependencies = [];
|
|
@@ -9900,13 +10200,13 @@ function flowManyAutoBatchIds(command, name) {
|
|
|
9900
10200
|
return fixedFlowItemIds(
|
|
9901
10201
|
command,
|
|
9902
10202
|
mixed ? 4 : 3,
|
|
9903
|
-
(itemIndex) => isAutoBatchResourceValue(command[itemIndex]) && (!mixed || isAutoBatchResourceValue(command[itemIndex + 1])) && isFencingToken(command[itemIndex + (mixed ? 2 : 1)]) &&
|
|
10203
|
+
(itemIndex) => isAutoBatchResourceValue(command[itemIndex]) && (!mixed || isAutoBatchResourceValue(command[itemIndex + 1])) && isFencingToken(command[itemIndex + (mixed ? 2 : 1)]) && import_node_buffer32.Buffer.isBuffer(command[itemIndex + (mixed ? 3 : 2)])
|
|
9904
10204
|
);
|
|
9905
10205
|
}
|
|
9906
10206
|
return fixedFlowItemIds(
|
|
9907
10207
|
command,
|
|
9908
10208
|
mixed ? 4 : 3,
|
|
9909
|
-
(itemIndex) => isAutoBatchResourceValue(command[itemIndex]) && (!mixed || isAutoBatchResourceValue(command[itemIndex + 1])) &&
|
|
10209
|
+
(itemIndex) => isAutoBatchResourceValue(command[itemIndex]) && (!mixed || isAutoBatchResourceValue(command[itemIndex + 1])) && import_node_buffer32.Buffer.isBuffer(command[itemIndex + (mixed ? 2 : 1)]) && isFencingToken(command[itemIndex + (mixed ? 3 : 2)])
|
|
9910
10210
|
);
|
|
9911
10211
|
}
|
|
9912
10212
|
function createManyAutoBatchIds(command) {
|
|
@@ -9919,7 +10219,7 @@ function createManyAutoBatchIds(command) {
|
|
|
9919
10219
|
const ids = fixedFlowItemIds(
|
|
9920
10220
|
command,
|
|
9921
10221
|
width,
|
|
9922
|
-
(itemIndex) => isAutoBatchResourceValue(command[itemIndex]) && (!mixed || isAutoBatchResourceValue(command[itemIndex + 1])) &&
|
|
10222
|
+
(itemIndex) => isAutoBatchResourceValue(command[itemIndex]) && (!mixed || isAutoBatchResourceValue(command[itemIndex + 1])) && import_node_buffer32.Buffer.isBuffer(command[itemIndex + width - 1]),
|
|
9923
10223
|
markerIndex
|
|
9924
10224
|
);
|
|
9925
10225
|
if (ids != null) return ids;
|
|
@@ -9937,7 +10237,7 @@ function extendedCreateManyAutoBatchIds(command, markerIndex) {
|
|
|
9937
10237
|
let cursor = markerIndex + 2;
|
|
9938
10238
|
for (let itemIndex = 0; itemIndex < itemCount; itemIndex += 1) {
|
|
9939
10239
|
const id = command[cursor];
|
|
9940
|
-
if (!isAutoBatchResourceValue(id) || !isAutoBatchResourceValue(command[cursor + 1]) || !
|
|
10240
|
+
if (!isAutoBatchResourceValue(id) || !isAutoBatchResourceValue(command[cursor + 1]) || !import_node_buffer32.Buffer.isBuffer(command[cursor + 2])) return void 0;
|
|
9941
10241
|
ids.push(id);
|
|
9942
10242
|
cursor += 3;
|
|
9943
10243
|
const afterValues = skipExtendedNamedItems(command, cursor, true);
|
|
@@ -9956,7 +10256,7 @@ function skipExtendedNamedItems(command, countIndex, encodedValues) {
|
|
|
9956
10256
|
for (let index = 0; index < count; index += 1) {
|
|
9957
10257
|
const name = command[firstItem + index * 2];
|
|
9958
10258
|
const value = command[firstItem + index * 2 + 1];
|
|
9959
|
-
if (!isAutoBatchResourceValue(name) || (encodedValues ? !
|
|
10259
|
+
if (!isAutoBatchResourceValue(name) || (encodedValues ? !import_node_buffer32.Buffer.isBuffer(value) : !isAutoBatchResourceValue(value))) return void 0;
|
|
9960
10260
|
}
|
|
9961
10261
|
return firstItem + count * 2;
|
|
9962
10262
|
}
|
|
@@ -9971,7 +10271,7 @@ function runStepsManyAutoBatchIds(command) {
|
|
|
9971
10271
|
ids.push(item);
|
|
9972
10272
|
continue;
|
|
9973
10273
|
}
|
|
9974
|
-
if (typeof item !== "object" || item == null || Array.isArray(item) ||
|
|
10274
|
+
if (typeof item !== "object" || item == null || Array.isArray(item) || import_node_buffer32.Buffer.isBuffer(item)) return void 0;
|
|
9975
10275
|
const id = item.id;
|
|
9976
10276
|
if (!isAutoBatchResourceValue(id)) return void 0;
|
|
9977
10277
|
ids.push(id);
|
|
@@ -10012,7 +10312,7 @@ function flowValuePutOwner(command, start) {
|
|
|
10012
10312
|
}
|
|
10013
10313
|
var flowValuePutOptionTokens = /* @__PURE__ */ new Set(["NAME", "NOW", "OVERRIDE", "OWNER_FLOW_ID", "PARTITION", "TTL", "TTL_MS"]);
|
|
10014
10314
|
function isAutoBatchResourceValue(value) {
|
|
10015
|
-
return typeof value === "string" ||
|
|
10315
|
+
return typeof value === "string" || import_node_buffer32.Buffer.isBuffer(value);
|
|
10016
10316
|
}
|
|
10017
10317
|
function isFencingToken(value) {
|
|
10018
10318
|
return typeof value === "number" && Number.isSafeInteger(value) || typeof value === "bigint";
|
|
@@ -10021,7 +10321,7 @@ function nonNegativeItemCount(value) {
|
|
|
10021
10321
|
return typeof value === "number" && Number.isSafeInteger(value) && value >= 0 ? value : void 0;
|
|
10022
10322
|
}
|
|
10023
10323
|
function autoBatchResourceKey(namespace, value) {
|
|
10024
|
-
return `${namespace}:${
|
|
10324
|
+
return `${namespace}:${import_node_buffer32.Buffer.from(value).toString("base64")}`;
|
|
10025
10325
|
}
|
|
10026
10326
|
function autoBatchCommandName(command) {
|
|
10027
10327
|
return commandView(command).name ?? null;
|
|
@@ -10430,15 +10730,15 @@ function claimFailure(error) {
|
|
|
10430
10730
|
}
|
|
10431
10731
|
|
|
10432
10732
|
// src/client-flow-support.ts
|
|
10433
|
-
var
|
|
10733
|
+
var import_node_buffer39 = require("buffer");
|
|
10434
10734
|
|
|
10435
10735
|
// src/client-core.ts
|
|
10436
|
-
var
|
|
10736
|
+
var import_node_buffer38 = require("buffer");
|
|
10437
10737
|
|
|
10438
10738
|
// src/client-core-helpers.ts
|
|
10439
|
-
var
|
|
10739
|
+
var import_node_buffer34 = require("buffer");
|
|
10440
10740
|
function bgsaveResponse(response) {
|
|
10441
|
-
if ((typeof response === "string" ||
|
|
10741
|
+
if ((typeof response === "string" || import_node_buffer34.Buffer.isBuffer(response) || response instanceof Uint8Array) && text(response) === "Background saving started") {
|
|
10442
10742
|
return true;
|
|
10443
10743
|
}
|
|
10444
10744
|
return okResponse(response);
|
|
@@ -10449,11 +10749,11 @@ function clientNameResponse(response) {
|
|
|
10449
10749
|
function fetchOrComputeCompletionToken(options) {
|
|
10450
10750
|
if (options == null || !Object.hasOwn(options, "computeToken") || options.computeToken === void 0) {
|
|
10451
10751
|
throw new TypeError(
|
|
10452
|
-
"fetch-or-compute completion requires computeToken
|
|
10752
|
+
"fetch-or-compute completion requires computeToken"
|
|
10453
10753
|
);
|
|
10454
10754
|
}
|
|
10455
|
-
if (
|
|
10456
|
-
throw new TypeError("fetch-or-compute computeToken must be a Buffer
|
|
10755
|
+
if (!import_node_buffer34.Buffer.isBuffer(options.computeToken)) {
|
|
10756
|
+
throw new TypeError("fetch-or-compute computeToken must be a Buffer");
|
|
10457
10757
|
}
|
|
10458
10758
|
return options.computeToken;
|
|
10459
10759
|
}
|
|
@@ -10475,10 +10775,10 @@ function unsupportedClientCaching() {
|
|
|
10475
10775
|
}
|
|
10476
10776
|
|
|
10477
10777
|
// src/client-base.ts
|
|
10478
|
-
var
|
|
10778
|
+
var import_node_buffer36 = require("buffer");
|
|
10479
10779
|
|
|
10480
10780
|
// src/client-executor.ts
|
|
10481
|
-
var
|
|
10781
|
+
var import_node_buffer35 = require("buffer");
|
|
10482
10782
|
var ErrorMappingExecutor = class {
|
|
10483
10783
|
constructor(executor) {
|
|
10484
10784
|
this.executor = executor;
|
|
@@ -10575,14 +10875,17 @@ var FerricStoreClientBase = class {
|
|
|
10575
10875
|
};
|
|
10576
10876
|
}
|
|
10577
10877
|
async command(...args) {
|
|
10878
|
+
assertAtomicKeyValueCommandSharesSlot(args);
|
|
10578
10879
|
return await executeCommandArgs(this.executor, args);
|
|
10579
10880
|
}
|
|
10580
10881
|
/** Execute an already-built command without a JavaScript variadic-call limit. */
|
|
10581
10882
|
async commandArgs(args) {
|
|
10883
|
+
assertAtomicKeyValueCommandSharesSlot(args);
|
|
10582
10884
|
return await executeCommandArgs(this.executor, args);
|
|
10583
10885
|
}
|
|
10584
10886
|
async pipeline(commands, options) {
|
|
10585
10887
|
const snapshot = snapshotPipelineCommands(commands);
|
|
10888
|
+
for (const command of snapshot) assertAtomicKeyValueCommandSharesSlot(command);
|
|
10586
10889
|
const snapshotOptions = snapshotPipelineOptions(options);
|
|
10587
10890
|
const results = this.executor.executePipeline != null ? await this.executor.executePipeline(snapshot, snapshotOptions) : await executeCommandArraysIndividually(
|
|
10588
10891
|
async (command) => await this.commandArgs(command),
|
|
@@ -10809,14 +11112,14 @@ var FerricStoreAdministrationClient = class extends FerricStoreClientBase {
|
|
|
10809
11112
|
};
|
|
10810
11113
|
|
|
10811
11114
|
// src/store-utilities.ts
|
|
10812
|
-
var
|
|
11115
|
+
var import_node_buffer37 = require("buffer");
|
|
10813
11116
|
function encode(codec, value) {
|
|
10814
11117
|
return codec.encode(value);
|
|
10815
11118
|
}
|
|
10816
11119
|
function decode(codec, value) {
|
|
10817
11120
|
if (value == null) return null;
|
|
10818
|
-
if (
|
|
10819
|
-
if (value instanceof Uint8Array) return codec.decode(
|
|
11121
|
+
if (import_node_buffer37.Buffer.isBuffer(value)) return codec.decode(value);
|
|
11122
|
+
if (value instanceof Uint8Array) return codec.decode(import_node_buffer37.Buffer.from(value));
|
|
10820
11123
|
return value;
|
|
10821
11124
|
}
|
|
10822
11125
|
function number(value) {
|
|
@@ -11222,12 +11525,15 @@ var TopKStore = class {
|
|
|
11222
11525
|
const width = ownOption(options, "width");
|
|
11223
11526
|
const depth = ownOption(options, "depth");
|
|
11224
11527
|
const decay = ownOption(options, "decay");
|
|
11225
|
-
|
|
11226
|
-
|
|
11227
|
-
|
|
11528
|
+
if (decay != null || Object.hasOwn(options, "decay")) {
|
|
11529
|
+
throw new TypeError("TOPK.RESERVE decay is not supported by FerricStore 0.8");
|
|
11530
|
+
}
|
|
11531
|
+
const tuningCount = [width, depth].filter((value) => value != null).length;
|
|
11532
|
+
if (tuningCount !== 0 && tuningCount !== 2) {
|
|
11533
|
+
throw new TypeError("TOPK.RESERVE width and depth must be provided together");
|
|
11228
11534
|
}
|
|
11229
|
-
if (tuningCount ===
|
|
11230
|
-
args.push(width, depth
|
|
11535
|
+
if (tuningCount === 2) {
|
|
11536
|
+
args.push(width, depth);
|
|
11231
11537
|
}
|
|
11232
11538
|
return okResponse(await commandArgs(this.client, args));
|
|
11233
11539
|
}
|
|
@@ -11633,10 +11939,14 @@ var KeyValueStore = class {
|
|
|
11633
11939
|
);
|
|
11634
11940
|
}
|
|
11635
11941
|
async mset(entries) {
|
|
11636
|
-
|
|
11942
|
+
const args = keyValueArgs(["MSET"], this.client.codec, entries);
|
|
11943
|
+
assertKeyValueCommandSharesSlot(args, "MSET");
|
|
11944
|
+
return okResponse(await commandArgs(this.client, args));
|
|
11637
11945
|
}
|
|
11638
11946
|
async msetnx(entries) {
|
|
11639
|
-
|
|
11947
|
+
const args = keyValueArgs(["MSETNX"], this.client.codec, entries);
|
|
11948
|
+
assertKeyValueCommandSharesSlot(args, "MSETNX");
|
|
11949
|
+
return binaryBooleanResponse(await commandArgs(this.client, args));
|
|
11640
11950
|
}
|
|
11641
11951
|
async incr(key) {
|
|
11642
11952
|
return integerReply(await this.client.command("INCR", key));
|
|
@@ -12706,7 +13016,8 @@ var FerricStoreClientCore = class extends FerricStoreAdministrationClient {
|
|
|
12706
13016
|
return okResponse(await this.command(
|
|
12707
13017
|
"FETCH_OR_COMPUTE_RESULT",
|
|
12708
13018
|
key,
|
|
12709
|
-
|
|
13019
|
+
computeToken,
|
|
13020
|
+
encoded,
|
|
12710
13021
|
options.ttlMs
|
|
12711
13022
|
));
|
|
12712
13023
|
}
|
|
@@ -12715,7 +13026,7 @@ var FerricStoreClientCore = class extends FerricStoreAdministrationClient {
|
|
|
12715
13026
|
return okResponse(await this.command(
|
|
12716
13027
|
"FETCH_OR_COMPUTE_ERROR",
|
|
12717
13028
|
key,
|
|
12718
|
-
|
|
13029
|
+
computeToken,
|
|
12719
13030
|
message
|
|
12720
13031
|
));
|
|
12721
13032
|
}
|
|
@@ -12841,7 +13152,7 @@ var FerricStoreManagementClient = class extends FerricStoreClientCore {
|
|
|
12841
13152
|
}
|
|
12842
13153
|
async effectGet(id, effectKey, options = {}) {
|
|
12843
13154
|
const args = ["FLOW.EFFECT.GET", id, "EFFECT_KEY", effectKey];
|
|
12844
|
-
append(args, "PARTITION", options.partitionKey
|
|
13155
|
+
append(args, "PARTITION", options.partitionKey);
|
|
12845
13156
|
return optionalAdminRecord(await this.commandArgs(args), "FLOW.EFFECT.GET");
|
|
12846
13157
|
}
|
|
12847
13158
|
async effectStatus(command, id, effectKey, options) {
|
|
@@ -13013,7 +13324,7 @@ var FerricStoreManagementClient = class extends FerricStoreClientCore {
|
|
|
13013
13324
|
}
|
|
13014
13325
|
async governanceLedger(id, options = {}) {
|
|
13015
13326
|
const args = ["FLOW.GOVERNANCE.LEDGER", id];
|
|
13016
|
-
append(args, "PARTITION", options.partitionKey
|
|
13327
|
+
append(args, "PARTITION", options.partitionKey);
|
|
13017
13328
|
append(args, "LIMIT", options.limit);
|
|
13018
13329
|
append(args, "FROM_MS", options.fromMs);
|
|
13019
13330
|
append(args, "TO_MS", options.toMs);
|
|
@@ -13029,7 +13340,7 @@ async function executeProducerWriteWithBackpressure(execute, policy, signal) {
|
|
|
13029
13340
|
try {
|
|
13030
13341
|
return await execute();
|
|
13031
13342
|
} catch (error) {
|
|
13032
|
-
if (!(error instanceof OverloadedError) || attempt >= policy.maxRetries) throw error;
|
|
13343
|
+
if (!(error instanceof OverloadedError) || error.retryable !== true || error.safeToRetry !== true || attempt >= policy.maxRetries) throw error;
|
|
13033
13344
|
const exponential = Math.min(policy.maxDelayMs, policy.baseDelayMs * 2 ** attempt);
|
|
13034
13345
|
const base = Math.min(policy.maxDelayMs, error.retryAfterMs ?? exponential);
|
|
13035
13346
|
const jitter = base * (policy.jitterPct / 100) * Math.random();
|
|
@@ -13294,7 +13605,7 @@ var FerricStoreFlowSupportClient = class extends FerricStoreManagementClient {
|
|
|
13294
13605
|
};
|
|
13295
13606
|
|
|
13296
13607
|
// src/flow-many-snapshot.ts
|
|
13297
|
-
var
|
|
13608
|
+
var import_node_buffer40 = require("buffer");
|
|
13298
13609
|
var encodedOptionFields = ["error", "payload", "reason", "result"];
|
|
13299
13610
|
function snapshotCreateItem(item, codec) {
|
|
13300
13611
|
const snapshot = {
|
|
@@ -13334,7 +13645,7 @@ function snapshotFlowManyOptions(options, codec) {
|
|
|
13334
13645
|
}
|
|
13335
13646
|
function snapshotClaimedItem(item) {
|
|
13336
13647
|
const wire = item[CLAIMED_ITEM_WIRE];
|
|
13337
|
-
const leaseToken =
|
|
13648
|
+
const leaseToken = import_node_buffer40.Buffer.from(wire?.leaseToken ?? item.leaseToken);
|
|
13338
13649
|
const snapshot = {
|
|
13339
13650
|
...item,
|
|
13340
13651
|
fencingToken: wire?.fencingToken ?? item.fencingToken,
|
|
@@ -13351,15 +13662,15 @@ function snapshotClaimedItem(item) {
|
|
|
13351
13662
|
function snapshotFencedItem(item) {
|
|
13352
13663
|
return Object.freeze({
|
|
13353
13664
|
...item,
|
|
13354
|
-
...item.leaseToken == null ? {} : { leaseToken:
|
|
13665
|
+
...item.leaseToken == null ? {} : { leaseToken: import_node_buffer40.Buffer.from(item.leaseToken) }
|
|
13355
13666
|
});
|
|
13356
13667
|
}
|
|
13357
13668
|
function snapshotClaimedItemWire(wire, leaseToken) {
|
|
13358
13669
|
return Object.freeze({
|
|
13359
13670
|
fencingToken: wire.fencingToken,
|
|
13360
|
-
id:
|
|
13671
|
+
id: import_node_buffer40.Buffer.from(wire.id),
|
|
13361
13672
|
leaseToken,
|
|
13362
|
-
partitionKey: wire.partitionKey == null ? wire.partitionKey :
|
|
13673
|
+
partitionKey: wire.partitionKey == null ? wire.partitionKey : import_node_buffer40.Buffer.from(wire.partitionKey)
|
|
13363
13674
|
});
|
|
13364
13675
|
}
|
|
13365
13676
|
function snapshotArray(values) {
|
|
@@ -13370,7 +13681,7 @@ function snapshotArray(values) {
|
|
|
13370
13681
|
return Object.freeze(snapshot);
|
|
13371
13682
|
}
|
|
13372
13683
|
function snapshotStateMeta(stateMeta) {
|
|
13373
|
-
return snapshotRecord(stateMeta, (value) =>
|
|
13684
|
+
return snapshotRecord(stateMeta, (value) => import_node_buffer40.Buffer.isBuffer(value) ? import_node_buffer40.Buffer.from(value) : value);
|
|
13374
13685
|
}
|
|
13375
13686
|
function snapshotCommandRecord(values) {
|
|
13376
13687
|
const seen = /* @__PURE__ */ new WeakMap();
|
|
@@ -13388,7 +13699,7 @@ function snapshotRecord(values, capture) {
|
|
|
13388
13699
|
}
|
|
13389
13700
|
function snapshotCommandArgument(value, seen) {
|
|
13390
13701
|
if (typeof value !== "object" || value == null) return value;
|
|
13391
|
-
if (
|
|
13702
|
+
if (import_node_buffer40.Buffer.isBuffer(value) || value instanceof Uint8Array) return import_node_buffer40.Buffer.from(value);
|
|
13392
13703
|
const objectValue = value;
|
|
13393
13704
|
const existing = seen.get(objectValue);
|
|
13394
13705
|
if (existing != null) return existing;
|
|
@@ -14186,6 +14497,9 @@ var FerricStoreClient = class _FerricStoreClient extends FerricStoreProducerClie
|
|
|
14186
14497
|
return new _FerricStoreClient(executor, clientOptions);
|
|
14187
14498
|
}
|
|
14188
14499
|
async valuePut(value, options = {}) {
|
|
14500
|
+
if (options.ownerFlowId != null && options.name != null && options.ttlMs != null) {
|
|
14501
|
+
throw new TypeError("named Flow values cannot have a TTL");
|
|
14502
|
+
}
|
|
14189
14503
|
const args = ["FLOW.VALUE.PUT", this.codec.encode(value), "NOW", options.nowMs ?? nowMs()];
|
|
14190
14504
|
append(args, "PARTITION", options.partitionKey);
|
|
14191
14505
|
append(args, "OWNER_FLOW_ID", options.ownerFlowId);
|
|
@@ -14217,7 +14531,6 @@ var FerricStoreClient = class _FerricStoreClient extends FerricStoreProducerClie
|
|
|
14217
14531
|
append(args, "TRANSITION_TO", options.transitionTo);
|
|
14218
14532
|
append(args, "RUN_AT", options.runAtMs);
|
|
14219
14533
|
append(args, "NOW", options.nowMs ?? nowMs());
|
|
14220
|
-
append(args, "PRIORITY", options.priority);
|
|
14221
14534
|
appendNamedValues(args, this.codec, options);
|
|
14222
14535
|
return await this.commandArgs(args);
|
|
14223
14536
|
}
|
|
@@ -14247,6 +14560,7 @@ var FerricStoreClient = class _FerricStoreClient extends FerricStoreProducerClie
|
|
|
14247
14560
|
append(args, "CORRELATION_ID", options.correlationId);
|
|
14248
14561
|
append(args, "PRIORITY", options.priority);
|
|
14249
14562
|
append(args, "RETENTION_TTL_MS", options.retentionTtlMs);
|
|
14563
|
+
append(args, "MAX_ACTIVE_MS", options.maxActiveMs);
|
|
14250
14564
|
appendAttributes(args, options.attributes);
|
|
14251
14565
|
appendStateMeta(args, options.stateMeta);
|
|
14252
14566
|
appendNamedValues(args, this.codec, options);
|
|
@@ -16352,16 +16666,23 @@ var WorkflowWorker = class {
|
|
|
16352
16666
|
);
|
|
16353
16667
|
}
|
|
16354
16668
|
};
|
|
16669
|
+
|
|
16670
|
+
// src/version.ts
|
|
16671
|
+
var FERRICSTORE_SDK_VERSION = "0.2.0";
|
|
16672
|
+
var FERRICSTORE_MINIMUM_SERVER_VERSION = "0.8.0";
|
|
16673
|
+
var FERRICSTORE_NATIVE_PROTOCOL_VERSION = 1;
|
|
16355
16674
|
// Annotate the CommonJS export names for ESM import in node:
|
|
16356
16675
|
0 && (module.exports = {
|
|
16357
16676
|
BitmapStore,
|
|
16358
16677
|
BloomFilterStore,
|
|
16359
16678
|
COMMAND_OPCODES,
|
|
16360
|
-
COMPACT_RESPONSE_OPCODES,
|
|
16361
16679
|
ClaimHydrationError,
|
|
16362
16680
|
ConnectionClosedError,
|
|
16363
16681
|
CountMinSketchStore,
|
|
16364
16682
|
CuckooFilterStore,
|
|
16683
|
+
FERRICSTORE_MINIMUM_SERVER_VERSION,
|
|
16684
|
+
FERRICSTORE_NATIVE_PROTOCOL_VERSION,
|
|
16685
|
+
FERRICSTORE_SDK_VERSION,
|
|
16365
16686
|
FerricStoreClient,
|
|
16366
16687
|
FerricStoreError,
|
|
16367
16688
|
FlowAlreadyExistsError,
|