@aztec/world-state 0.7.10 → 0.8.6

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.
Files changed (45) hide show
  1. package/README.md +3 -3
  2. package/dest/index.d.ts +2 -2
  3. package/dest/index.js +2 -2
  4. package/dest/merkle-tree/merkle_tree_operations_facade.d.ts +3 -3
  5. package/dest/merkle-tree/merkle_tree_operations_facade.d.ts.map +1 -1
  6. package/dest/merkle-tree/merkle_tree_operations_facade.js +2 -2
  7. package/dest/{synchroniser → synchronizer}/config.d.ts +3 -3
  8. package/dest/{synchroniser → synchronizer}/config.d.ts.map +1 -1
  9. package/dest/{synchroniser → synchronizer}/config.js +3 -3
  10. package/dest/synchronizer/index.d.ts +3 -0
  11. package/dest/synchronizer/index.d.ts.map +1 -0
  12. package/dest/{synchroniser → synchronizer}/index.js +3 -3
  13. package/dest/{synchroniser/server_world_state_synchroniser.d.ts → synchronizer/server_world_state_synchronizer.d.ts} +13 -6
  14. package/dest/synchronizer/server_world_state_synchronizer.d.ts.map +1 -0
  15. package/dest/synchronizer/server_world_state_synchronizer.js +203 -0
  16. package/dest/{synchroniser/world_state_synchroniser.d.ts → synchronizer/world_state_synchronizer.d.ts} +11 -11
  17. package/dest/{synchroniser/world_state_synchroniser.d.ts.map → synchronizer/world_state_synchronizer.d.ts.map} +1 -1
  18. package/dest/{synchroniser/world_state_synchroniser.js → synchronizer/world_state_synchronizer.js} +2 -2
  19. package/dest/world-state-db/index.d.ts +5 -1
  20. package/dest/world-state-db/index.d.ts.map +1 -1
  21. package/dest/world-state-db/index.js +1 -1
  22. package/dest/world-state-db/merkle_trees.d.ts +9 -8
  23. package/dest/world-state-db/merkle_trees.d.ts.map +1 -1
  24. package/dest/world-state-db/merkle_trees.js +55 -44
  25. package/package.json +56 -6
  26. package/src/index.ts +2 -2
  27. package/src/merkle-tree/merkle_tree_operations_facade.ts +10 -3
  28. package/src/{synchroniser → synchronizer}/config.ts +3 -3
  29. package/src/synchronizer/index.ts +2 -0
  30. package/src/{synchroniser/server_world_state_synchroniser.ts → synchronizer/server_world_state_synchronizer.ts} +60 -10
  31. package/src/{synchroniser/world_state_synchroniser.ts → synchronizer/world_state_synchronizer.ts} +10 -10
  32. package/src/world-state-db/index.ts +6 -1
  33. package/src/world-state-db/merkle_trees.ts +61 -46
  34. package/.eslintrc.cjs +0 -1
  35. package/.tsbuildinfo +0 -1
  36. package/dest/synchroniser/index.d.ts +0 -3
  37. package/dest/synchroniser/index.d.ts.map +0 -1
  38. package/dest/synchroniser/server_world_state_synchroniser.d.ts.map +0 -1
  39. package/dest/synchroniser/server_world_state_synchroniser.js +0 -163
  40. package/dest/synchroniser/server_world_state_synchroniser.test.d.ts +0 -2
  41. package/dest/synchroniser/server_world_state_synchroniser.test.d.ts.map +0 -1
  42. package/dest/synchroniser/server_world_state_synchroniser.test.js +0 -317
  43. package/src/synchroniser/index.ts +0 -2
  44. package/src/synchroniser/server_world_state_synchroniser.test.ts +0 -428
  45. package/tsconfig.json +0 -23
