cojson 0.19.22 → 0.20.1
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/.turbo/turbo-build.log +1 -1
- package/CHANGELOG.md +66 -0
- package/dist/PeerState.d.ts +6 -1
- package/dist/PeerState.d.ts.map +1 -1
- package/dist/PeerState.js +18 -3
- package/dist/PeerState.js.map +1 -1
- package/dist/coValueContentMessage.d.ts +0 -2
- package/dist/coValueContentMessage.d.ts.map +1 -1
- package/dist/coValueContentMessage.js +0 -8
- package/dist/coValueContentMessage.js.map +1 -1
- package/dist/coValueCore/SessionMap.d.ts +4 -2
- package/dist/coValueCore/SessionMap.d.ts.map +1 -1
- package/dist/coValueCore/SessionMap.js +30 -0
- package/dist/coValueCore/SessionMap.js.map +1 -1
- package/dist/coValueCore/coValueCore.d.ts +70 -5
- package/dist/coValueCore/coValueCore.d.ts.map +1 -1
- package/dist/coValueCore/coValueCore.js +302 -31
- package/dist/coValueCore/coValueCore.js.map +1 -1
- package/dist/coValueCore/verifiedState.d.ts +6 -1
- package/dist/coValueCore/verifiedState.d.ts.map +1 -1
- package/dist/coValueCore/verifiedState.js +9 -0
- package/dist/coValueCore/verifiedState.js.map +1 -1
- package/dist/coValues/coList.d.ts +4 -2
- package/dist/coValues/coList.d.ts.map +1 -1
- package/dist/coValues/coList.js +3 -0
- package/dist/coValues/coList.js.map +1 -1
- package/dist/coValues/group.d.ts.map +1 -1
- package/dist/coValues/group.js +3 -6
- package/dist/coValues/group.js.map +1 -1
- package/dist/config.d.ts +2 -8
- package/dist/config.d.ts.map +1 -1
- package/dist/config.js +4 -12
- package/dist/config.js.map +1 -1
- package/dist/crypto/NapiCrypto.d.ts +1 -2
- package/dist/crypto/NapiCrypto.d.ts.map +1 -1
- package/dist/crypto/NapiCrypto.js +19 -4
- package/dist/crypto/NapiCrypto.js.map +1 -1
- package/dist/crypto/RNCrypto.d.ts.map +1 -1
- package/dist/crypto/RNCrypto.js +19 -4
- package/dist/crypto/RNCrypto.js.map +1 -1
- package/dist/crypto/WasmCrypto.d.ts +11 -4
- package/dist/crypto/WasmCrypto.d.ts.map +1 -1
- package/dist/crypto/WasmCrypto.js +52 -10
- package/dist/crypto/WasmCrypto.js.map +1 -1
- package/dist/crypto/WasmCryptoEdge.d.ts +1 -0
- package/dist/crypto/WasmCryptoEdge.d.ts.map +1 -1
- package/dist/crypto/WasmCryptoEdge.js +4 -1
- package/dist/crypto/WasmCryptoEdge.js.map +1 -1
- package/dist/crypto/crypto.d.ts +3 -3
- package/dist/crypto/crypto.d.ts.map +1 -1
- package/dist/crypto/crypto.js +6 -1
- package/dist/crypto/crypto.js.map +1 -1
- package/dist/exports.d.ts +5 -5
- package/dist/exports.d.ts.map +1 -1
- package/dist/exports.js +4 -3
- package/dist/exports.js.map +1 -1
- package/dist/ids.d.ts +4 -1
- package/dist/ids.d.ts.map +1 -1
- package/dist/ids.js +4 -0
- package/dist/ids.js.map +1 -1
- package/dist/knownState.d.ts +2 -0
- package/dist/knownState.d.ts.map +1 -1
- package/dist/localNode.d.ts +12 -0
- package/dist/localNode.d.ts.map +1 -1
- package/dist/localNode.js +14 -0
- package/dist/localNode.js.map +1 -1
- package/dist/platformUtils.d.ts +3 -0
- package/dist/platformUtils.d.ts.map +1 -0
- package/dist/platformUtils.js +24 -0
- package/dist/platformUtils.js.map +1 -0
- package/dist/queue/LinkedList.d.ts +9 -3
- package/dist/queue/LinkedList.d.ts.map +1 -1
- package/dist/queue/LinkedList.js +30 -1
- package/dist/queue/LinkedList.js.map +1 -1
- package/dist/queue/OutgoingLoadQueue.d.ts +95 -0
- package/dist/queue/OutgoingLoadQueue.d.ts.map +1 -0
- package/dist/queue/OutgoingLoadQueue.js +240 -0
- package/dist/queue/OutgoingLoadQueue.js.map +1 -0
- package/dist/storage/DeletedCoValuesEraserScheduler.d.ts +30 -0
- package/dist/storage/DeletedCoValuesEraserScheduler.d.ts.map +1 -0
- package/dist/storage/DeletedCoValuesEraserScheduler.js +84 -0
- package/dist/storage/DeletedCoValuesEraserScheduler.js.map +1 -0
- package/dist/storage/sqlite/client.d.ts +3 -0
- package/dist/storage/sqlite/client.d.ts.map +1 -1
- package/dist/storage/sqlite/client.js +44 -0
- package/dist/storage/sqlite/client.js.map +1 -1
- package/dist/storage/sqlite/sqliteMigrations.d.ts.map +1 -1
- package/dist/storage/sqlite/sqliteMigrations.js +7 -0
- package/dist/storage/sqlite/sqliteMigrations.js.map +1 -1
- package/dist/storage/sqliteAsync/client.d.ts +3 -0
- package/dist/storage/sqliteAsync/client.d.ts.map +1 -1
- package/dist/storage/sqliteAsync/client.js +42 -0
- package/dist/storage/sqliteAsync/client.js.map +1 -1
- package/dist/storage/storageAsync.d.ts +7 -0
- package/dist/storage/storageAsync.d.ts.map +1 -1
- package/dist/storage/storageAsync.js +48 -0
- package/dist/storage/storageAsync.js.map +1 -1
- package/dist/storage/storageSync.d.ts +6 -0
- package/dist/storage/storageSync.d.ts.map +1 -1
- package/dist/storage/storageSync.js +42 -0
- package/dist/storage/storageSync.js.map +1 -1
- package/dist/storage/types.d.ts +59 -0
- package/dist/storage/types.d.ts.map +1 -1
- package/dist/storage/types.js +12 -1
- package/dist/storage/types.js.map +1 -1
- package/dist/sync.d.ts.map +1 -1
- package/dist/sync.js +66 -43
- package/dist/sync.js.map +1 -1
- package/dist/tests/DeletedCoValuesEraserScheduler.test.d.ts +2 -0
- package/dist/tests/DeletedCoValuesEraserScheduler.test.d.ts.map +1 -0
- package/dist/tests/DeletedCoValuesEraserScheduler.test.js +149 -0
- package/dist/tests/DeletedCoValuesEraserScheduler.test.js.map +1 -0
- package/dist/tests/GarbageCollector.test.js +5 -6
- package/dist/tests/GarbageCollector.test.js.map +1 -1
- package/dist/tests/LinkedList.test.js +90 -0
- package/dist/tests/LinkedList.test.js.map +1 -1
- package/dist/tests/OutgoingLoadQueue.test.d.ts +2 -0
- package/dist/tests/OutgoingLoadQueue.test.d.ts.map +1 -0
- package/dist/tests/OutgoingLoadQueue.test.js +814 -0
- package/dist/tests/OutgoingLoadQueue.test.js.map +1 -0
- package/dist/tests/StorageApiAsync.test.js +484 -152
- package/dist/tests/StorageApiAsync.test.js.map +1 -1
- package/dist/tests/StorageApiSync.test.js +505 -136
- package/dist/tests/StorageApiSync.test.js.map +1 -1
- package/dist/tests/WasmCrypto.test.js +6 -3
- package/dist/tests/WasmCrypto.test.js.map +1 -1
- package/dist/tests/coValueCore.loadFromStorage.test.js +3 -0
- package/dist/tests/coValueCore.loadFromStorage.test.js.map +1 -1
- package/dist/tests/coValueCore.test.js +34 -13
- package/dist/tests/coValueCore.test.js.map +1 -1
- package/dist/tests/coreWasm.test.js +127 -4
- package/dist/tests/coreWasm.test.js.map +1 -1
- package/dist/tests/crypto.test.js +89 -93
- package/dist/tests/crypto.test.js.map +1 -1
- package/dist/tests/deleteCoValue.test.d.ts +2 -0
- package/dist/tests/deleteCoValue.test.d.ts.map +1 -0
- package/dist/tests/deleteCoValue.test.js +313 -0
- package/dist/tests/deleteCoValue.test.js.map +1 -0
- package/dist/tests/group.removeMember.test.js +18 -30
- package/dist/tests/group.removeMember.test.js.map +1 -1
- package/dist/tests/knownState.lazyLoading.test.js +3 -0
- package/dist/tests/knownState.lazyLoading.test.js.map +1 -1
- package/dist/tests/sync.concurrentLoad.test.d.ts +2 -0
- package/dist/tests/sync.concurrentLoad.test.d.ts.map +1 -0
- package/dist/tests/sync.concurrentLoad.test.js +481 -0
- package/dist/tests/sync.concurrentLoad.test.js.map +1 -0
- package/dist/tests/sync.deleted.test.d.ts +2 -0
- package/dist/tests/sync.deleted.test.d.ts.map +1 -0
- package/dist/tests/sync.deleted.test.js +214 -0
- package/dist/tests/sync.deleted.test.js.map +1 -0
- package/dist/tests/sync.mesh.test.js +3 -2
- package/dist/tests/sync.mesh.test.js.map +1 -1
- package/dist/tests/sync.storage.test.js +4 -3
- package/dist/tests/sync.storage.test.js.map +1 -1
- package/dist/tests/sync.test.js +3 -2
- package/dist/tests/sync.test.js.map +1 -1
- package/dist/tests/testStorage.d.ts +3 -0
- package/dist/tests/testStorage.d.ts.map +1 -1
- package/dist/tests/testStorage.js +17 -1
- package/dist/tests/testStorage.js.map +1 -1
- package/dist/tests/testUtils.d.ts +7 -3
- package/dist/tests/testUtils.d.ts.map +1 -1
- package/dist/tests/testUtils.js +19 -4
- package/dist/tests/testUtils.js.map +1 -1
- package/package.json +6 -16
- package/src/PeerState.ts +26 -3
- package/src/coValueContentMessage.ts +0 -14
- package/src/coValueCore/SessionMap.ts +43 -1
- package/src/coValueCore/coValueCore.ts +415 -27
- package/src/coValueCore/verifiedState.ts +26 -3
- package/src/coValues/coList.ts +9 -3
- package/src/coValues/group.ts +5 -6
- package/src/config.ts +4 -13
- package/src/crypto/NapiCrypto.ts +29 -13
- package/src/crypto/RNCrypto.ts +29 -11
- package/src/crypto/WasmCrypto.ts +67 -20
- package/src/crypto/WasmCryptoEdge.ts +5 -1
- package/src/crypto/crypto.ts +16 -4
- package/src/exports.ts +4 -2
- package/src/ids.ts +11 -1
- package/src/localNode.ts +15 -0
- package/src/platformUtils.ts +26 -0
- package/src/queue/LinkedList.ts +34 -4
- package/src/queue/OutgoingLoadQueue.ts +307 -0
- package/src/storage/DeletedCoValuesEraserScheduler.ts +124 -0
- package/src/storage/sqlite/client.ts +77 -0
- package/src/storage/sqlite/sqliteMigrations.ts +7 -0
- package/src/storage/sqliteAsync/client.ts +75 -0
- package/src/storage/storageAsync.ts +62 -0
- package/src/storage/storageSync.ts +58 -0
- package/src/storage/types.ts +69 -0
- package/src/sync.ts +78 -46
- package/src/tests/DeletedCoValuesEraserScheduler.test.ts +185 -0
- package/src/tests/GarbageCollector.test.ts +6 -10
- package/src/tests/LinkedList.test.ts +111 -0
- package/src/tests/OutgoingLoadQueue.test.ts +1129 -0
- package/src/tests/StorageApiAsync.test.ts +572 -162
- package/src/tests/StorageApiSync.test.ts +580 -143
- package/src/tests/WasmCrypto.test.ts +8 -3
- package/src/tests/coValueCore.loadFromStorage.test.ts +6 -0
- package/src/tests/coValueCore.test.ts +49 -14
- package/src/tests/coreWasm.test.ts +319 -10
- package/src/tests/crypto.test.ts +141 -150
- package/src/tests/deleteCoValue.test.ts +528 -0
- package/src/tests/group.removeMember.test.ts +35 -35
- package/src/tests/knownState.lazyLoading.test.ts +6 -0
- package/src/tests/sync.concurrentLoad.test.ts +650 -0
- package/src/tests/sync.deleted.test.ts +294 -0
- package/src/tests/sync.mesh.test.ts +5 -2
- package/src/tests/sync.storage.test.ts +6 -3
- package/src/tests/sync.test.ts +5 -2
- package/src/tests/testStorage.ts +31 -2
- package/src/tests/testUtils.ts +31 -10
- package/dist/crypto/PureJSCrypto.d.ts +0 -77
- package/dist/crypto/PureJSCrypto.d.ts.map +0 -1
- package/dist/crypto/PureJSCrypto.js +0 -236
- package/dist/crypto/PureJSCrypto.js.map +0 -1
- package/dist/tests/PureJSCrypto.test.d.ts +0 -2
- package/dist/tests/PureJSCrypto.test.d.ts.map +0 -1
- package/dist/tests/PureJSCrypto.test.js +0 -145
- package/dist/tests/PureJSCrypto.test.js.map +0 -1
- package/src/crypto/PureJSCrypto.ts +0 -429
- package/src/tests/PureJSCrypto.test.ts +0 -217
|
@@ -0,0 +1,481 @@
|
|
|
1
|
+
import { afterEach, beforeEach, describe, expect, test, vi } from "vitest";
|
|
2
|
+
import { CO_VALUE_LOADING_CONFIG, setMaxInFlightLoadsPerPeer, } from "../config.js";
|
|
3
|
+
import { blockMessageTypeOnOutgoingPeer, fillCoMapWithLargeData, loadCoValueOrFail, importContentIntoNode, setupTestNode, SyncMessagesLog, TEST_NODE_CONFIG, waitFor, } from "./testUtils.js";
|
|
4
|
+
let jazzCloud;
|
|
5
|
+
// Store original config values
|
|
6
|
+
let originalMaxInFlightLoads;
|
|
7
|
+
let originalTimeout;
|
|
8
|
+
beforeEach(async () => {
|
|
9
|
+
// We want to simulate a real world communication that happens asynchronously
|
|
10
|
+
TEST_NODE_CONFIG.withAsyncPeers = true;
|
|
11
|
+
originalMaxInFlightLoads =
|
|
12
|
+
CO_VALUE_LOADING_CONFIG.MAX_IN_FLIGHT_LOADS_PER_PEER;
|
|
13
|
+
originalTimeout = CO_VALUE_LOADING_CONFIG.TIMEOUT;
|
|
14
|
+
SyncMessagesLog.clear();
|
|
15
|
+
jazzCloud = setupTestNode({ isSyncServer: true });
|
|
16
|
+
});
|
|
17
|
+
afterEach(() => {
|
|
18
|
+
// Restore original config
|
|
19
|
+
setMaxInFlightLoadsPerPeer(originalMaxInFlightLoads);
|
|
20
|
+
CO_VALUE_LOADING_CONFIG.TIMEOUT = originalTimeout;
|
|
21
|
+
vi.useRealTimers();
|
|
22
|
+
});
|
|
23
|
+
describe("concurrent load", () => {
|
|
24
|
+
test("should throttle load requests when at capacity", async () => {
|
|
25
|
+
setMaxInFlightLoadsPerPeer(2);
|
|
26
|
+
const client = setupTestNode({
|
|
27
|
+
connected: false,
|
|
28
|
+
});
|
|
29
|
+
const { peerOnServer } = client.connectToSyncServer();
|
|
30
|
+
// Create multiple CoValues on the server
|
|
31
|
+
const group = jazzCloud.node.createGroup();
|
|
32
|
+
const map1 = group.createMap();
|
|
33
|
+
const map2 = group.createMap();
|
|
34
|
+
const map3 = group.createMap();
|
|
35
|
+
map1.set("key", "value1");
|
|
36
|
+
map2.set("key", "value2");
|
|
37
|
+
map3.set("key", "value3");
|
|
38
|
+
// Block content responses to see the throttling effect
|
|
39
|
+
const blocker = blockMessageTypeOnOutgoingPeer(peerOnServer, "content", {});
|
|
40
|
+
// Start loading all three
|
|
41
|
+
const promise1 = client.node.loadCoValueCore(map1.id);
|
|
42
|
+
const promise2 = client.node.loadCoValueCore(map2.id);
|
|
43
|
+
const promise3 = client.node.loadCoValueCore(map3.id);
|
|
44
|
+
// Wait for messages to be sent
|
|
45
|
+
await new Promise((resolve) => setTimeout(resolve, 10));
|
|
46
|
+
// Get the LOAD messages sent
|
|
47
|
+
const loadMessages = SyncMessagesLog.messages.filter((m) => m.msg.action === "load");
|
|
48
|
+
// Only 2 LOAD messages should have been sent (throttled)
|
|
49
|
+
expect(loadMessages.length).toBe(2);
|
|
50
|
+
// Unblock and let it complete
|
|
51
|
+
blocker.unblock();
|
|
52
|
+
blocker.sendBlockedMessages();
|
|
53
|
+
await Promise.all([promise1, promise2, promise3]);
|
|
54
|
+
// After completion, all 3 should have been loaded
|
|
55
|
+
const allLoadMessages = SyncMessagesLog.messages.filter((m) => m.msg.action === "load");
|
|
56
|
+
expect(allLoadMessages.length).toBe(3);
|
|
57
|
+
// Verify all were loaded successfully despite throttling
|
|
58
|
+
expect(SyncMessagesLog.getMessages({
|
|
59
|
+
Group: group.core,
|
|
60
|
+
Map1: map1.core,
|
|
61
|
+
Map2: map2.core,
|
|
62
|
+
Map3: map3.core,
|
|
63
|
+
})).toMatchInlineSnapshot(`
|
|
64
|
+
[
|
|
65
|
+
"client -> server | LOAD Map1 sessions: empty",
|
|
66
|
+
"client -> server | LOAD Map2 sessions: empty",
|
|
67
|
+
"server -> client | CONTENT Group header: true new: After: 0 New: 3",
|
|
68
|
+
"server -> client | CONTENT Map1 header: true new: After: 0 New: 1",
|
|
69
|
+
"server -> client | CONTENT Map2 header: true new: After: 0 New: 1",
|
|
70
|
+
"client -> server | KNOWN Group sessions: header/3",
|
|
71
|
+
"client -> server | KNOWN Map1 sessions: header/1",
|
|
72
|
+
"client -> server | LOAD Map3 sessions: empty",
|
|
73
|
+
"client -> server | KNOWN Map2 sessions: header/1",
|
|
74
|
+
"server -> client | CONTENT Map3 header: true new: After: 0 New: 1",
|
|
75
|
+
"client -> server | KNOWN Map3 sessions: header/1",
|
|
76
|
+
]
|
|
77
|
+
`);
|
|
78
|
+
});
|
|
79
|
+
test("should process pending loads when capacity becomes available", async () => {
|
|
80
|
+
setMaxInFlightLoadsPerPeer(1);
|
|
81
|
+
const client = setupTestNode({
|
|
82
|
+
connected: true,
|
|
83
|
+
});
|
|
84
|
+
// Create multiple CoValues on the server
|
|
85
|
+
const group = jazzCloud.node.createGroup();
|
|
86
|
+
const map1 = group.createMap();
|
|
87
|
+
const map2 = group.createMap();
|
|
88
|
+
map1.set("key", "value1", "trusting");
|
|
89
|
+
map2.set("key", "value2", "trusting");
|
|
90
|
+
// Load both sequentially due to throttling
|
|
91
|
+
const [result1, result2] = await Promise.all([
|
|
92
|
+
loadCoValueOrFail(client.node, map1.id),
|
|
93
|
+
loadCoValueOrFail(client.node, map2.id),
|
|
94
|
+
]);
|
|
95
|
+
expect(result1.get("key")).toBe("value1");
|
|
96
|
+
expect(result2.get("key")).toBe("value2");
|
|
97
|
+
// Verify both were loaded successfully despite throttling
|
|
98
|
+
expect(SyncMessagesLog.getMessages({
|
|
99
|
+
Group: group.core,
|
|
100
|
+
Map1: map1.core,
|
|
101
|
+
Map2: map2.core,
|
|
102
|
+
})).toMatchInlineSnapshot(`
|
|
103
|
+
[
|
|
104
|
+
"client -> server | LOAD Map1 sessions: empty",
|
|
105
|
+
"server -> client | CONTENT Group header: true new: After: 0 New: 3",
|
|
106
|
+
"server -> client | CONTENT Map1 header: true new: After: 0 New: 1",
|
|
107
|
+
"client -> server | KNOWN Group sessions: header/3",
|
|
108
|
+
"client -> server | KNOWN Map1 sessions: header/1",
|
|
109
|
+
"client -> server | LOAD Map2 sessions: empty",
|
|
110
|
+
"server -> client | CONTENT Map2 header: true new: After: 0 New: 1",
|
|
111
|
+
"client -> server | KNOWN Map2 sessions: header/1",
|
|
112
|
+
]
|
|
113
|
+
`);
|
|
114
|
+
});
|
|
115
|
+
test("should prioritize unavailable CoValues over available ones", async () => {
|
|
116
|
+
setMaxInFlightLoadsPerPeer(1);
|
|
117
|
+
const client = setupTestNode({
|
|
118
|
+
connected: true,
|
|
119
|
+
});
|
|
120
|
+
// Create CoValues on the server
|
|
121
|
+
const group = jazzCloud.node.createGroup();
|
|
122
|
+
const map1 = group.createMap();
|
|
123
|
+
const map2 = group.createMap();
|
|
124
|
+
const map3 = group.createMap();
|
|
125
|
+
map1.set("key", "value1", "trusting");
|
|
126
|
+
map2.set("key", "value2", "trusting");
|
|
127
|
+
map3.set("key", "value3", "trusting");
|
|
128
|
+
// First, load map1 to make it "available" locally
|
|
129
|
+
await loadCoValueOrFail(client.node, map1.id);
|
|
130
|
+
SyncMessagesLog.clear();
|
|
131
|
+
// Update map1 on server (so client has stale version)
|
|
132
|
+
map1.set("key", "updated1", "trusting");
|
|
133
|
+
// Now load map2 (unavailable) and reload map1 (available but outdated)
|
|
134
|
+
// map2 should be prioritized
|
|
135
|
+
const [result1, result2] = await Promise.all([
|
|
136
|
+
loadCoValueOrFail(client.node, map1.id), // Available, lower priority
|
|
137
|
+
loadCoValueOrFail(client.node, map2.id), // Unavailable, higher priority
|
|
138
|
+
]);
|
|
139
|
+
// Both should succeed
|
|
140
|
+
expect(result2.get("key")).toBe("value2");
|
|
141
|
+
// map2 (unavailable) should have been loaded first
|
|
142
|
+
const loadMessages = SyncMessagesLog.messages.filter((m) => m.msg.action === "load");
|
|
143
|
+
expect(loadMessages.length).toBeGreaterThanOrEqual(1);
|
|
144
|
+
// The first load should be for map2 (unavailable, high priority)
|
|
145
|
+
expect(loadMessages[0]?.msg).toMatchObject({
|
|
146
|
+
action: "load",
|
|
147
|
+
id: map2.id,
|
|
148
|
+
});
|
|
149
|
+
});
|
|
150
|
+
test("should handle high load with many concurrent requests", async () => {
|
|
151
|
+
setMaxInFlightLoadsPerPeer(5);
|
|
152
|
+
const client = setupTestNode({
|
|
153
|
+
connected: true,
|
|
154
|
+
});
|
|
155
|
+
// Create many CoValues on the server
|
|
156
|
+
const group = jazzCloud.node.createGroup();
|
|
157
|
+
const maps = Array.from({ length: 20 }, (_, i) => {
|
|
158
|
+
const map = group.createMap();
|
|
159
|
+
map.set("index", i, "trusting");
|
|
160
|
+
return map;
|
|
161
|
+
});
|
|
162
|
+
// Load all of them concurrently
|
|
163
|
+
const results = await Promise.all(maps.map((map) => loadCoValueOrFail(client.node, map.id)));
|
|
164
|
+
// All should have been loaded successfully
|
|
165
|
+
results.forEach((result, i) => {
|
|
166
|
+
expect(result.get("index")).toBe(i);
|
|
167
|
+
});
|
|
168
|
+
});
|
|
169
|
+
test("should timeout load requests that take too long", async () => {
|
|
170
|
+
vi.useFakeTimers();
|
|
171
|
+
setMaxInFlightLoadsPerPeer(1);
|
|
172
|
+
CO_VALUE_LOADING_CONFIG.TIMEOUT = 1000;
|
|
173
|
+
const client = setupTestNode({
|
|
174
|
+
connected: false,
|
|
175
|
+
});
|
|
176
|
+
const { peerOnServer } = client.connectToSyncServer();
|
|
177
|
+
// Create a CoValue on the server
|
|
178
|
+
const group = jazzCloud.node.createGroup();
|
|
179
|
+
const map = group.createMap();
|
|
180
|
+
map.set("key", "value");
|
|
181
|
+
// Block content to simulate a slow/unresponsive server
|
|
182
|
+
const blocker = blockMessageTypeOnOutgoingPeer(peerOnServer, "content", {
|
|
183
|
+
id: map.id,
|
|
184
|
+
});
|
|
185
|
+
const loadPromise = client.node.loadCoValueCore(map.id);
|
|
186
|
+
// Advance past the timeout
|
|
187
|
+
await vi.advanceTimersByTimeAsync(CO_VALUE_LOADING_CONFIG.TIMEOUT + 100);
|
|
188
|
+
// The queue slot should be freed
|
|
189
|
+
// The second retry attempt should happen after RETRY_DELAY
|
|
190
|
+
await vi.advanceTimersByTimeAsync(CO_VALUE_LOADING_CONFIG.RETRY_DELAY + 100);
|
|
191
|
+
// Unblock to let retries succeed
|
|
192
|
+
blocker.sendBlockedMessages();
|
|
193
|
+
blocker.unblock();
|
|
194
|
+
// Wait for the retry to complete
|
|
195
|
+
await vi.advanceTimersByTimeAsync(100);
|
|
196
|
+
const result = await loadPromise;
|
|
197
|
+
// The retry should have succeeded (since we unblocked)
|
|
198
|
+
expect(result.isAvailable()).toBe(true);
|
|
199
|
+
});
|
|
200
|
+
test("should free queue slots on disconnect", async () => {
|
|
201
|
+
setMaxInFlightLoadsPerPeer(2);
|
|
202
|
+
const client = setupTestNode({
|
|
203
|
+
connected: false,
|
|
204
|
+
});
|
|
205
|
+
const { peerState, peerOnServer } = client.connectToSyncServer();
|
|
206
|
+
// Create CoValues on the server
|
|
207
|
+
const group = jazzCloud.node.createGroup();
|
|
208
|
+
const map1 = group.createMap();
|
|
209
|
+
const map2 = group.createMap();
|
|
210
|
+
const map3 = group.createMap();
|
|
211
|
+
// Block content to keep requests in-flight
|
|
212
|
+
const blocker = blockMessageTypeOnOutgoingPeer(peerOnServer, "content", {});
|
|
213
|
+
// Start loading (will be in-flight)
|
|
214
|
+
client.node.loadCoValueCore(map1.id);
|
|
215
|
+
client.node.loadCoValueCore(map2.id);
|
|
216
|
+
client.node.loadCoValueCore(map3.id);
|
|
217
|
+
await new Promise((resolve) => setTimeout(resolve, 10));
|
|
218
|
+
// Disconnect
|
|
219
|
+
peerState.gracefulShutdown();
|
|
220
|
+
// Queue should be cleared
|
|
221
|
+
// Reconnect and verify new requests can be sent
|
|
222
|
+
client.connectToSyncServer();
|
|
223
|
+
const result = await loadCoValueOrFail(client.node, map1.id);
|
|
224
|
+
expect(result.get("key")).toBeUndefined(); // map1 was created without a key
|
|
225
|
+
blocker.unblock();
|
|
226
|
+
});
|
|
227
|
+
test("should handle reconnection with pending loads", async () => {
|
|
228
|
+
setMaxInFlightLoadsPerPeer(1);
|
|
229
|
+
const client = setupTestNode({
|
|
230
|
+
connected: false,
|
|
231
|
+
});
|
|
232
|
+
const { peerState, peerOnServer } = client.connectToSyncServer({
|
|
233
|
+
persistent: true,
|
|
234
|
+
});
|
|
235
|
+
// Create a CoValue on the server
|
|
236
|
+
const group = jazzCloud.node.createGroup();
|
|
237
|
+
const map = group.createMap();
|
|
238
|
+
map.set("key", "value");
|
|
239
|
+
// Block content to keep request in-flight
|
|
240
|
+
blockMessageTypeOnOutgoingPeer(peerOnServer, "content", {
|
|
241
|
+
id: map.id,
|
|
242
|
+
});
|
|
243
|
+
// Start loading
|
|
244
|
+
const loadPromise = client.node.loadCoValueCore(map.id);
|
|
245
|
+
await new Promise((resolve) => setTimeout(resolve, 10));
|
|
246
|
+
// Disconnect
|
|
247
|
+
peerState.gracefulShutdown();
|
|
248
|
+
// Reconnect
|
|
249
|
+
client.connectToSyncServer({
|
|
250
|
+
persistent: true,
|
|
251
|
+
});
|
|
252
|
+
// The load should complete after reconnection
|
|
253
|
+
const result = await loadPromise;
|
|
254
|
+
expect(result.isAvailable()).toBe(true);
|
|
255
|
+
});
|
|
256
|
+
test("should maintain FIFO order for queued requests", async () => {
|
|
257
|
+
setMaxInFlightLoadsPerPeer(1);
|
|
258
|
+
const client = setupTestNode({
|
|
259
|
+
connected: false,
|
|
260
|
+
});
|
|
261
|
+
const { peerOnServer } = client.connectToSyncServer();
|
|
262
|
+
// Create CoValues on the server
|
|
263
|
+
const group = jazzCloud.node.createGroup();
|
|
264
|
+
const maps = Array.from({ length: 5 }, () => group.createMap());
|
|
265
|
+
// Block content to build up the queue
|
|
266
|
+
const blocker = blockMessageTypeOnOutgoingPeer(peerOnServer, "content", {});
|
|
267
|
+
// Start loading all maps (first one goes in-flight, rest queued)
|
|
268
|
+
const loadPromises = maps.map((map) => client.node.loadCoValueCore(map.id));
|
|
269
|
+
await new Promise((resolve) => setTimeout(resolve, 10));
|
|
270
|
+
// Get the LOAD messages before unblocking
|
|
271
|
+
const loadMessagesBefore = SyncMessagesLog.messages.filter((m) => m.msg.action === "load");
|
|
272
|
+
// Only 1 should be sent (at capacity)
|
|
273
|
+
expect(loadMessagesBefore.length).toBe(1);
|
|
274
|
+
expect(loadMessagesBefore[0]?.msg).toMatchObject({
|
|
275
|
+
action: "load",
|
|
276
|
+
id: maps[0]?.id,
|
|
277
|
+
});
|
|
278
|
+
// Unblock to process the queue
|
|
279
|
+
blocker.sendBlockedMessages();
|
|
280
|
+
blocker.unblock();
|
|
281
|
+
await Promise.all(loadPromises);
|
|
282
|
+
// Verify all LOAD messages were sent
|
|
283
|
+
const allLoadMessages = SyncMessagesLog.messages.filter((m) => m.msg.action === "load");
|
|
284
|
+
// All 5 should eventually be sent
|
|
285
|
+
expect(allLoadMessages.length).toBe(5);
|
|
286
|
+
// They should be in order (maps[0], maps[1], maps[2], maps[3], maps[4])
|
|
287
|
+
for (let i = 0; i < allLoadMessages.length; i++) {
|
|
288
|
+
expect(allLoadMessages[i]?.msg).toMatchObject({
|
|
289
|
+
action: "load",
|
|
290
|
+
id: maps[i]?.id,
|
|
291
|
+
});
|
|
292
|
+
}
|
|
293
|
+
});
|
|
294
|
+
test("should allow dependency loads to overflow the concurrency limit", async () => {
|
|
295
|
+
setMaxInFlightLoadsPerPeer(1);
|
|
296
|
+
const server = setupTestNode();
|
|
297
|
+
const client = setupTestNode({ connected: false });
|
|
298
|
+
client.connectToSyncServer({
|
|
299
|
+
ourName: "client",
|
|
300
|
+
syncServerName: "server",
|
|
301
|
+
syncServer: server.node,
|
|
302
|
+
});
|
|
303
|
+
// Create a CoValue on the server - the Map depends on the Group
|
|
304
|
+
const group = server.node.createGroup();
|
|
305
|
+
group.addMember("everyone", "writer");
|
|
306
|
+
const map = group.createMap();
|
|
307
|
+
map.set("key", "value");
|
|
308
|
+
// Delete the Group from server so it won't be pushed with the Map content
|
|
309
|
+
// skipVerify prevents the server from checking dependencies before sending
|
|
310
|
+
server.node.syncManager.disableTransactionVerification();
|
|
311
|
+
server.node.internalDeleteCoValue(group.id);
|
|
312
|
+
// Load the map from the client
|
|
313
|
+
// The flow is:
|
|
314
|
+
// 1. Client sends LOAD Map to server (takes the slot, limit=1)
|
|
315
|
+
// 2. Server responds with Map content (no deps pushed because skipVerify + Group deleted)
|
|
316
|
+
// 3. Client sees missing dependency (Group), sends LOAD Group to server
|
|
317
|
+
// This would be blocked by limit=1 without allowOverflow since Map load slot is taken
|
|
318
|
+
// 4. With allowOverflow, Group load bypasses the queue
|
|
319
|
+
// 5. Server responds with KNOWN Group (doesn't have it - was deleted)
|
|
320
|
+
// 6. Group content is moved back to server (simulating it becoming available)
|
|
321
|
+
// 7. Server responds with Group content
|
|
322
|
+
// 8. Client can now process Map content
|
|
323
|
+
const promise = loadCoValueOrFail(client.node, map.id);
|
|
324
|
+
// Wait for the Map content to be sent
|
|
325
|
+
await waitFor(() => SyncMessagesLog.messages.length >= 2);
|
|
326
|
+
importContentIntoNode(group.core, server.node, 1);
|
|
327
|
+
const result = await promise;
|
|
328
|
+
expect(result.get("key")).toBe("value");
|
|
329
|
+
// Verify both were loaded successfully despite throttling
|
|
330
|
+
expect(SyncMessagesLog.getMessages({
|
|
331
|
+
Group: group.core,
|
|
332
|
+
Map: map.core,
|
|
333
|
+
})).toMatchInlineSnapshot(`
|
|
334
|
+
[
|
|
335
|
+
"client -> server | LOAD Map sessions: empty",
|
|
336
|
+
"server -> client | CONTENT Map header: true new: After: 0 New: 1",
|
|
337
|
+
"client -> server | LOAD Group sessions: empty",
|
|
338
|
+
"server -> client | KNOWN Group sessions: empty",
|
|
339
|
+
"server -> client | CONTENT Group header: true new: After: 0 New: 5",
|
|
340
|
+
"client -> server | KNOWN Group sessions: header/5",
|
|
341
|
+
"client -> server | KNOWN Map sessions: header/1",
|
|
342
|
+
]
|
|
343
|
+
`);
|
|
344
|
+
});
|
|
345
|
+
test("should keep load slot occupied while streaming large CoValues", async () => {
|
|
346
|
+
setMaxInFlightLoadsPerPeer(1);
|
|
347
|
+
const client = setupTestNode({
|
|
348
|
+
connected: false,
|
|
349
|
+
});
|
|
350
|
+
const { peerState, peerOnServer } = client.connectToSyncServer();
|
|
351
|
+
// Create a large CoValue that requires multiple chunks to stream
|
|
352
|
+
const group = jazzCloud.node.createGroup();
|
|
353
|
+
const largeMap = group.createMap();
|
|
354
|
+
fillCoMapWithLargeData(largeMap);
|
|
355
|
+
// Create a small CoValue that will be queued
|
|
356
|
+
const smallMap = group.createMap();
|
|
357
|
+
smallMap.set("key", "value", "trusting");
|
|
358
|
+
// Block all the streaming chunks, except the first content message
|
|
359
|
+
const blocker = blockMessageTypeOnOutgoingPeer(peerOnServer, "content", {
|
|
360
|
+
id: largeMap.id,
|
|
361
|
+
matcher: (msg) => msg.action === "content" && !msg.expectContentUntil,
|
|
362
|
+
});
|
|
363
|
+
// Start loading both maps concurrently
|
|
364
|
+
const largeMapOnClient = await client.node.loadCoValueCore(largeMap.id);
|
|
365
|
+
const smallMapPromise = client.node.loadCoValueCore(smallMap.id);
|
|
366
|
+
expect(client.node.getCoValue(largeMap.id).isStreaming()).toBe(true);
|
|
367
|
+
await new Promise((resolve) => setTimeout(resolve, 10));
|
|
368
|
+
// The SmallMap load should still be waiting in the queue
|
|
369
|
+
expect(SyncMessagesLog.getMessages({
|
|
370
|
+
Group: group.core,
|
|
371
|
+
LargeMap: largeMapOnClient,
|
|
372
|
+
SmallMap: smallMap.core,
|
|
373
|
+
})).toMatchInlineSnapshot(`
|
|
374
|
+
[
|
|
375
|
+
"client -> server | LOAD LargeMap sessions: empty",
|
|
376
|
+
"server -> client | CONTENT Group header: true new: After: 0 New: 3",
|
|
377
|
+
"server -> client | CONTENT LargeMap header: true new: After: 0 New: 73 expectContentUntil: header/200",
|
|
378
|
+
"client -> server | KNOWN Group sessions: header/3",
|
|
379
|
+
"client -> server | KNOWN LargeMap sessions: header/73",
|
|
380
|
+
]
|
|
381
|
+
`);
|
|
382
|
+
// Now unblock and send all remaining chunks to complete streaming
|
|
383
|
+
blocker.unblock();
|
|
384
|
+
blocker.sendBlockedMessages();
|
|
385
|
+
await client.node.getCoValue(largeMap.id).waitForFullStreaming();
|
|
386
|
+
const loadedSmallMap = await smallMapPromise;
|
|
387
|
+
expect(loadedSmallMap.isAvailable()).toBe(true);
|
|
388
|
+
});
|
|
389
|
+
test("should prioritize user-initiated loads over peer reconciliation loads", async () => {
|
|
390
|
+
setMaxInFlightLoadsPerPeer(1);
|
|
391
|
+
// Create CoValues on the server before the client connects
|
|
392
|
+
const group = jazzCloud.node.createGroup();
|
|
393
|
+
const [a, b, c] = [
|
|
394
|
+
group.createMap({ test: "a" }),
|
|
395
|
+
group.createMap({ test: "b" }),
|
|
396
|
+
group.createMap({ test: "c" }),
|
|
397
|
+
];
|
|
398
|
+
const client = setupTestNode({
|
|
399
|
+
connected: false,
|
|
400
|
+
});
|
|
401
|
+
const { peerState } = client.connectToSyncServer();
|
|
402
|
+
// Load a CoValue to make it available locally
|
|
403
|
+
await loadCoValueOrFail(client.node, a.id);
|
|
404
|
+
await loadCoValueOrFail(client.node, b.id);
|
|
405
|
+
// Close the peer connection
|
|
406
|
+
peerState.gracefulShutdown();
|
|
407
|
+
SyncMessagesLog.clear();
|
|
408
|
+
// Reconnect to the server to trigger the reconciliation load
|
|
409
|
+
client.connectToSyncServer();
|
|
410
|
+
// The reconciliation load should be in the low-priority queue
|
|
411
|
+
// Now make a user-initiated load for a different CoValue
|
|
412
|
+
await loadCoValueOrFail(client.node, c.id);
|
|
413
|
+
// Wait for the reconciliation loads to be sent
|
|
414
|
+
await waitFor(() => SyncMessagesLog.messages.length >= 8);
|
|
415
|
+
// Expect Group, C, A, B
|
|
416
|
+
expect(SyncMessagesLog.getMessages({
|
|
417
|
+
Group: group.core,
|
|
418
|
+
A: a.core,
|
|
419
|
+
B: b.core,
|
|
420
|
+
C: c.core,
|
|
421
|
+
})).toMatchInlineSnapshot(`
|
|
422
|
+
[
|
|
423
|
+
"client -> server | LOAD Group sessions: header/3",
|
|
424
|
+
"server -> client | KNOWN Group sessions: header/3",
|
|
425
|
+
"client -> server | LOAD C sessions: empty",
|
|
426
|
+
"server -> client | CONTENT C header: true new: After: 0 New: 1",
|
|
427
|
+
"client -> server | KNOWN C sessions: header/1",
|
|
428
|
+
"client -> server | LOAD A sessions: header/1",
|
|
429
|
+
"server -> client | KNOWN A sessions: header/1",
|
|
430
|
+
"client -> server | LOAD B sessions: header/1",
|
|
431
|
+
"server -> client | KNOWN B sessions: header/1",
|
|
432
|
+
]
|
|
433
|
+
`);
|
|
434
|
+
});
|
|
435
|
+
test("should upgrade low-priority reconciliation load to high-priority when user requests it", async () => {
|
|
436
|
+
setMaxInFlightLoadsPerPeer(1);
|
|
437
|
+
// Create CoValues on the server before the client connects
|
|
438
|
+
const group = jazzCloud.node.createGroup();
|
|
439
|
+
const [a, b, c] = [
|
|
440
|
+
group.createMap({ test: "a" }),
|
|
441
|
+
group.createMap({ test: "b" }),
|
|
442
|
+
group.createMap({ test: "c" }),
|
|
443
|
+
];
|
|
444
|
+
const client = setupTestNode({
|
|
445
|
+
connected: false,
|
|
446
|
+
});
|
|
447
|
+
// Load both CoValues to make them marked as unavailable
|
|
448
|
+
await client.node.loadCoValueCore(a.id);
|
|
449
|
+
await client.node.loadCoValueCore(b.id);
|
|
450
|
+
await client.node.loadCoValueCore(c.id);
|
|
451
|
+
// Reconnect to the server to trigger the reconciliation load
|
|
452
|
+
client.connectToSyncServer();
|
|
453
|
+
// The reconciliation load should be in the low-priority queue
|
|
454
|
+
// Now try to bump-up the priority of the load for c
|
|
455
|
+
client.node.loadCoValueCore(c.id);
|
|
456
|
+
// Wait for the reconciliation loads to be sent
|
|
457
|
+
await waitFor(() => SyncMessagesLog.messages.length >= 6);
|
|
458
|
+
// Expect A, C, B
|
|
459
|
+
expect(SyncMessagesLog.getMessages({
|
|
460
|
+
Group: group.core,
|
|
461
|
+
A: a.core,
|
|
462
|
+
B: b.core,
|
|
463
|
+
C: c.core,
|
|
464
|
+
})).toMatchInlineSnapshot(`
|
|
465
|
+
[
|
|
466
|
+
"client -> server | LOAD A sessions: empty",
|
|
467
|
+
"server -> client | CONTENT Group header: true new: After: 0 New: 3",
|
|
468
|
+
"server -> client | CONTENT A header: true new: After: 0 New: 1",
|
|
469
|
+
"client -> server | KNOWN Group sessions: header/3",
|
|
470
|
+
"client -> server | KNOWN A sessions: header/1",
|
|
471
|
+
"client -> server | LOAD C sessions: empty",
|
|
472
|
+
"server -> client | CONTENT C header: true new: After: 0 New: 1",
|
|
473
|
+
"client -> server | KNOWN C sessions: header/1",
|
|
474
|
+
"client -> server | LOAD B sessions: empty",
|
|
475
|
+
"server -> client | CONTENT B header: true new: After: 0 New: 1",
|
|
476
|
+
"client -> server | KNOWN B sessions: header/1",
|
|
477
|
+
]
|
|
478
|
+
`);
|
|
479
|
+
});
|
|
480
|
+
});
|
|
481
|
+
//# sourceMappingURL=sync.concurrentLoad.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sync.concurrentLoad.test.js","sourceRoot":"","sources":["../../src/tests/sync.concurrentLoad.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sync.deleted.test.d.ts","sourceRoot":"","sources":["../../src/tests/sync.deleted.test.ts"],"names":[],"mappings":""}
|