@harperfast/harper-pro 5.0.30 → 5.0.31
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/core/package-lock.json +37 -37
- package/core/resources/Table.ts +32 -2
- package/dist/core/resources/Table.js +23 -2
- package/dist/core/resources/Table.js.map +1 -1
- package/dist/replication/knownNodes.js +29 -1
- package/dist/replication/knownNodes.js.map +1 -1
- package/dist/replication/replicationConnection.js +75 -12
- package/dist/replication/replicationConnection.js.map +1 -1
- package/dist/replication/replicator.js +12 -2
- package/dist/replication/replicator.js.map +1 -1
- package/dist/replication/subscriptionManager.js +150 -9
- package/dist/replication/subscriptionManager.js.map +1 -1
- package/npm-shrinkwrap.json +37 -37
- package/package.json +1 -1
- package/replication/knownNodes.ts +31 -1
- package/replication/replicationConnection.ts +73 -12
- package/replication/replicator.ts +12 -2
- package/replication/subscriptionManager.ts +166 -9
- package/studio/web/assets/{index-CybLScHg.js → index-BA-5bmxI.js} +5 -5
- package/studio/web/assets/{index-CybLScHg.js.map → index-BA-5bmxI.js.map} +1 -1
- package/studio/web/assets/{index.lazy-DKx5-iXF.js → index.lazy-D97owG2z.js} +2 -2
- package/studio/web/assets/{index.lazy-DKx5-iXF.js.map → index.lazy-D97owG2z.js.map} +1 -1
- package/studio/web/assets/{profile-BOjes0Wl.js → profile-B-xiyCsJ.js} +2 -2
- package/studio/web/assets/{profile-BOjes0Wl.js.map → profile-B-xiyCsJ.js.map} +1 -1
- package/studio/web/assets/{status-EWKUIrjT.js → status-DEEb31XH.js} +2 -2
- package/studio/web/assets/{status-EWKUIrjT.js.map → status-DEEb31XH.js.map} +1 -1
- package/studio/web/index.html +1 -1
package/core/package-lock.json
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "harper",
|
|
3
|
-
"version": "5.0.
|
|
3
|
+
"version": "5.0.31",
|
|
4
4
|
"lockfileVersion": 3,
|
|
5
5
|
"requires": true,
|
|
6
6
|
"packages": {
|
|
7
7
|
"": {
|
|
8
8
|
"name": "harper",
|
|
9
|
-
"version": "5.0.
|
|
9
|
+
"version": "5.0.31",
|
|
10
10
|
"license": "Apache-2.0",
|
|
11
11
|
"dependencies": {
|
|
12
12
|
"@aws-sdk/client-s3": "^3.1012.0",
|
|
@@ -2218,9 +2218,9 @@
|
|
|
2218
2218
|
"license": "Apache-2.0"
|
|
2219
2219
|
},
|
|
2220
2220
|
"node_modules/@harperfast/rocksdb-js": {
|
|
2221
|
-
"version": "1.
|
|
2222
|
-
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js/-/rocksdb-js-1.
|
|
2223
|
-
"integrity": "sha512-
|
|
2221
|
+
"version": "1.5.0",
|
|
2222
|
+
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js/-/rocksdb-js-1.5.0.tgz",
|
|
2223
|
+
"integrity": "sha512-NyH8Nr+jOclzzFzPmN9aC58lvl7X7Gf94E/laJqIeWP7/dsrdbDgNPHBueBdh1JnAq5Fxd+qvEDf/PCGaA/cgw==",
|
|
2224
2224
|
"license": "Apache-2.0",
|
|
2225
2225
|
"dependencies": {
|
|
2226
2226
|
"@harperfast/extended-iterable": "1.0.3",
|
|
@@ -2234,20 +2234,20 @@
|
|
|
2234
2234
|
"node": ">=18"
|
|
2235
2235
|
},
|
|
2236
2236
|
"optionalDependencies": {
|
|
2237
|
-
"@harperfast/rocksdb-js-darwin-arm64": "1.
|
|
2238
|
-
"@harperfast/rocksdb-js-darwin-x64": "1.
|
|
2239
|
-
"@harperfast/rocksdb-js-linux-arm64-glibc": "1.
|
|
2240
|
-
"@harperfast/rocksdb-js-linux-arm64-musl": "1.
|
|
2241
|
-
"@harperfast/rocksdb-js-linux-x64-glibc": "1.
|
|
2242
|
-
"@harperfast/rocksdb-js-linux-x64-musl": "1.
|
|
2243
|
-
"@harperfast/rocksdb-js-win32-arm64": "1.
|
|
2244
|
-
"@harperfast/rocksdb-js-win32-x64": "1.
|
|
2237
|
+
"@harperfast/rocksdb-js-darwin-arm64": "1.5.0",
|
|
2238
|
+
"@harperfast/rocksdb-js-darwin-x64": "1.5.0",
|
|
2239
|
+
"@harperfast/rocksdb-js-linux-arm64-glibc": "1.5.0",
|
|
2240
|
+
"@harperfast/rocksdb-js-linux-arm64-musl": "1.5.0",
|
|
2241
|
+
"@harperfast/rocksdb-js-linux-x64-glibc": "1.5.0",
|
|
2242
|
+
"@harperfast/rocksdb-js-linux-x64-musl": "1.5.0",
|
|
2243
|
+
"@harperfast/rocksdb-js-win32-arm64": "1.5.0",
|
|
2244
|
+
"@harperfast/rocksdb-js-win32-x64": "1.5.0"
|
|
2245
2245
|
}
|
|
2246
2246
|
},
|
|
2247
2247
|
"node_modules/@harperfast/rocksdb-js-darwin-arm64": {
|
|
2248
|
-
"version": "1.
|
|
2249
|
-
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-darwin-arm64/-/rocksdb-js-darwin-arm64-1.
|
|
2250
|
-
"integrity": "sha512-
|
|
2248
|
+
"version": "1.5.0",
|
|
2249
|
+
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-darwin-arm64/-/rocksdb-js-darwin-arm64-1.5.0.tgz",
|
|
2250
|
+
"integrity": "sha512-g8P4H/imnxn/AoGp+R5TZjHbwezdcMJCyIqo+2F1bLm3lGGaqTMrrmXK7vXxLj/COUMbooJ04QlGei7+nGShhA==",
|
|
2251
2251
|
"cpu": [
|
|
2252
2252
|
"arm64"
|
|
2253
2253
|
],
|
|
@@ -2261,9 +2261,9 @@
|
|
|
2261
2261
|
}
|
|
2262
2262
|
},
|
|
2263
2263
|
"node_modules/@harperfast/rocksdb-js-darwin-x64": {
|
|
2264
|
-
"version": "1.
|
|
2265
|
-
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-darwin-x64/-/rocksdb-js-darwin-x64-1.
|
|
2266
|
-
"integrity": "sha512-
|
|
2264
|
+
"version": "1.5.0",
|
|
2265
|
+
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-darwin-x64/-/rocksdb-js-darwin-x64-1.5.0.tgz",
|
|
2266
|
+
"integrity": "sha512-62g7+n0G/QV2iBPFGV8ihCi6ZFW/4cxfe+SqQAOQ7p+YtA8/68o3X7b9j2+/fEixAC0ktLp/5mUie5hQVSmZrg==",
|
|
2267
2267
|
"cpu": [
|
|
2268
2268
|
"x64"
|
|
2269
2269
|
],
|
|
@@ -2277,9 +2277,9 @@
|
|
|
2277
2277
|
}
|
|
2278
2278
|
},
|
|
2279
2279
|
"node_modules/@harperfast/rocksdb-js-linux-arm64-glibc": {
|
|
2280
|
-
"version": "1.
|
|
2281
|
-
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-linux-arm64-glibc/-/rocksdb-js-linux-arm64-glibc-1.
|
|
2282
|
-
"integrity": "sha512-
|
|
2280
|
+
"version": "1.5.0",
|
|
2281
|
+
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-linux-arm64-glibc/-/rocksdb-js-linux-arm64-glibc-1.5.0.tgz",
|
|
2282
|
+
"integrity": "sha512-hls3Hg8tHIAwBLL+3VHsHHpZO/D1BWoPkN8cjq8vnVSLEAAYS1qyJpePY1hdwEsL8TD2jBPs5YZwMGQ2EQCiWQ==",
|
|
2283
2283
|
"cpu": [
|
|
2284
2284
|
"arm64"
|
|
2285
2285
|
],
|
|
@@ -2296,9 +2296,9 @@
|
|
|
2296
2296
|
}
|
|
2297
2297
|
},
|
|
2298
2298
|
"node_modules/@harperfast/rocksdb-js-linux-arm64-musl": {
|
|
2299
|
-
"version": "1.
|
|
2300
|
-
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-linux-arm64-musl/-/rocksdb-js-linux-arm64-musl-1.
|
|
2301
|
-
"integrity": "sha512-
|
|
2299
|
+
"version": "1.5.0",
|
|
2300
|
+
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-linux-arm64-musl/-/rocksdb-js-linux-arm64-musl-1.5.0.tgz",
|
|
2301
|
+
"integrity": "sha512-aS+/ZzoOAGiEcIfhpS0xPMMBlBKkEjZAVE9Y92yhVFaMIMhE8UhRPwu0tFyWos6BdyLQ7/Ud5ncR42ZIUh8Y1g==",
|
|
2302
2302
|
"cpu": [
|
|
2303
2303
|
"arm64"
|
|
2304
2304
|
],
|
|
@@ -2315,9 +2315,9 @@
|
|
|
2315
2315
|
}
|
|
2316
2316
|
},
|
|
2317
2317
|
"node_modules/@harperfast/rocksdb-js-linux-x64-glibc": {
|
|
2318
|
-
"version": "1.
|
|
2319
|
-
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-linux-x64-glibc/-/rocksdb-js-linux-x64-glibc-1.
|
|
2320
|
-
"integrity": "sha512-
|
|
2318
|
+
"version": "1.5.0",
|
|
2319
|
+
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-linux-x64-glibc/-/rocksdb-js-linux-x64-glibc-1.5.0.tgz",
|
|
2320
|
+
"integrity": "sha512-70kPD6KKwtRJMsBBnKm8JYP+QncIYl7xb02/dVswdv1I5AqN1UNeqJBU4+K4q6QP6FeNpK25oruz8S1iy8QkLQ==",
|
|
2321
2321
|
"cpu": [
|
|
2322
2322
|
"x64"
|
|
2323
2323
|
],
|
|
@@ -2334,9 +2334,9 @@
|
|
|
2334
2334
|
}
|
|
2335
2335
|
},
|
|
2336
2336
|
"node_modules/@harperfast/rocksdb-js-linux-x64-musl": {
|
|
2337
|
-
"version": "1.
|
|
2338
|
-
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-linux-x64-musl/-/rocksdb-js-linux-x64-musl-1.
|
|
2339
|
-
"integrity": "sha512-
|
|
2337
|
+
"version": "1.5.0",
|
|
2338
|
+
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-linux-x64-musl/-/rocksdb-js-linux-x64-musl-1.5.0.tgz",
|
|
2339
|
+
"integrity": "sha512-jnGa96c1w9L98ioGAzAezlni6Nls9LQ3A5Z4HYnPrY+Dz7Q9SeYANVv+edLR/Xt8fEQn9Yz6DkpYpns3ykUzGA==",
|
|
2340
2340
|
"cpu": [
|
|
2341
2341
|
"x64"
|
|
2342
2342
|
],
|
|
@@ -2353,9 +2353,9 @@
|
|
|
2353
2353
|
}
|
|
2354
2354
|
},
|
|
2355
2355
|
"node_modules/@harperfast/rocksdb-js-win32-arm64": {
|
|
2356
|
-
"version": "1.
|
|
2357
|
-
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-win32-arm64/-/rocksdb-js-win32-arm64-1.
|
|
2358
|
-
"integrity": "sha512-
|
|
2356
|
+
"version": "1.5.0",
|
|
2357
|
+
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-win32-arm64/-/rocksdb-js-win32-arm64-1.5.0.tgz",
|
|
2358
|
+
"integrity": "sha512-a3A68UqztdRS1Ind5UK9sytOJPoE9UJKlGt3623HVIaiQPfP3me9mx6YpnddqBshK0Lojzr5+cc6G1ewSFGEBw==",
|
|
2359
2359
|
"cpu": [
|
|
2360
2360
|
"arm64"
|
|
2361
2361
|
],
|
|
@@ -2369,9 +2369,9 @@
|
|
|
2369
2369
|
}
|
|
2370
2370
|
},
|
|
2371
2371
|
"node_modules/@harperfast/rocksdb-js-win32-x64": {
|
|
2372
|
-
"version": "1.
|
|
2373
|
-
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-win32-x64/-/rocksdb-js-win32-x64-1.
|
|
2374
|
-
"integrity": "sha512-
|
|
2372
|
+
"version": "1.5.0",
|
|
2373
|
+
"resolved": "https://registry.npmjs.org/@harperfast/rocksdb-js-win32-x64/-/rocksdb-js-win32-x64-1.5.0.tgz",
|
|
2374
|
+
"integrity": "sha512-0PKUTon/o5TUT3XBMPGPJl6Ry4aP/1D134HDP9XGSYWqtcQwzDb0LsRQdJhF9ixJQzVPrXw9mDGMQFzasVmvcw==",
|
|
2375
2375
|
"cpu": [
|
|
2376
2376
|
"x64"
|
|
2377
2377
|
],
|
package/core/resources/Table.ts
CHANGED
|
@@ -1733,6 +1733,32 @@ export function makeTable(options) {
|
|
|
1733
1733
|
// of the updates to the record to ensure consistency across the cluster
|
|
1734
1734
|
// TODO: can the previous version be older, but even more previous version be newer?
|
|
1735
1735
|
if (audit) {
|
|
1736
|
+
// A re-delivered out-of-order write (full-copy audit-replay re-delivers writes) must not have
|
|
1737
|
+
// its commutative ops re-folded. additionalAuditRefs is the record's own list of folded
|
|
1738
|
+
// out-of-order versions, read with read-your-writes consistency, so this skips the duplicate up
|
|
1739
|
+
// front — before the audit-log walk below, which can miss it: the walk stops at the depth cap, or
|
|
1740
|
+
// breaks early on a not-yet-visible audit entry, before reaching txnTime, and the keyed
|
|
1741
|
+
// transaction-log lookup it would otherwise use can lag a back-to-back re-delivery (that lag
|
|
1742
|
+
// silently double-applied the increment — #1137). This covers the re-delivery while the ref is
|
|
1743
|
+
// still on the record; a later in-order write rewrites the record and drops the ref (it survives
|
|
1744
|
+
// only as previousAdditionalAuditRefs on the audit log), so that case falls back to the
|
|
1745
|
+
// best-effort keyed lookup in the capped block below — see #1148. precedesExistingVersion(...)
|
|
1746
|
+
// === 0 is the identity tie: same version AND same node (the local node is id 0, so an undefined
|
|
1747
|
+
// options?.nodeId resolves to the same 0 the ref stored).
|
|
1748
|
+
if (
|
|
1749
|
+
existingEntry.additionalAuditRefs?.some(
|
|
1750
|
+
(ref) =>
|
|
1751
|
+
ref.version === txnTime &&
|
|
1752
|
+
precedesExistingVersion(
|
|
1753
|
+
txnTime,
|
|
1754
|
+
{ version: txnTime, localTime: txnTime, key: id, nodeId: ref.nodeId },
|
|
1755
|
+
options?.nodeId
|
|
1756
|
+
) === 0
|
|
1757
|
+
)
|
|
1758
|
+
) {
|
|
1759
|
+
write.skipped = true;
|
|
1760
|
+
return; // out-of-order write already folded into this record
|
|
1761
|
+
}
|
|
1736
1762
|
// incremental CRDT updates are only available with audit logging on
|
|
1737
1763
|
let localTime = existingEntry.localTime;
|
|
1738
1764
|
let auditedVersion = existingEntry.version;
|
|
@@ -1864,8 +1890,12 @@ export function makeTable(options) {
|
|
|
1864
1890
|
// retained window are not layered in — but the authoritative full-copy record restores exact
|
|
1865
1891
|
// convergence. Because we stopped before reaching txnTime, the inline duplicate detection in
|
|
1866
1892
|
// the walk never ran; full-copy audit-replay re-delivers writes, and re-applying one would
|
|
1867
|
-
// double-apply its commutative ops
|
|
1868
|
-
//
|
|
1893
|
+
// double-apply its commutative ops. A re-delivered out-of-order write is already ruled out by
|
|
1894
|
+
// the additionalAuditRefs check at the top of this block; this keyed lookup is the best-effort
|
|
1895
|
+
// guard for the remaining case — a re-delivered write that was originally in-order (so it left
|
|
1896
|
+
// no ref) and is now deeper than the cap. It is best-effort because the transaction-log lookup
|
|
1897
|
+
// can intermittently miss an entry under load (tracked separately); the authoritative full-copy
|
|
1898
|
+
// record still restores exact convergence.
|
|
1869
1899
|
logger.warn?.(
|
|
1870
1900
|
'Out-of-order audit reconciliation exceeded depth cap; reconciling against most recent updates only',
|
|
1871
1901
|
{
|
|
@@ -1623,6 +1623,23 @@ function makeTable(options) {
|
|
|
1623
1623
|
// of the updates to the record to ensure consistency across the cluster
|
|
1624
1624
|
// TODO: can the previous version be older, but even more previous version be newer?
|
|
1625
1625
|
if (audit) {
|
|
1626
|
+
// A re-delivered out-of-order write (full-copy audit-replay re-delivers writes) must not have
|
|
1627
|
+
// its commutative ops re-folded. additionalAuditRefs is the record's own list of folded
|
|
1628
|
+
// out-of-order versions, read with read-your-writes consistency, so this skips the duplicate up
|
|
1629
|
+
// front — before the audit-log walk below, which can miss it: the walk stops at the depth cap, or
|
|
1630
|
+
// breaks early on a not-yet-visible audit entry, before reaching txnTime, and the keyed
|
|
1631
|
+
// transaction-log lookup it would otherwise use can lag a back-to-back re-delivery (that lag
|
|
1632
|
+
// silently double-applied the increment — #1137). This covers the re-delivery while the ref is
|
|
1633
|
+
// still on the record; a later in-order write rewrites the record and drops the ref (it survives
|
|
1634
|
+
// only as previousAdditionalAuditRefs on the audit log), so that case falls back to the
|
|
1635
|
+
// best-effort keyed lookup in the capped block below — see #1148. precedesExistingVersion(...)
|
|
1636
|
+
// === 0 is the identity tie: same version AND same node (the local node is id 0, so an undefined
|
|
1637
|
+
// options?.nodeId resolves to the same 0 the ref stored).
|
|
1638
|
+
if (existingEntry.additionalAuditRefs?.some((ref) => ref.version === txnTime &&
|
|
1639
|
+
precedesExistingVersion(txnTime, { version: txnTime, localTime: txnTime, key: id, nodeId: ref.nodeId }, options?.nodeId) === 0)) {
|
|
1640
|
+
write.skipped = true;
|
|
1641
|
+
return; // out-of-order write already folded into this record
|
|
1642
|
+
}
|
|
1626
1643
|
// incremental CRDT updates are only available with audit logging on
|
|
1627
1644
|
let localTime = existingEntry.localTime;
|
|
1628
1645
|
let auditedVersion = existingEntry.version;
|
|
@@ -1733,8 +1750,12 @@ function makeTable(options) {
|
|
|
1733
1750
|
// retained window are not layered in — but the authoritative full-copy record restores exact
|
|
1734
1751
|
// convergence. Because we stopped before reaching txnTime, the inline duplicate detection in
|
|
1735
1752
|
// the walk never ran; full-copy audit-replay re-delivers writes, and re-applying one would
|
|
1736
|
-
// double-apply its commutative ops
|
|
1737
|
-
//
|
|
1753
|
+
// double-apply its commutative ops. A re-delivered out-of-order write is already ruled out by
|
|
1754
|
+
// the additionalAuditRefs check at the top of this block; this keyed lookup is the best-effort
|
|
1755
|
+
// guard for the remaining case — a re-delivered write that was originally in-order (so it left
|
|
1756
|
+
// no ref) and is now deeper than the cap. It is best-effort because the transaction-log lookup
|
|
1757
|
+
// can intermittently miss an entry under load (tracked separately); the authoritative full-copy
|
|
1758
|
+
// record still restores exact convergence.
|
|
1738
1759
|
logger_ts_1.logger.warn?.('Out-of-order audit reconciliation exceeded depth cap; reconciling against most recent updates only', {
|
|
1739
1760
|
table: tableName,
|
|
1740
1761
|
id,
|