@@ -1,428 +0,0 @@
1
- import {
2
- AppendOnlyTreeSnapshot,
3
- CircuitsWasm,
4
- Fr,
5
- GlobalVariables,
6
- MAX_NEW_COMMITMENTS_PER_TX,
7
- MAX_NEW_CONTRACTS_PER_TX,
8
- MAX_NEW_L2_TO_L1_MSGS_PER_CALL,
9
- MAX_NEW_NULLIFIERS_PER_TX,
10
- MAX_PUBLIC_DATA_UPDATE_REQUESTS_PER_TX,
11
- NUMBER_OF_L1_L2_MESSAGES_PER_ROLLUP,
12
- } from '@aztec/circuits.js';
13
- import { createDebugLogger } from '@aztec/foundation/log';
14
- import { sleep } from '@aztec/foundation/sleep';
15
- import { INITIAL_LEAF, Pedersen } from '@aztec/merkle-tree';
16
- import {
17
- ContractData,
18
- L2Block,
19
- L2BlockL2Logs,
20
- L2BlockSource,
21
- MerkleTreeId,
22
- PublicDataWrite,
23
- SiblingPath,
24
- } from '@aztec/types';
25
-
26
- import { jest } from '@jest/globals';
27
- import times from 'lodash.times';
28
-
29
- import { MerkleTreeDb, MerkleTrees, WorldStateConfig } from '../index.js';
30
- import { ServerWorldStateSynchroniser } from './server_world_state_synchroniser.js';
31
- import { WorldStateRunningState } from './world_state_synchroniser.js';
32
-
33
- /**
34
- * Generic mock implementation.
35
- */
36
- type Mockify<T> = {
37
- [P in keyof T]: jest.Mock;
38
- };
39
-
40
- const LATEST_BLOCK_NUMBER = 5;
41
- const getLatestBlockNumber = () => LATEST_BLOCK_NUMBER;
42
- let nextBlocks: L2Block[] = [];
43
- const consumeNextBlocks = () => {
44
- const blocks = nextBlocks;
45
- nextBlocks = [];
46
- return Promise.resolve(blocks);
47
- };
48
-
49
- const getMockTreeSnapshot = () => {
50
- return new AppendOnlyTreeSnapshot(Fr.random(), 16);
51
- };
52
-
53
- const getMockContractData = () => {
54
- return ContractData.random();
55
- };
56
-
57
- const getMockGlobalVariables = () => {
58
- return GlobalVariables.from({
59
- chainId: Fr.random(),
60
- version: Fr.random(),
61
- blockNumber: Fr.random(),
62
- timestamp: Fr.random(),
63
- });
64
- };
65
-
66
- const getMockL1ToL2MessagesData = () => {
67
- return new Array(NUMBER_OF_L1_L2_MESSAGES_PER_ROLLUP).map(() => Fr.random());
68
- };
69
-
70
- const getMockBlock = (blockNumber: number, newContractsCommitments?: Buffer[]) => {
71
- const newEncryptedLogs = L2BlockL2Logs.random(1, 2, 3);
72
- const block = L2Block.fromFields({
73
- number: blockNumber,
74
- globalVariables: getMockGlobalVariables(),
75
- startPrivateDataTreeSnapshot: getMockTreeSnapshot(),
76
- startNullifierTreeSnapshot: getMockTreeSnapshot(),
77
- startContractTreeSnapshot: getMockTreeSnapshot(),
78
- startPublicDataTreeRoot: Fr.random(),
79
- startL1ToL2MessagesTreeSnapshot: getMockTreeSnapshot(),
80
- startHistoricBlocksTreeSnapshot: getMockTreeSnapshot(),
81
- endPrivateDataTreeSnapshot: getMockTreeSnapshot(),
82
- endNullifierTreeSnapshot: getMockTreeSnapshot(),
83
- endContractTreeSnapshot: getMockTreeSnapshot(),
84
- endPublicDataTreeRoot: Fr.random(),
85
- endL1ToL2MessagesTreeSnapshot: getMockTreeSnapshot(),
86
- endHistoricBlocksTreeSnapshot: getMockTreeSnapshot(),
87
- newCommitments: times(MAX_NEW_COMMITMENTS_PER_TX, Fr.random),
88
- newNullifiers: times(MAX_NEW_NULLIFIERS_PER_TX, Fr.random),
89
- newContracts: newContractsCommitments?.map(x => Fr.fromBuffer(x)) ?? [Fr.random()],
90
- newContractData: times(MAX_NEW_CONTRACTS_PER_TX, getMockContractData),
91
- newPublicDataWrites: times(MAX_PUBLIC_DATA_UPDATE_REQUESTS_PER_TX, PublicDataWrite.random),
92
- newL1ToL2Messages: getMockL1ToL2MessagesData(),
93
- newL2ToL1Msgs: times(MAX_NEW_L2_TO_L1_MSGS_PER_CALL, Fr.random),
94
- newEncryptedLogs,
95
- });
96
- return block;
97
- };
98
-
99
- const createSynchroniser = (merkleTreeDb: any, rollupSource: any, blockCheckInterval = 100) => {
100
- const worldStateConfig: WorldStateConfig = {
101
- worldStateBlockCheckIntervalMS: blockCheckInterval,
102
- l2QueueSize: 1000,
103
- };
104
- return new ServerWorldStateSynchroniser(merkleTreeDb as MerkleTrees, rollupSource as L2BlockSource, worldStateConfig);
105
- };
106
-
107
- const log = createDebugLogger('aztec:server_world_state_synchroniser_test');
108
-
109
- describe('server_world_state_synchroniser', () => {
110
- const rollupSource: Mockify<Pick<L2BlockSource, 'getBlockNumber' | 'getL2Blocks'>> = {
111
- getBlockNumber: jest.fn().mockImplementation(getLatestBlockNumber),
112
- getL2Blocks: jest.fn().mockImplementation(consumeNextBlocks),
113
- };
114
-
115
- const merkleTreeDb: Mockify<MerkleTreeDb> = {
116
- getTreeInfo: jest
117
- .fn()
118
- .mockImplementation(() =>
119
- Promise.resolve({ treeId: MerkleTreeId.CONTRACT_TREE, root: Buffer.alloc(32, 0), size: 0n }),
120
- ),
121
- appendLeaves: jest.fn().mockImplementation(() => Promise.resolve()),
122
- updateLeaf: jest.fn().mockImplementation(() => Promise.resolve()),
123
- getSiblingPath: jest.fn().mockImplementation(() => {
124
- return async () => {
125
- const wasm = await CircuitsWasm.get();
126
- const pedersen: Pedersen = new Pedersen(wasm);
127
- SiblingPath.ZERO(32, INITIAL_LEAF, pedersen);
128
- }; //Promise.resolve();
129
- }),
130
- updateHistoricBlocksTree: jest.fn().mockImplementation(() => Promise.resolve()),
131
- commit: jest.fn().mockImplementation(() => Promise.resolve()),
132
- rollback: jest.fn().mockImplementation(() => Promise.resolve()),
133
- handleL2Block: jest.fn().mockImplementation(() => Promise.resolve()),
134
- stop: jest.fn().mockImplementation(() => Promise.resolve()),
135
- } as any;
136
-
137
- const performInitialSync = async (server: ServerWorldStateSynchroniser) => {
138
- // test initial state
139
- let status = await server.status();
140
- expect(status.syncedToL2Block).toEqual(0);
141
- expect(status.state).toEqual(WorldStateRunningState.IDLE);
142
-
143
- // create the initial blocks
144
- nextBlocks = Array(LATEST_BLOCK_NUMBER)
145
- .fill(0)
146
- .map((_, index: number) => getMockBlock(index + 1));
147
-
148
- // start the sync process and await it
149
- await server.start().catch(err => log.error('Sync not completed: ', err));
150
-
151
- status = await server.status();
152
- expect(status.syncedToL2Block).toBe(LATEST_BLOCK_NUMBER);
153
- };
154
-
155
- it('can be constructed', () => {
156
- expect(() => createSynchroniser(merkleTreeDb, rollupSource)).not.toThrow();
157
- });
158
-
159
- it('updates sync progress', async () => {
160
- const server = createSynchroniser(merkleTreeDb, rollupSource);
161
-
162
- // test initial state
163
- let status = await server.status();
164
- expect(status.syncedToL2Block).toEqual(0);
165
- expect(status.state).toEqual(WorldStateRunningState.IDLE);
166
-
167
- // create an initial block
168
- let currentBlockNumber = 0;
169
- nextBlocks = [getMockBlock(currentBlockNumber + 1)];
170
-
171
- // start the sync process but don't await
172
- server.start().catch(err => log.error('Sync not completed: ', err));
173
-
174
- // now setup a loop to monitor the sync progress and push new blocks in
175
- while (currentBlockNumber <= LATEST_BLOCK_NUMBER) {
176
- status = await server.status();
177
- expect(
178
- status.syncedToL2Block >= currentBlockNumber || status.syncedToL2Block <= currentBlockNumber + 1,
179
- ).toBeTruthy();
180
- if (status.syncedToL2Block === LATEST_BLOCK_NUMBER) {
181
- break;
182
- }
183
- expect(
184
- status.state >= WorldStateRunningState.IDLE || status.state <= WorldStateRunningState.SYNCHING,
185
- ).toBeTruthy();
186
- if (status.syncedToL2Block === currentBlockNumber) {
187
- await sleep(100);
188
- continue;
189
- }
190
- currentBlockNumber++;
191
- nextBlocks = [getMockBlock(currentBlockNumber + 1)];
192
- }
193
-
194
- // check the status agian, should be fully synced
195
- status = await server.status();
196
- expect(status.state).toEqual(WorldStateRunningState.RUNNING);
197
- expect(status.syncedToL2Block).toEqual(LATEST_BLOCK_NUMBER);
198
-
199
- // stop the synchroniser
200
- await server.stop();
201
-
202
- // check the final status
203
- status = await server.status();
204
- expect(status.state).toEqual(WorldStateRunningState.STOPPED);
205
- expect(status.syncedToL2Block).toEqual(LATEST_BLOCK_NUMBER);
206
- });
207
-
208
- it('enables blocking until synced', async () => {
209
- const server = createSynchroniser(merkleTreeDb, rollupSource);
210
- let currentBlockNumber = 0;
211
-
212
- const newBlocks = async () => {
213
- while (currentBlockNumber <= LATEST_BLOCK_NUMBER) {
214
- await sleep(100);
215
- nextBlocks = [...nextBlocks, getMockBlock(++currentBlockNumber)];
216
- }
217
- };
218
-
219
- // kick off the background queueing of blocks
220
- const newBlockPromise = newBlocks();
221
-
222
- // kick off the synching
223
- const syncPromise = server.start();
224
-
225
- // await the synching
226
- await syncPromise;
227
-
228
- await newBlockPromise;
229
-
230
- let status = await server.status();
231
- expect(status.state).toEqual(WorldStateRunningState.RUNNING);
232
- expect(status.syncedToL2Block).toEqual(LATEST_BLOCK_NUMBER);
233
- await server.stop();
234
- status = await server.status();
235
- expect(status.state).toEqual(WorldStateRunningState.STOPPED);
236
- expect(status.syncedToL2Block).toEqual(LATEST_BLOCK_NUMBER);
237
- });
238
-
239
- it('handles multiple calls to start', async () => {
240
- const server = createSynchroniser(merkleTreeDb, rollupSource);
241
- let currentBlockNumber = 0;
242
-
243
- const newBlocks = async () => {
244
- while (currentBlockNumber < LATEST_BLOCK_NUMBER) {
245
- await sleep(100);
246
- const newBlock = getMockBlock(++currentBlockNumber);
247
- nextBlocks = [...nextBlocks, newBlock];
248
- }
249
- };
250
-
251
- // kick off the background queueing of blocks
252
- const newBlockPromise = newBlocks();
253
-
254
- // kick off the synching
255
- await server.start();
256
-
257
- // call start again, should get back the same promise
258
- await server.start();
259
-
260
- // wait until the block production has finished
261
- await newBlockPromise;
262
-
263
- await server.stop();
264
- });
265
-
266
- it('immediately syncs if no new blocks', async () => {
267
- const server = createSynchroniser(merkleTreeDb, rollupSource);
268
- rollupSource.getBlockNumber.mockImplementationOnce(() => {
269
- return Promise.resolve(0);
270
- });
271
-
272
- // kick off the synching
273
- const syncPromise = server.start();
274
-
275
- // it should already be synced, no need to push new blocks
276
- await syncPromise;
277
-
278
- const status = await server.status();
279
- expect(status.state).toBe(WorldStateRunningState.RUNNING);
280
- expect(status.syncedToL2Block).toBe(0);
281
- await server.stop();
282
- });
283
-
284
- it("can't be started if already stopped", async () => {
285
- const server = createSynchroniser(merkleTreeDb, rollupSource);
286
- rollupSource.getBlockNumber.mockImplementationOnce(() => {
287
- return Promise.resolve(0);
288
- });
289
-
290
- // kick off the synching
291
- const syncPromise = server.start();
292
- await syncPromise;
293
- await server.stop();
294
-
295
- await expect(server.start()).rejects.toThrow();
296
- });
297
-
298
- it('adds the received L2 blocks', async () => {
299
- merkleTreeDb.handleL2Block.mockReset();
300
- const server = createSynchroniser(merkleTreeDb, rollupSource);
301
- const totalBlocks = LATEST_BLOCK_NUMBER + 1;
302
- nextBlocks = Array(totalBlocks)
303
- .fill(0)
304
- .map((_, index) => getMockBlock(index, [Buffer.alloc(32, index)]));
305
- // sync the server
306
- await server.start();
307
-
308
- expect(merkleTreeDb.handleL2Block).toHaveBeenCalledTimes(totalBlocks);
309
- await server.stop();
310
- });
311
-
312
- it('can immediately sync to latest', async () => {
313
- const server = createSynchroniser(merkleTreeDb, rollupSource, 10000);
314
-
315
- await performInitialSync(server);
316
-
317
- // the server should now be asleep for a long time
318
- // we will add a new block and force an immediate sync
319
- nextBlocks = [getMockBlock(LATEST_BLOCK_NUMBER + 1)];
320
- await server.syncImmediate();
321
-
322
- let status = await server.status();
323
- expect(status.syncedToL2Block).toBe(LATEST_BLOCK_NUMBER + 1);
324
-
325
- nextBlocks = [getMockBlock(LATEST_BLOCK_NUMBER + 2), getMockBlock(LATEST_BLOCK_NUMBER + 3)];
326
- await server.syncImmediate();
327
-
328
- status = await server.status();
329
- expect(status.syncedToL2Block).toBe(LATEST_BLOCK_NUMBER + 3);
330
-
331
- // stop the synchroniser
332
- await server.stop();
333
-
334
- // check the final status
335
- status = await server.status();
336
- expect(status.state).toEqual(WorldStateRunningState.STOPPED);
337
- expect(status.syncedToL2Block).toEqual(LATEST_BLOCK_NUMBER + 3);
338
- });
339
-
340
- it('can immediately sync to a minimum block number', async () => {
341
- const server = createSynchroniser(merkleTreeDb, rollupSource, 10000);
342
-
343
- await performInitialSync(server);
344
-
345
- // the server should now be asleep for a long time
346
- // we will add 20 blocks and force a sync to at least LATEST + 5
347
- nextBlocks = Array(20)
348
- .fill(0)
349
- .map((_, index: number) => getMockBlock(index + 1 + LATEST_BLOCK_NUMBER));
350
- await server.syncImmediate(LATEST_BLOCK_NUMBER + 5);
351
-
352
- // we should have synced all of the blocks
353
- let status = await server.status();
354
- expect(status.syncedToL2Block).toBe(LATEST_BLOCK_NUMBER + 20);
355
-
356
- // stop the synchroniser
357
- await server.stop();
358
-
359
- // check the final status
360
- status = await server.status();
361
- expect(status.state).toEqual(WorldStateRunningState.STOPPED);
362
- expect(status.syncedToL2Block).toEqual(LATEST_BLOCK_NUMBER + 20);
363
- });
364
-
365
- it('can immediately sync to a minimum block in the past', async () => {
366
- const server = createSynchroniser(merkleTreeDb, rollupSource, 10000);
367
-
368
- await performInitialSync(server);
369
- // syncing to a block in the past should succeed
370
- await server.syncImmediate(LATEST_BLOCK_NUMBER - 1);
371
- // syncing to the current block should succeed
372
- await server.syncImmediate(LATEST_BLOCK_NUMBER);
373
-
374
- // we should have synced all of the blocks
375
- let status = await server.status();
376
- expect(status.syncedToL2Block).toBe(LATEST_BLOCK_NUMBER);
377
-
378
- // stop the synchroniser
379
- await server.stop();
380
-
381
- // check the final status
382
- status = await server.status();
383
- expect(status.state).toEqual(WorldStateRunningState.STOPPED);
384
- expect(status.syncedToL2Block).toEqual(LATEST_BLOCK_NUMBER);
385
- });
386
-
387
- it('throws if you try to sync to an unavailable block', async () => {
388
- const server = createSynchroniser(merkleTreeDb, rollupSource, 10000);
389
-
390
- await performInitialSync(server);
391
-
392
- // the server should now be asleep for a long time
393
- // we will add 2 blocks and force a sync to at least LATEST + 5
394
- nextBlocks = Array(2)
395
- .fill(0)
396
- .map((_, index: number) => getMockBlock(index + 1 + LATEST_BLOCK_NUMBER));
397
- await expect(server.syncImmediate(LATEST_BLOCK_NUMBER + 5)).rejects.toThrow(
398
- `Unable to sync to block number ${LATEST_BLOCK_NUMBER + 5}, currently synced to block ${LATEST_BLOCK_NUMBER + 2}`,
399
- );
400
-
401
- let status = await server.status();
402
- expect(status.syncedToL2Block).toBe(LATEST_BLOCK_NUMBER + 2);
403
-
404
- // stop the synchroniser
405
- await server.stop();
406
-
407
- // check the final status
408
- status = await server.status();
409
- expect(status.state).toEqual(WorldStateRunningState.STOPPED);
410
- expect(status.syncedToL2Block).toEqual(LATEST_BLOCK_NUMBER + 2);
411
- });
412
-
413
- it('throws if you try to immediate sync when not running', async () => {
414
- const server = createSynchroniser(merkleTreeDb, rollupSource, 10000);
415
-
416
- // test initial state
417
- const status = await server.status();
418
- expect(status.syncedToL2Block).toEqual(0);
419
- expect(status.state).toEqual(WorldStateRunningState.IDLE);
420
-
421
- // create an initial block
422
- nextBlocks = Array(LATEST_BLOCK_NUMBER)
423
- .fill(0)
424
- .map((_, index: number) => getMockBlock(index + 1));
425
-
426
- await expect(server.syncImmediate()).rejects.toThrow(`World State is not running, unable to perform sync`);
427
- });
428
- });
package/tsconfig.json DELETED
@@ -1,23 +0,0 @@
1
- {
2
- "extends": "..",
3
- "compilerOptions": {
4
- "outDir": "dest",
5
- "rootDir": "src",
6
- "tsBuildInfoFile": ".tsbuildinfo"
7
- },
8
- "references": [
9
- {
10
- "path": "../circuits.js"
11
- },
12
- {
13
- "path": "../foundation"
14
- },
15
- {
16
- "path": "../merkle-tree"
17
- },
18
- {
19
- "path": "../types"
20
- }
21
- ],
22
- "include": ["src"]
23
- }