@aztec/end-to-end 0.0.1-commit.934299a21 → 0.0.1-commit.949a33fd8
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 +27 -0
- package/dest/bench/client_flows/client_flows_benchmark.d.ts +1 -1
- package/dest/bench/client_flows/client_flows_benchmark.d.ts.map +1 -1
- package/dest/bench/client_flows/client_flows_benchmark.js +21 -28
- package/dest/bench/utils.d.ts +1 -1
- package/dest/bench/utils.d.ts.map +1 -1
- package/dest/bench/utils.js +6 -3
- package/dest/e2e_blacklist_token_contract/blacklist_token_contract_test.d.ts +3 -2
- package/dest/e2e_blacklist_token_contract/blacklist_token_contract_test.d.ts.map +1 -1
- package/dest/e2e_blacklist_token_contract/blacklist_token_contract_test.js +15 -15
- package/dest/e2e_cross_chain_messaging/cross_chain_messaging_test.js +1 -1
- package/dest/e2e_epochs/epochs_test.d.ts +18 -1
- package/dest/e2e_epochs/epochs_test.d.ts.map +1 -1
- package/dest/e2e_epochs/epochs_test.js +61 -10
- package/dest/e2e_fees/fees_test.d.ts +1 -1
- package/dest/e2e_fees/fees_test.d.ts.map +1 -1
- package/dest/e2e_fees/fees_test.js +16 -9
- package/dest/e2e_nested_contract/nested_contract_test.d.ts +1 -1
- package/dest/e2e_nested_contract/nested_contract_test.d.ts.map +1 -1
- package/dest/e2e_nested_contract/nested_contract_test.js +4 -6
- package/dest/e2e_p2p/inactivity_slash_test.js +3 -3
- package/dest/e2e_p2p/p2p_network.d.ts +13 -11
- package/dest/e2e_p2p/p2p_network.d.ts.map +1 -1
- package/dest/e2e_p2p/p2p_network.js +65 -43
- package/dest/e2e_p2p/reqresp/utils.d.ts +1 -1
- package/dest/e2e_p2p/reqresp/utils.d.ts.map +1 -1
- package/dest/e2e_p2p/reqresp/utils.js +23 -7
- package/dest/e2e_p2p/shared.d.ts +25 -7
- package/dest/e2e_p2p/shared.d.ts.map +1 -1
- package/dest/e2e_p2p/shared.js +69 -49
- package/dest/e2e_token_contract/token_contract_test.d.ts +1 -1
- package/dest/e2e_token_contract/token_contract_test.d.ts.map +1 -1
- package/dest/e2e_token_contract/token_contract_test.js +11 -11
- package/dest/fixtures/authwit_proxy.d.ts +3 -3
- package/dest/fixtures/authwit_proxy.d.ts.map +1 -1
- package/dest/fixtures/authwit_proxy.js +4 -0
- package/dest/fixtures/e2e_prover_test.d.ts +4 -3
- package/dest/fixtures/e2e_prover_test.d.ts.map +1 -1
- package/dest/fixtures/e2e_prover_test.js +11 -16
- package/dest/fixtures/fixtures.d.ts +12 -1
- package/dest/fixtures/fixtures.d.ts.map +1 -1
- package/dest/fixtures/fixtures.js +10 -0
- package/dest/fixtures/get_bb_config.d.ts +1 -1
- package/dest/fixtures/get_bb_config.d.ts.map +1 -1
- package/dest/fixtures/get_bb_config.js +5 -5
- package/dest/fixtures/ha_setup.d.ts +2 -2
- package/dest/fixtures/ha_setup.d.ts.map +1 -1
- package/dest/fixtures/ha_setup.js +1 -1
- package/dest/fixtures/schnorr_hardcoded_account_contract.d.ts +25 -0
- package/dest/fixtures/schnorr_hardcoded_account_contract.d.ts.map +1 -0
- package/dest/fixtures/schnorr_hardcoded_account_contract.js +39 -0
- package/dest/fixtures/setup.d.ts +24 -13
- package/dest/fixtures/setup.d.ts.map +1 -1
- package/dest/fixtures/setup.js +45 -25
- package/dest/fixtures/setup_p2p_test.d.ts +6 -6
- package/dest/fixtures/setup_p2p_test.d.ts.map +1 -1
- package/dest/fixtures/setup_p2p_test.js +8 -8
- package/dest/fixtures/token_utils.d.ts +1 -1
- package/dest/fixtures/token_utils.d.ts.map +1 -1
- package/dest/fixtures/token_utils.js +2 -5
- package/dest/forward-compatibility/wallet_rpc_client.d.ts +7 -0
- package/dest/forward-compatibility/wallet_rpc_client.d.ts.map +1 -0
- package/dest/forward-compatibility/wallet_rpc_client.js +15 -0
- package/dest/forward-compatibility/wallet_service.d.ts +3 -0
- package/dest/forward-compatibility/wallet_service.d.ts.map +1 -0
- package/dest/forward-compatibility/wallet_service.js +109 -0
- package/dest/legacy-jest-resolver.d.cts +3 -0
- package/dest/legacy-jest-resolver.d.cts.map +1 -0
- package/dest/shared/cross_chain_test_harness.d.ts +1 -1
- package/dest/shared/cross_chain_test_harness.d.ts.map +1 -1
- package/dest/shared/cross_chain_test_harness.js +13 -13
- package/dest/shared/gas_portal_test_harness.js +3 -3
- package/dest/shared/jest_setup.js +32 -1
- package/dest/shared/submit-transactions.d.ts +1 -1
- package/dest/shared/submit-transactions.d.ts.map +1 -1
- package/dest/shared/submit-transactions.js +1 -1
- package/dest/shared/uniswap_l1_l2.d.ts +1 -1
- package/dest/shared/uniswap_l1_l2.d.ts.map +1 -1
- package/dest/shared/uniswap_l1_l2.js +14 -21
- package/dest/simulators/lending_simulator.d.ts +1 -1
- package/dest/simulators/lending_simulator.d.ts.map +1 -1
- package/dest/simulators/lending_simulator.js +4 -4
- package/dest/simulators/token_simulator.d.ts +1 -1
- package/dest/simulators/token_simulator.d.ts.map +1 -1
- package/dest/simulators/token_simulator.js +2 -2
- package/dest/spartan/setup_test_wallets.d.ts +4 -2
- package/dest/spartan/setup_test_wallets.d.ts.map +1 -1
- package/dest/spartan/setup_test_wallets.js +69 -38
- package/dest/spartan/tx_metrics.d.ts +1 -1
- package/dest/spartan/tx_metrics.d.ts.map +1 -1
- package/dest/spartan/tx_metrics.js +19 -3
- package/dest/spartan/utils/config.d.ts +7 -1
- package/dest/spartan/utils/config.d.ts.map +1 -1
- package/dest/spartan/utils/config.js +3 -1
- package/dest/spartan/utils/index.d.ts +3 -1
- package/dest/spartan/utils/index.d.ts.map +1 -1
- package/dest/spartan/utils/index.js +4 -0
- package/dest/spartan/utils/nodes.js +1 -1
- package/dest/spartan/utils/pod_logs.d.ts +25 -0
- package/dest/spartan/utils/pod_logs.d.ts.map +1 -0
- package/dest/spartan/utils/pod_logs.js +74 -0
- package/dest/test-wallet/test_wallet.d.ts +24 -23
- package/dest/test-wallet/test_wallet.d.ts.map +1 -1
- package/dest/test-wallet/test_wallet.js +124 -83
- package/dest/test-wallet/worker_wallet.d.ts +4 -4
- package/dest/test-wallet/worker_wallet.d.ts.map +1 -1
- package/dest/test-wallet/worker_wallet_schema.d.ts +10 -5
- package/dest/test-wallet/worker_wallet_schema.d.ts.map +1 -1
- package/package.json +43 -44
- package/src/bench/client_flows/client_flows_benchmark.ts +29 -12
- package/src/bench/utils.ts +7 -2
- package/src/e2e_blacklist_token_contract/blacklist_token_contract_test.ts +21 -20
- package/src/e2e_cross_chain_messaging/cross_chain_messaging_test.ts +1 -1
- package/src/e2e_epochs/epochs_test.ts +70 -9
- package/src/e2e_fees/fees_test.ts +17 -8
- package/src/e2e_nested_contract/nested_contract_test.ts +6 -4
- package/src/e2e_p2p/inactivity_slash_test.ts +3 -3
- package/src/e2e_p2p/p2p_network.ts +82 -60
- package/src/e2e_p2p/reqresp/utils.ts +29 -7
- package/src/e2e_p2p/shared.ts +88 -63
- package/src/e2e_token_contract/token_contract_test.ts +16 -8
- package/src/fixtures/authwit_proxy.ts +4 -0
- package/src/fixtures/e2e_prover_test.ts +19 -18
- package/src/fixtures/fixtures.ts +22 -0
- package/src/fixtures/get_bb_config.ts +7 -6
- package/src/fixtures/ha_setup.ts +4 -2
- package/src/fixtures/schnorr_hardcoded_account_contract.ts +49 -0
- package/src/fixtures/setup.ts +69 -33
- package/src/fixtures/setup_p2p_test.ts +9 -9
- package/src/fixtures/token_utils.ts +1 -2
- package/src/forward-compatibility/wallet_rpc_client.ts +14 -0
- package/src/forward-compatibility/wallet_service.ts +104 -0
- package/src/guides/up_quick_start.sh +0 -2
- package/src/legacy-jest-resolver.cjs +135 -0
- package/src/shared/cross_chain_test_harness.ts +13 -9
- package/src/shared/gas_portal_test_harness.ts +1 -2
- package/src/shared/jest_setup.ts +36 -1
- package/src/shared/submit-transactions.ts +1 -4
- package/src/shared/uniswap_l1_l2.ts +35 -32
- package/src/simulators/lending_simulator.ts +8 -4
- package/src/simulators/token_simulator.ts +6 -2
- package/src/spartan/setup_test_wallets.ts +90 -35
- package/src/spartan/tx_metrics.ts +17 -5
- package/src/spartan/utils/config.ts +2 -0
- package/src/spartan/utils/index.ts +6 -0
- package/src/spartan/utils/nodes.ts +1 -1
- package/src/spartan/utils/pod_logs.ts +99 -0
- package/src/test-wallet/test_wallet.ts +152 -101
- package/src/test-wallet/worker_wallet.ts +3 -2
|
@@ -1,5 +1,7 @@
|
|
|
1
|
+
import type { InitialAccountData } from '@aztec/accounts/testing';
|
|
1
2
|
import type { Archiver } from '@aztec/archiver';
|
|
2
3
|
import { type AztecNodeConfig, AztecNodeService } from '@aztec/aztec-node';
|
|
4
|
+
import { getAccountContractAddress } from '@aztec/aztec.js/account';
|
|
3
5
|
import { getTimestampRangeForEpoch } from '@aztec/aztec.js/block';
|
|
4
6
|
import { getContractInstanceFromInstantiationParams } from '@aztec/aztec.js/contracts';
|
|
5
7
|
import { Fr } from '@aztec/aztec.js/fields';
|
|
@@ -28,11 +30,16 @@ import { type SequencerClient, type SequencerEvents, SequencerState } from '@azt
|
|
|
28
30
|
import { type BlockParameter, EthAddress } from '@aztec/stdlib/block';
|
|
29
31
|
import { type L1RollupConstants, getProofSubmissionDeadlineTimestamp } from '@aztec/stdlib/epoch-helpers';
|
|
30
32
|
import { tryStop } from '@aztec/stdlib/interfaces/server';
|
|
33
|
+
import type { SlashingProtectionDatabase } from '@aztec/validator-ha-signer/types';
|
|
31
34
|
|
|
32
35
|
import { join } from 'path';
|
|
33
36
|
import type { Hex } from 'viem';
|
|
34
37
|
import { privateKeyToAccount } from 'viem/accounts';
|
|
35
38
|
|
|
39
|
+
import {
|
|
40
|
+
SCHNORR_HARDCODED_PRIVATE_KEY,
|
|
41
|
+
SchnorrHardcodedKeyAccountContract,
|
|
42
|
+
} from '../fixtures/schnorr_hardcoded_account_contract.js';
|
|
36
43
|
import {
|
|
37
44
|
type EndToEndContext,
|
|
38
45
|
type SetupOptions,
|
|
@@ -40,6 +47,7 @@ import {
|
|
|
40
47
|
getPrivateKeyFromIndex,
|
|
41
48
|
setup,
|
|
42
49
|
} from '../fixtures/utils.js';
|
|
50
|
+
import type { TestWallet } from '../test-wallet/test_wallet.js';
|
|
43
51
|
|
|
44
52
|
export const WORLD_STATE_CHECKPOINT_HISTORY = 2;
|
|
45
53
|
export const WORLD_STATE_BLOCK_CHECK_INTERVAL = 50;
|
|
@@ -50,6 +58,8 @@ export type EpochsTestOpts = Partial<SetupOptions> & {
|
|
|
50
58
|
numberOfAccounts?: number;
|
|
51
59
|
pxeOpts?: Partial<PXEConfig>;
|
|
52
60
|
aztecSlotDurationInL1Slots?: number;
|
|
61
|
+
/** Skip creating/registering the hardcoded account during setup (for tests that handle accounts themselves). */
|
|
62
|
+
skipHardcodedAccount?: boolean;
|
|
53
63
|
};
|
|
54
64
|
|
|
55
65
|
export type TrackedSequencerEvent = {
|
|
@@ -120,10 +130,18 @@ export class EpochsTestContext {
|
|
|
120
130
|
this.L1_BLOCK_TIME_IN_S = ethereumSlotDuration;
|
|
121
131
|
this.L2_SLOT_DURATION_IN_S = aztecSlotDuration;
|
|
122
132
|
|
|
133
|
+
// When skipInitialSequencer is set, auto-create a hardcoded account funded via genesis.
|
|
134
|
+
// This avoids needing to deploy accounts on-chain (which would require a running sequencer).
|
|
135
|
+
const useHardcodedAccount = opts.skipInitialSequencer && !opts.skipHardcodedAccount;
|
|
136
|
+
let hardcodedAccountData: InitialAccountData | undefined;
|
|
137
|
+
if (useHardcodedAccount) {
|
|
138
|
+
hardcodedAccountData = await EpochsTestContext.getHardcodedAccountData(Fr.random(), Fr.random());
|
|
139
|
+
}
|
|
140
|
+
|
|
123
141
|
// Set up system without any account nor protocol contracts
|
|
124
142
|
// and with faster block times and shorter epochs.
|
|
125
143
|
const context = await setup(
|
|
126
|
-
opts.numberOfAccounts ?? 0,
|
|
144
|
+
useHardcodedAccount ? 0 : (opts.numberOfAccounts ?? 0),
|
|
127
145
|
{
|
|
128
146
|
automineL1Setup: true,
|
|
129
147
|
checkIntervalMs: 50,
|
|
@@ -138,15 +156,13 @@ export class EpochsTestContext {
|
|
|
138
156
|
realProofs: false,
|
|
139
157
|
startProverNode: true,
|
|
140
158
|
proverTestDelayMs: opts.proverTestDelayMs ?? 0,
|
|
141
|
-
// We use numeric incremental prover ids for simplicity, but we can switch to
|
|
142
|
-
// using the prover's eth address if the proverId is used for something in the rollup contract
|
|
143
|
-
// Use numeric EthAddress for deterministic prover id
|
|
144
159
|
proverId: EthAddress.fromNumber(1),
|
|
145
160
|
worldStateCheckpointHistory: WORLD_STATE_CHECKPOINT_HISTORY,
|
|
146
161
|
exitDelaySeconds: DefaultL1ContractsConfig.exitDelaySeconds,
|
|
147
|
-
|
|
162
|
+
slasherEnabled: false,
|
|
148
163
|
l1PublishingTime,
|
|
149
164
|
...opts,
|
|
165
|
+
...(hardcodedAccountData ? { initialFundedAccounts: [hardcodedAccountData], numberOfAccounts: 0 } : {}),
|
|
150
166
|
},
|
|
151
167
|
// Use checkpointed chain tip for PXE by default to avoid issues with blocks being dropped due to pruned anchor blocks.
|
|
152
168
|
// Can be overridden via opts.pxeOpts.
|
|
@@ -154,6 +170,11 @@ export class EpochsTestContext {
|
|
|
154
170
|
);
|
|
155
171
|
|
|
156
172
|
this.context = context;
|
|
173
|
+
|
|
174
|
+
// Register the hardcoded account in PXE (local only, no on-chain deployment needed).
|
|
175
|
+
if (hardcodedAccountData) {
|
|
176
|
+
await this.registerHardcodedAccount(hardcodedAccountData);
|
|
177
|
+
}
|
|
157
178
|
this.proverNodes = context.proverNode ? [context.proverNode] : [];
|
|
158
179
|
this.nodes = context.aztecNode ? [context.aztecNode as AztecNodeService] : [];
|
|
159
180
|
this.logger = context.logger;
|
|
@@ -181,6 +202,7 @@ export class EpochsTestContext {
|
|
|
181
202
|
ethereumSlotDuration,
|
|
182
203
|
proofSubmissionEpochs: Number(await this.rollup.getProofSubmissionEpochs()),
|
|
183
204
|
targetCommitteeSize: await this.rollup.getTargetCommitteeSize(),
|
|
205
|
+
rollupManaLimit: Number(await this.rollup.getManaLimit()),
|
|
184
206
|
};
|
|
185
207
|
|
|
186
208
|
this.logger.info(
|
|
@@ -195,6 +217,35 @@ export class EpochsTestContext {
|
|
|
195
217
|
await this.context.teardown();
|
|
196
218
|
}
|
|
197
219
|
|
|
220
|
+
/**
|
|
221
|
+
* Computes InitialAccountData for a SchnorrHardcodedKeyAccountContract.
|
|
222
|
+
* This contract has a hardcoded signing key and no initializer, so it can be used without
|
|
223
|
+
* on-chain deployment. Pass the returned data in `initialFundedAccounts` so the address
|
|
224
|
+
* gets funded with fee juice in genesis.
|
|
225
|
+
*/
|
|
226
|
+
public static async getHardcodedAccountData(secret: Fr, salt: Fr): Promise<InitialAccountData> {
|
|
227
|
+
const contract = new SchnorrHardcodedKeyAccountContract();
|
|
228
|
+
const address = await getAccountContractAddress(contract, secret, salt);
|
|
229
|
+
const signingKey = SCHNORR_HARDCODED_PRIVATE_KEY;
|
|
230
|
+
return { secret, salt, signingKey, address };
|
|
231
|
+
}
|
|
232
|
+
|
|
233
|
+
/**
|
|
234
|
+
* Registers a SchnorrHardcodedKeyAccountContract in PXE. The account must have been funded
|
|
235
|
+
* at genesis (via getHardcodedAccountData). No on-chain deployment or block mining needed.
|
|
236
|
+
*/
|
|
237
|
+
public async registerHardcodedAccount(accountData: InitialAccountData) {
|
|
238
|
+
const contract = new SchnorrHardcodedKeyAccountContract();
|
|
239
|
+
const wallet = this.context.wallet;
|
|
240
|
+
const accountManager = await (wallet as TestWallet).createAccount({
|
|
241
|
+
secret: accountData.secret,
|
|
242
|
+
salt: accountData.salt,
|
|
243
|
+
contract,
|
|
244
|
+
});
|
|
245
|
+
this.context.accounts = [accountManager.address];
|
|
246
|
+
return accountManager.address;
|
|
247
|
+
}
|
|
248
|
+
|
|
198
249
|
public async createProverNode(opts: { dontStart?: boolean } & Partial<ProverNodeConfig> = {}) {
|
|
199
250
|
this.logger.warn('Creating and syncing a simulated prover node...');
|
|
200
251
|
const proverNodePrivateKey = this.getNextPrivateKey();
|
|
@@ -221,7 +272,7 @@ export class EpochsTestContext {
|
|
|
221
272
|
},
|
|
222
273
|
},
|
|
223
274
|
{
|
|
224
|
-
|
|
275
|
+
genesis: this.context.genesis,
|
|
225
276
|
dontStart: opts.dontStart,
|
|
226
277
|
},
|
|
227
278
|
),
|
|
@@ -237,13 +288,21 @@ export class EpochsTestContext {
|
|
|
237
288
|
|
|
238
289
|
public createValidatorNode(
|
|
239
290
|
privateKeys: `0x${string}`[],
|
|
240
|
-
opts: Partial<AztecNodeConfig> & {
|
|
291
|
+
opts: Partial<AztecNodeConfig> & {
|
|
292
|
+
dontStartSequencer?: boolean;
|
|
293
|
+
slashingProtectionDb?: SlashingProtectionDatabase;
|
|
294
|
+
} = {},
|
|
241
295
|
) {
|
|
242
296
|
this.logger.warn('Creating and syncing a validator node...');
|
|
243
297
|
return this.createNode({ ...opts, disableValidator: false, validatorPrivateKeys: new SecretValue(privateKeys) });
|
|
244
298
|
}
|
|
245
299
|
|
|
246
|
-
private async createNode(
|
|
300
|
+
private async createNode(
|
|
301
|
+
opts: Partial<AztecNodeConfig> & {
|
|
302
|
+
dontStartSequencer?: boolean;
|
|
303
|
+
slashingProtectionDb?: SlashingProtectionDatabase;
|
|
304
|
+
} = {},
|
|
305
|
+
) {
|
|
247
306
|
const nodeIndex = this.nodes.length + 1;
|
|
248
307
|
const actorPrefix = opts.disableValidator ? 'node' : 'validator';
|
|
249
308
|
const { mockGossipSubNetwork } = this.context;
|
|
@@ -256,6 +315,7 @@ export class EpochsTestContext {
|
|
|
256
315
|
...resolvedConfig,
|
|
257
316
|
dataDirectory: join(this.context.config.dataDirectory!, randomBytes(8).toString('hex')),
|
|
258
317
|
validatorPrivateKeys: opts.validatorPrivateKeys ?? new SecretValue([]),
|
|
318
|
+
nodeId: resolvedConfig.nodeId || `${actorPrefix}-${nodeIndex}`,
|
|
259
319
|
p2pEnabled,
|
|
260
320
|
p2pIp,
|
|
261
321
|
},
|
|
@@ -264,9 +324,10 @@ export class EpochsTestContext {
|
|
|
264
324
|
p2pClientDeps: {
|
|
265
325
|
p2pServiceFactory: mockGossipSubNetwork ? getMockPubSubP2PServiceFactory(mockGossipSubNetwork) : undefined,
|
|
266
326
|
},
|
|
327
|
+
slashingProtectionDb: opts.slashingProtectionDb,
|
|
267
328
|
},
|
|
268
329
|
{
|
|
269
|
-
|
|
330
|
+
genesis: this.context.genesis,
|
|
270
331
|
...opts,
|
|
271
332
|
},
|
|
272
333
|
),
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import type { AztecAddress } from '@aztec/aztec.js/addresses';
|
|
2
2
|
import { type Logger, createLogger } from '@aztec/aztec.js/log';
|
|
3
3
|
import type { AztecNode } from '@aztec/aztec.js/node';
|
|
4
|
-
import { CheatCodes } from '@aztec/aztec/testing';
|
|
4
|
+
import { CheatCodes, getTokenAllowedSetupFunctions } from '@aztec/aztec/testing';
|
|
5
5
|
import { createExtendedL1Client } from '@aztec/ethereum/client';
|
|
6
6
|
import { RollupContract } from '@aztec/ethereum/contracts';
|
|
7
7
|
import type { DeployAztecL1ContractsArgs } from '@aztec/ethereum/deploy-aztec-l1-contracts';
|
|
@@ -23,7 +23,7 @@ import type { AztecNodeAdmin } from '@aztec/stdlib/interfaces/client';
|
|
|
23
23
|
|
|
24
24
|
import { getContract } from 'viem';
|
|
25
25
|
|
|
26
|
-
import { MNEMONIC } from '../fixtures/fixtures.js';
|
|
26
|
+
import { MNEMONIC, getPaddedMaxFeesPerGas } from '../fixtures/fixtures.js';
|
|
27
27
|
import {
|
|
28
28
|
type EndToEndContext,
|
|
29
29
|
type SetupOptions,
|
|
@@ -104,12 +104,15 @@ export class FeesTest {
|
|
|
104
104
|
|
|
105
105
|
async setup() {
|
|
106
106
|
this.logger.verbose('Setting up fresh context...');
|
|
107
|
+
// Token allowlist entries are test-only: FPC-based fee payment with custom tokens won't work on mainnet alpha.
|
|
108
|
+
const tokenAllowList = await getTokenAllowedSetupFunctions();
|
|
107
109
|
this.context = await setup(0, {
|
|
108
110
|
startProverNode: true,
|
|
109
111
|
...this.setupOptions,
|
|
110
112
|
fundSponsoredFPC: true,
|
|
111
113
|
skipAccountDeployment: true,
|
|
112
114
|
l1ContractsArgs: { ...this.setupOptions },
|
|
115
|
+
txPublicSetupAllowListExtend: [...(this.setupOptions.txPublicSetupAllowListExtend ?? []), ...tokenAllowList],
|
|
113
116
|
});
|
|
114
117
|
|
|
115
118
|
this.rollupContract = RollupContract.getFromConfig(this.context.config);
|
|
@@ -131,7 +134,7 @@ export class FeesTest {
|
|
|
131
134
|
|
|
132
135
|
async catchUpProvenChain() {
|
|
133
136
|
const bn = await this.aztecNode.getBlockNumber();
|
|
134
|
-
while ((await this.aztecNode.
|
|
137
|
+
while ((await this.aztecNode.getBlockNumber('proven')) < bn) {
|
|
135
138
|
await sleep(1000);
|
|
136
139
|
}
|
|
137
140
|
}
|
|
@@ -157,11 +160,15 @@ export class FeesTest {
|
|
|
157
160
|
|
|
158
161
|
/** Alice mints bananaCoin tokens privately to the target address and redeems them. */
|
|
159
162
|
async mintPrivateBananas(amount: bigint, address: AztecAddress) {
|
|
160
|
-
const balanceBefore = await this.bananaCoin.methods
|
|
163
|
+
const { result: balanceBefore } = await this.bananaCoin.methods
|
|
164
|
+
.balance_of_private(address)
|
|
165
|
+
.simulate({ from: address });
|
|
161
166
|
|
|
162
167
|
await mintTokensToPrivate(this.bananaCoin, this.aliceAddress, address, amount);
|
|
163
168
|
|
|
164
|
-
const balanceAfter = await this.bananaCoin.methods
|
|
169
|
+
const { result: balanceAfter } = await this.bananaCoin.methods
|
|
170
|
+
.balance_of_private(address)
|
|
171
|
+
.simulate({ from: address });
|
|
165
172
|
expect(balanceAfter).toEqual(balanceBefore + amount);
|
|
166
173
|
}
|
|
167
174
|
|
|
@@ -186,7 +193,9 @@ export class FeesTest {
|
|
|
186
193
|
this.wallet = this.context.wallet;
|
|
187
194
|
this.aztecNode = this.context.aztecNodeService;
|
|
188
195
|
this.aztecNodeAdmin = this.context.aztecNodeService;
|
|
189
|
-
this.gasSettings = GasSettings.
|
|
196
|
+
this.gasSettings = GasSettings.fallback({
|
|
197
|
+
maxFeesPerGas: await getPaddedMaxFeesPerGas(this.aztecNode),
|
|
198
|
+
});
|
|
190
199
|
this.cheatCodes = this.context.cheatCodes;
|
|
191
200
|
this.accounts = deployedAccounts.map(a => a.address);
|
|
192
201
|
this.accounts.forEach((a, i) => this.logger.verbose(`Account ${i} address: ${a}`));
|
|
@@ -223,7 +232,7 @@ export class FeesTest {
|
|
|
223
232
|
async applyDeployBananaToken() {
|
|
224
233
|
this.logger.info('Applying deploy banana token setup');
|
|
225
234
|
|
|
226
|
-
const bananaCoin = await BananaCoin.deploy(this.wallet, this.aliceAddress, 'BC', 'BC', 18n).send({
|
|
235
|
+
const { contract: bananaCoin } = await BananaCoin.deploy(this.wallet, this.aliceAddress, 'BC', 'BC', 18n).send({
|
|
227
236
|
from: this.aliceAddress,
|
|
228
237
|
});
|
|
229
238
|
this.logger.info(`BananaCoin deployed at ${bananaCoin.address}`);
|
|
@@ -244,7 +253,7 @@ export class FeesTest {
|
|
|
244
253
|
expect((await this.wallet.getContractMetadata(feeJuiceContract.address)).isContractPublished).toBe(true);
|
|
245
254
|
|
|
246
255
|
const bananaCoin = this.bananaCoin;
|
|
247
|
-
const bananaFPC = await FPCContract.deploy(this.wallet, bananaCoin.address, this.fpcAdmin).send({
|
|
256
|
+
const { contract: bananaFPC } = await FPCContract.deploy(this.wallet, bananaCoin.address, this.fpcAdmin).send({
|
|
248
257
|
from: this.aliceAddress,
|
|
249
258
|
});
|
|
250
259
|
|
|
@@ -65,9 +65,11 @@ export class NestedContractTest {
|
|
|
65
65
|
|
|
66
66
|
async applyManual() {
|
|
67
67
|
this.logger.info('Deploying parent and child contracts');
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
this.childContract =
|
|
68
|
+
({ contract: this.parentContract } = await ParentContract.deploy(this.wallet).send({
|
|
69
|
+
from: this.defaultAccountAddress,
|
|
70
|
+
}));
|
|
71
|
+
({ contract: this.childContract } = await ChildContract.deploy(this.wallet).send({
|
|
72
|
+
from: this.defaultAccountAddress,
|
|
73
|
+
}));
|
|
72
74
|
}
|
|
73
75
|
}
|
|
@@ -58,6 +58,7 @@ export class P2PInactivityTest {
|
|
|
58
58
|
basePort: BOOT_NODE_UDP_PORT,
|
|
59
59
|
startProverNode: true,
|
|
60
60
|
initialConfig: {
|
|
61
|
+
anvilSlotsInAnEpoch: 4,
|
|
61
62
|
proverNodeConfig: { proverNodeEpochProvingDelayMs: AZTEC_SLOT_DURATION * 1000 },
|
|
62
63
|
aztecTargetCommitteeSize: COMMITTEE_SIZE,
|
|
63
64
|
aztecSlotDuration: AZTEC_SLOT_DURATION,
|
|
@@ -66,7 +67,6 @@ export class P2PInactivityTest {
|
|
|
66
67
|
listenAddress: '127.0.0.1',
|
|
67
68
|
minTxsPerBlock: 0,
|
|
68
69
|
aztecEpochDuration: EPOCH_DURATION,
|
|
69
|
-
validatorReexecute: false,
|
|
70
70
|
sentinelEnabled: true,
|
|
71
71
|
slashingQuorum: SLASHING_QUORUM,
|
|
72
72
|
slashingRoundSizeInEpochs: SLASHING_ROUND_SIZE_IN_EPOCHS,
|
|
@@ -108,7 +108,7 @@ export class P2PInactivityTest {
|
|
|
108
108
|
this.test.bootstrapNodeEnr,
|
|
109
109
|
NUM_NODES - this.inactiveNodeCount - Number(this.keepInitialNode),
|
|
110
110
|
BOOT_NODE_UDP_PORT,
|
|
111
|
-
this.test.
|
|
111
|
+
this.test.genesis,
|
|
112
112
|
this.dataDir,
|
|
113
113
|
undefined,
|
|
114
114
|
Number(this.keepInitialNode),
|
|
@@ -122,7 +122,7 @@ export class P2PInactivityTest {
|
|
|
122
122
|
this.test.bootstrapNodeEnr,
|
|
123
123
|
this.inactiveNodeCount,
|
|
124
124
|
BOOT_NODE_UDP_PORT,
|
|
125
|
-
this.test.
|
|
125
|
+
this.test.genesis,
|
|
126
126
|
this.dataDir,
|
|
127
127
|
undefined,
|
|
128
128
|
NUM_NODES - this.inactiveNodeCount,
|
|
@@ -1,14 +1,10 @@
|
|
|
1
|
-
import type
|
|
1
|
+
import { type InitialAccountData, generateSchnorrAccounts } from '@aztec/accounts/testing';
|
|
2
2
|
import type { AztecNodeConfig, AztecNodeService } from '@aztec/aztec-node';
|
|
3
|
+
import { getAccountContractAddress } from '@aztec/aztec.js/account';
|
|
3
4
|
import { AztecAddress, EthAddress } from '@aztec/aztec.js/addresses';
|
|
4
5
|
import { Fr } from '@aztec/aztec.js/fields';
|
|
5
6
|
import { getL1ContractsConfigEnvVars } from '@aztec/ethereum/config';
|
|
6
|
-
import {
|
|
7
|
-
type EmpireSlashingProposerContract,
|
|
8
|
-
GSEContract,
|
|
9
|
-
RollupContract,
|
|
10
|
-
type TallySlashingProposerContract,
|
|
11
|
-
} from '@aztec/ethereum/contracts';
|
|
7
|
+
import { GSEContract, RollupContract, type SlashingProposerContract } from '@aztec/ethereum/contracts';
|
|
12
8
|
import type { Operator } from '@aztec/ethereum/deploy-aztec-l1-contracts';
|
|
13
9
|
import { deployL1Contract } from '@aztec/ethereum/deploy-l1-contract';
|
|
14
10
|
import { MultiAdderArtifact } from '@aztec/ethereum/l1-artifacts';
|
|
@@ -24,9 +20,8 @@ import { SpamContract } from '@aztec/noir-test-contracts.js/Spam';
|
|
|
24
20
|
import type { BootstrapNode } from '@aztec/p2p/bootstrap';
|
|
25
21
|
import { createBootstrapNodeFromPrivateKey, getBootstrapNodeEnr } from '@aztec/p2p/test-helpers';
|
|
26
22
|
import { tryStop } from '@aztec/stdlib/interfaces/server';
|
|
27
|
-
import { SlashFactoryContract } from '@aztec/stdlib/l1-contracts';
|
|
28
23
|
import { TopicType } from '@aztec/stdlib/p2p';
|
|
29
|
-
import type {
|
|
24
|
+
import type { GenesisData } from '@aztec/stdlib/world-state';
|
|
30
25
|
import { ZkPassportProofParams } from '@aztec/stdlib/zkpassport';
|
|
31
26
|
import { getGenesisValues } from '@aztec/world-state/testing';
|
|
32
27
|
|
|
@@ -34,10 +29,13 @@ import getPort from 'get-port';
|
|
|
34
29
|
import { type GetContractReturnType, getAddress, getContract } from 'viem';
|
|
35
30
|
import { privateKeyToAccount } from 'viem/accounts';
|
|
36
31
|
|
|
32
|
+
import {
|
|
33
|
+
SCHNORR_HARDCODED_PRIVATE_KEY,
|
|
34
|
+
SchnorrHardcodedKeyAccountContract,
|
|
35
|
+
} from '../fixtures/schnorr_hardcoded_account_contract.js';
|
|
37
36
|
import {
|
|
38
37
|
type EndToEndContext,
|
|
39
38
|
type SetupOptions,
|
|
40
|
-
deployAccounts,
|
|
41
39
|
getPrivateKeyFromIndex,
|
|
42
40
|
getSponsoredFPCAddress,
|
|
43
41
|
setup,
|
|
@@ -59,7 +57,7 @@ export const WAIT_FOR_TX_TIMEOUT = l1ContractsConfig.aztecSlotDuration * 3;
|
|
|
59
57
|
export const SHORTENED_BLOCK_TIME_CONFIG_NO_PRUNES = {
|
|
60
58
|
aztecSlotDuration: 12,
|
|
61
59
|
ethereumSlotDuration: 4,
|
|
62
|
-
|
|
60
|
+
aztecProofSubmissionEpochs: 640,
|
|
63
61
|
};
|
|
64
62
|
|
|
65
63
|
export class P2PNetworkTest {
|
|
@@ -76,8 +74,8 @@ export class P2PNetworkTest {
|
|
|
76
74
|
public peerIdPrivateKeys: string[] = [];
|
|
77
75
|
public validators: Operator[] = [];
|
|
78
76
|
|
|
79
|
-
public
|
|
80
|
-
public
|
|
77
|
+
public hardcodedAccountData!: InitialAccountData;
|
|
78
|
+
public genesis: GenesisData | undefined;
|
|
81
79
|
|
|
82
80
|
// The re-execution test needs a wallet and a spam contract
|
|
83
81
|
public wallet?: TestWallet;
|
|
@@ -124,12 +122,11 @@ export class P2PNetworkTest {
|
|
|
124
122
|
initialValidatorConfig.aztecProofSubmissionEpochs ?? l1ContractsConfig.aztecProofSubmissionEpochs,
|
|
125
123
|
slashingRoundSizeInEpochs:
|
|
126
124
|
initialValidatorConfig.slashingRoundSizeInEpochs ?? l1ContractsConfig.slashingRoundSizeInEpochs,
|
|
127
|
-
|
|
125
|
+
slasherEnabled: initialValidatorConfig.slasherEnabled ?? true,
|
|
128
126
|
aztecTargetCommitteeSize: numberOfValidators,
|
|
129
127
|
metricsPort: metricsPort,
|
|
130
128
|
numberOfInitialFundedAccounts: 2,
|
|
131
129
|
startProverNode,
|
|
132
|
-
walletMinFeePadding: 2.0,
|
|
133
130
|
};
|
|
134
131
|
|
|
135
132
|
this.deployL1ContractsArgs = {
|
|
@@ -137,7 +134,7 @@ export class P2PNetworkTest {
|
|
|
137
134
|
aztecEpochDuration: initialValidatorConfig.aztecEpochDuration ?? l1ContractsConfig.aztecEpochDuration,
|
|
138
135
|
slashingRoundSizeInEpochs:
|
|
139
136
|
initialValidatorConfig.slashingRoundSizeInEpochs ?? l1ContractsConfig.slashingRoundSizeInEpochs,
|
|
140
|
-
|
|
137
|
+
slasherEnabled: initialValidatorConfig.slasherEnabled ?? true,
|
|
141
138
|
|
|
142
139
|
ethereumSlotDuration: initialValidatorConfig.ethereumSlotDuration ?? l1ContractsConfig.ethereumSlotDuration,
|
|
143
140
|
aztecSlotDuration: initialValidatorConfig.aztecSlotDuration ?? l1ContractsConfig.aztecSlotDuration,
|
|
@@ -192,10 +189,10 @@ export class P2PNetworkTest {
|
|
|
192
189
|
}
|
|
193
190
|
|
|
194
191
|
get fundedAccount() {
|
|
195
|
-
if (!this.
|
|
196
|
-
throw new Error('Call
|
|
192
|
+
if (!this.hardcodedAccountData) {
|
|
193
|
+
throw new Error('Call setup to initialize the hardcoded account.');
|
|
197
194
|
}
|
|
198
|
-
return this.
|
|
195
|
+
return this.hardcodedAccountData;
|
|
199
196
|
}
|
|
200
197
|
|
|
201
198
|
async addBootstrapNode() {
|
|
@@ -303,17 +300,22 @@ export class P2PNetworkTest {
|
|
|
303
300
|
await this._sendDummyTx(this.context.deployL1ContractsValues.l1Client);
|
|
304
301
|
}
|
|
305
302
|
|
|
303
|
+
/** Points the wallet to a P2P-enabled node so transactions can propagate through the network. */
|
|
304
|
+
setupWalletOnNode(node: AztecNodeService) {
|
|
305
|
+
this.logger.info('Pointing wallet to a P2P-enabled node');
|
|
306
|
+
this.context.wallet.updateNode(node);
|
|
307
|
+
}
|
|
308
|
+
|
|
309
|
+
/** Registers the hardcoded account in PXE without on-chain deployment. No sequencer needed. */
|
|
306
310
|
async setupAccount() {
|
|
307
|
-
this.logger.info('
|
|
308
|
-
const
|
|
309
|
-
|
|
310
|
-
this.
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
initialFundedAccounts: this.context.initialFundedAccounts,
|
|
311
|
+
this.logger.info('Registering hardcoded account (no deployment)');
|
|
312
|
+
const contract = new SchnorrHardcodedKeyAccountContract();
|
|
313
|
+
const accountManager = await (this.context.wallet as TestWallet).createAccount({
|
|
314
|
+
secret: this.hardcodedAccountData.secret,
|
|
315
|
+
salt: this.hardcodedAccountData.salt,
|
|
316
|
+
contract,
|
|
314
317
|
});
|
|
315
|
-
this.
|
|
316
|
-
[{ address: this.defaultAccountAddress }] = deployedAccounts;
|
|
318
|
+
this.defaultAccountAddress = accountManager.address;
|
|
317
319
|
this.wallet = this.context.wallet;
|
|
318
320
|
}
|
|
319
321
|
|
|
@@ -323,8 +325,9 @@ export class P2PNetworkTest {
|
|
|
323
325
|
throw new Error('Call setupAccount before deploying spam contract');
|
|
324
326
|
}
|
|
325
327
|
|
|
326
|
-
|
|
327
|
-
|
|
328
|
+
({ contract: this.spamContract } = await SpamContract.deploy(this.wallet).send({
|
|
329
|
+
from: this.defaultAccountAddress!,
|
|
330
|
+
}));
|
|
328
331
|
}
|
|
329
332
|
|
|
330
333
|
async removeInitialNode() {
|
|
@@ -353,13 +356,30 @@ export class P2PNetworkTest {
|
|
|
353
356
|
|
|
354
357
|
async setup() {
|
|
355
358
|
this.logger.info('Setting up subsystems from fresh');
|
|
359
|
+
|
|
360
|
+
// Pre-compute hardcoded account data so it gets funded in genesis.
|
|
361
|
+
const contract = new SchnorrHardcodedKeyAccountContract();
|
|
362
|
+
const secret = Fr.random();
|
|
363
|
+
const salt = Fr.random();
|
|
364
|
+
this.hardcodedAccountData = {
|
|
365
|
+
secret,
|
|
366
|
+
salt,
|
|
367
|
+
signingKey: SCHNORR_HARDCODED_PRIVATE_KEY,
|
|
368
|
+
address: await getAccountContractAddress(contract, secret, salt),
|
|
369
|
+
};
|
|
370
|
+
|
|
371
|
+
// Generate regular Schnorr accounts for tests that need deployable accounts (e.g. add_rollup).
|
|
372
|
+
const regularAccounts = await generateSchnorrAccounts(this.setupOptions.numberOfInitialFundedAccounts ?? 2);
|
|
373
|
+
|
|
356
374
|
this.context = await setup(
|
|
357
375
|
0,
|
|
358
376
|
{
|
|
359
377
|
...this.setupOptions,
|
|
360
378
|
fundSponsoredFPC: true,
|
|
361
379
|
skipAccountDeployment: true,
|
|
362
|
-
|
|
380
|
+
skipInitialSequencer: true,
|
|
381
|
+
initialFundedAccounts: [...regularAccounts, this.hardcodedAccountData],
|
|
382
|
+
slasherEnabled: this.setupOptions.slasherEnabled ?? this.deployL1ContractsArgs.slasherEnabled ?? false,
|
|
363
383
|
aztecTargetCommitteeSize: 0,
|
|
364
384
|
l1ContractsArgs: this.deployL1ContractsArgs,
|
|
365
385
|
},
|
|
@@ -371,8 +391,13 @@ export class P2PNetworkTest {
|
|
|
371
391
|
const sponsoredFPCAddress = await getSponsoredFPCAddress();
|
|
372
392
|
const initialFundedAccounts = [...this.context.initialFundedAccounts.map(a => a.address), sponsoredFPCAddress];
|
|
373
393
|
|
|
374
|
-
const {
|
|
375
|
-
|
|
394
|
+
const { genesis } = await getGenesisValues(
|
|
395
|
+
initialFundedAccounts,
|
|
396
|
+
undefined,
|
|
397
|
+
undefined,
|
|
398
|
+
this.context.genesis!.genesisTimestamp,
|
|
399
|
+
);
|
|
400
|
+
this.genesis = genesis;
|
|
376
401
|
|
|
377
402
|
const rollupContract = RollupContract.getFromL1ContractsValues(this.context.deployL1ContractsValues);
|
|
378
403
|
this.monitor = new ChainMonitor(rollupContract, this.context.dateProvider).start();
|
|
@@ -407,6 +432,7 @@ export class P2PNetworkTest {
|
|
|
407
432
|
expectedNodeCount?: number,
|
|
408
433
|
timeoutSeconds = 30,
|
|
409
434
|
checkIntervalSeconds = 0.1,
|
|
435
|
+
topics: TopicType[] = [TopicType.tx],
|
|
410
436
|
) {
|
|
411
437
|
const nodeCount = expectedNodeCount ?? nodes.length;
|
|
412
438
|
const minPeerCount = nodeCount - 1;
|
|
@@ -433,26 +459,28 @@ export class P2PNetworkTest {
|
|
|
433
459
|
|
|
434
460
|
this.logger.warn('All nodes connected to P2P mesh');
|
|
435
461
|
|
|
436
|
-
// Wait for GossipSub mesh to form for
|
|
462
|
+
// Wait for GossipSub mesh to form for all specified topics.
|
|
437
463
|
// We only require at least 1 mesh peer per node because GossipSub
|
|
438
464
|
// stops grafting once it reaches Dlo peers and won't fill the mesh to all available peers.
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
|
|
465
|
+
for (const topic of topics) {
|
|
466
|
+
this.logger.warn(`Waiting for GossipSub mesh to form for ${topic} topic...`);
|
|
467
|
+
await Promise.all(
|
|
468
|
+
nodes.map(async (node, index) => {
|
|
469
|
+
const p2p = node.getP2P();
|
|
470
|
+
await retryUntil(
|
|
471
|
+
async () => {
|
|
472
|
+
const meshPeers = await p2p.getGossipMeshPeerCount(topic);
|
|
473
|
+
this.logger.debug(`Node ${index} has ${meshPeers} gossip mesh peers for ${topic} topic`);
|
|
474
|
+
return meshPeers >= 1 ? true : undefined;
|
|
475
|
+
},
|
|
476
|
+
`Node ${index} to have gossip mesh peers for ${topic} topic`,
|
|
477
|
+
timeoutSeconds,
|
|
478
|
+
checkIntervalSeconds,
|
|
479
|
+
);
|
|
480
|
+
}),
|
|
481
|
+
);
|
|
482
|
+
this.logger.warn(`All nodes have gossip mesh peers for ${topic} topic`);
|
|
483
|
+
}
|
|
456
484
|
}
|
|
457
485
|
|
|
458
486
|
async teardown() {
|
|
@@ -464,8 +492,7 @@ export class P2PNetworkTest {
|
|
|
464
492
|
async getContracts(): Promise<{
|
|
465
493
|
rollup: RollupContract;
|
|
466
494
|
slasherContract: GetContractReturnType<typeof SlasherAbi, ViemClient>;
|
|
467
|
-
slashingProposer:
|
|
468
|
-
slashFactory: SlashFactoryContract;
|
|
495
|
+
slashingProposer: SlashingProposerContract | undefined;
|
|
469
496
|
}> {
|
|
470
497
|
if (!this.ctx.deployL1ContractsValues) {
|
|
471
498
|
throw new Error('DeployAztecL1ContractsValues not set');
|
|
@@ -482,14 +509,9 @@ export class P2PNetworkTest {
|
|
|
482
509
|
client: this.ctx.deployL1ContractsValues.l1Client,
|
|
483
510
|
});
|
|
484
511
|
|
|
485
|
-
// Get the actual slashing proposer from rollup
|
|
512
|
+
// Get the actual slashing proposer from rollup
|
|
486
513
|
const slashingProposer = await rollup.getSlashingProposer();
|
|
487
514
|
|
|
488
|
-
|
|
489
|
-
this.ctx.deployL1ContractsValues.l1Client,
|
|
490
|
-
getAddress(this.ctx.deployL1ContractsValues.l1ContractAddresses.slashFactoryAddress!.toString()),
|
|
491
|
-
);
|
|
492
|
-
|
|
493
|
-
return { rollup, slasherContract, slashingProposer, slashFactory };
|
|
515
|
+
return { rollup, slasherContract, slashingProposer };
|
|
494
516
|
}
|
|
495
517
|
}
|
|
@@ -91,7 +91,7 @@ export async function runReqrespTxTest(params: {
|
|
|
91
91
|
t.bootstrapNodeEnr,
|
|
92
92
|
NUM_VALIDATORS,
|
|
93
93
|
BOOT_NODE_UDP_PORT,
|
|
94
|
-
t.
|
|
94
|
+
t.genesis,
|
|
95
95
|
dataDir,
|
|
96
96
|
shouldCollectMetrics(),
|
|
97
97
|
);
|
|
@@ -149,6 +149,13 @@ export async function runReqrespTxTest(params: {
|
|
|
149
149
|
const submittedTxs = await Promise.all(
|
|
150
150
|
txBatches.map(async (batch, batchIndex) => {
|
|
151
151
|
const proposerNode = nodes[proposerIndexes[batchIndex]];
|
|
152
|
+
for (const tx of batch) {
|
|
153
|
+
t.logger.info(`Tx ${tx.getTxHash().toString()} base64: ${tx.toBuffer().toString('base64')}`);
|
|
154
|
+
}
|
|
155
|
+
const txHashes = batch.map(tx => tx.getTxHash().toString());
|
|
156
|
+
t.logger.info(
|
|
157
|
+
`Sending batch ${batchIndex} to proposer ${getNodePort(proposerIndexes[batchIndex])}: ${txHashes.join(', ')}`,
|
|
158
|
+
);
|
|
152
159
|
await Promise.all(
|
|
153
160
|
batch.map(async tx => {
|
|
154
161
|
try {
|
|
@@ -163,6 +170,12 @@ export async function runReqrespTxTest(params: {
|
|
|
163
170
|
}),
|
|
164
171
|
);
|
|
165
172
|
|
|
173
|
+
// Log pool state per node after sending
|
|
174
|
+
for (let i = 0; i < NUM_VALIDATORS; i++) {
|
|
175
|
+
const count = await nodes[i].getPendingTxCount();
|
|
176
|
+
t.logger.info(`Node ${getNodePort(i)} pool has ${count} pending txs`);
|
|
177
|
+
}
|
|
178
|
+
|
|
166
179
|
t.logger.info('Waiting for all transactions to be mined');
|
|
167
180
|
await Promise.all(
|
|
168
181
|
submittedTxs.flatMap((batch, batchIndex) =>
|
|
@@ -178,20 +191,29 @@ export async function runReqrespTxTest(params: {
|
|
|
178
191
|
|
|
179
192
|
// Assert that multiple blocks were built for at least one slot
|
|
180
193
|
t.logger.info('Verifying multiple blocks for at least one checkpoint');
|
|
181
|
-
|
|
182
|
-
|
|
194
|
+
// Wait for L1 checkpoint sync, which may lag behind P2P block propagation.
|
|
195
|
+
const checkpoints = await retryUntil(
|
|
196
|
+
async () => {
|
|
197
|
+
const cps = await nodes[0].getCheckpoints(CheckpointNumber(1), 50, { includeBlocks: true });
|
|
198
|
+
return cps.length > 0 && cps.some(cp => (cp.blocks?.length ?? 0) >= 2) ? cps : undefined;
|
|
199
|
+
},
|
|
200
|
+
'waiting for multi-block checkpoint to sync from L1',
|
|
201
|
+
30,
|
|
202
|
+
1,
|
|
203
|
+
);
|
|
183
204
|
|
|
184
205
|
let mbpsFound = false;
|
|
185
|
-
let expectedBlockNumber = checkpoints[0].
|
|
206
|
+
let expectedBlockNumber = checkpoints[0].blocks![0].number;
|
|
186
207
|
|
|
187
208
|
for (const published of checkpoints) {
|
|
188
|
-
const
|
|
209
|
+
const blocks = published.blocks!;
|
|
210
|
+
const blockCount = blocks.length;
|
|
189
211
|
mbpsFound = mbpsFound || blockCount >= 2;
|
|
190
212
|
|
|
191
213
|
for (let i = 0; i < blockCount; i++) {
|
|
192
|
-
const block =
|
|
214
|
+
const block = blocks[i];
|
|
193
215
|
expect(block.indexWithinCheckpoint).toBe(i);
|
|
194
|
-
expect(block.checkpointNumber).toBe(published.
|
|
216
|
+
expect(block.checkpointNumber).toBe(published.number);
|
|
195
217
|
expect(block.number).toBe(expectedBlockNumber);
|
|
196
218
|
expectedBlockNumber++;
|
|
197
219
|
}
|