@aztec-labs/cli 6.0.0-nightly.20260829
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 +23 -0
- package/dest/cmds/aztec_node/block_number.d.ts +3 -0
- package/dest/cmds/aztec_node/block_number.d.ts.map +1 -0
- package/dest/cmds/aztec_node/block_number.js +10 -0
- package/dest/cmds/aztec_node/get_block.d.ts +3 -0
- package/dest/cmds/aztec_node/get_block.d.ts.map +1 -0
- package/dest/cmds/aztec_node/get_block.js +10 -0
- package/dest/cmds/aztec_node/get_current_min_fee.d.ts +3 -0
- package/dest/cmds/aztec_node/get_current_min_fee.d.ts.map +1 -0
- package/dest/cmds/aztec_node/get_current_min_fee.js +7 -0
- package/dest/cmds/aztec_node/get_l1_to_l2_message_witness.d.ts +5 -0
- package/dest/cmds/aztec_node/get_l1_to_l2_message_witness.d.ts.map +1 -0
- package/dest/cmds/aztec_node/get_l1_to_l2_message_witness.js +12 -0
- package/dest/cmds/aztec_node/get_logs.d.ts +33 -0
- package/dest/cmds/aztec_node/get_logs.d.ts.map +1 -0
- package/dest/cmds/aztec_node/get_logs.js +61 -0
- package/dest/cmds/aztec_node/get_node_info.d.ts +3 -0
- package/dest/cmds/aztec_node/get_node_info.d.ts.map +1 -0
- package/dest/cmds/aztec_node/get_node_info.js +58 -0
- package/dest/cmds/aztec_node/index.d.ts +4 -0
- package/dest/cmds/aztec_node/index.d.ts.map +1 -0
- package/dest/cmds/aztec_node/index.js +38 -0
- package/dest/cmds/infrastructure/index.d.ts +4 -0
- package/dest/cmds/infrastructure/index.d.ts.map +1 -0
- package/dest/cmds/infrastructure/index.js +22 -0
- package/dest/cmds/infrastructure/sequencers.d.ts +12 -0
- package/dest/cmds/infrastructure/sequencers.d.ts.map +1 -0
- package/dest/cmds/infrastructure/sequencers.js +113 -0
- package/dest/cmds/infrastructure/setup_l2_contract.d.ts +3 -0
- package/dest/cmds/infrastructure/setup_l2_contract.d.ts.map +1 -0
- package/dest/cmds/infrastructure/setup_l2_contract.js +35 -0
- package/dest/cmds/l1/advance_epoch.d.ts +3 -0
- package/dest/cmds/l1/advance_epoch.d.ts.map +1 -0
- package/dest/cmds/l1/advance_epoch.js +12 -0
- package/dest/cmds/l1/assume_proven_through.d.ts +4 -0
- package/dest/cmds/l1/assume_proven_through.d.ts.map +1 -0
- package/dest/cmds/l1/assume_proven_through.js +12 -0
- package/dest/cmds/l1/compute_genesis_values.d.ts +4 -0
- package/dest/cmds/l1/compute_genesis_values.d.ts.map +1 -0
- package/dest/cmds/l1/compute_genesis_values.js +17 -0
- package/dest/cmds/l1/create_l1_account.d.ts +3 -0
- package/dest/cmds/l1/create_l1_account.d.ts.map +1 -0
- package/dest/cmds/l1/create_l1_account.js +15 -0
- package/dest/cmds/l1/deploy_l1_contracts_cmd.d.ts +4 -0
- package/dest/cmds/l1/deploy_l1_contracts_cmd.d.ts.map +1 -0
- package/dest/cmds/l1/deploy_l1_contracts_cmd.js +80 -0
- package/dest/cmds/l1/deploy_new_rollup.d.ts +5 -0
- package/dest/cmds/l1/deploy_new_rollup.d.ts.map +1 -0
- package/dest/cmds/l1/deploy_new_rollup.js +26 -0
- package/dest/cmds/l1/get_l1_addresses.d.ts +4 -0
- package/dest/cmds/l1/get_l1_addresses.d.ts.map +1 -0
- package/dest/cmds/l1/get_l1_addresses.js +21 -0
- package/dest/cmds/l1/get_l1_balance.d.ts +4 -0
- package/dest/cmds/l1/get_l1_balance.d.ts.map +1 -0
- package/dest/cmds/l1/get_l1_balance.js +35 -0
- package/dest/cmds/l1/governance_utils.d.ts +50 -0
- package/dest/cmds/l1/governance_utils.d.ts.map +1 -0
- package/dest/cmds/l1/governance_utils.js +87 -0
- package/dest/cmds/l1/index.d.ts +4 -0
- package/dest/cmds/l1/index.d.ts.map +1 -0
- package/dest/cmds/l1/index.js +201 -0
- package/dest/cmds/l1/prover_stats.d.ts +14 -0
- package/dest/cmds/l1/prover_stats.d.ts.map +1 -0
- package/dest/cmds/l1/prover_stats.js +147 -0
- package/dest/cmds/l1/trigger_seed_snapshot.d.ts +6 -0
- package/dest/cmds/l1/trigger_seed_snapshot.d.ts.map +1 -0
- package/dest/cmds/l1/trigger_seed_snapshot.js +20 -0
- package/dest/cmds/l1/update_l1_validators.d.ts +45 -0
- package/dest/cmds/l1/update_l1_validators.d.ts.map +1 -0
- package/dest/cmds/l1/update_l1_validators.js +280 -0
- package/dest/cmds/misc/generate_bootnode_enr.d.ts +3 -0
- package/dest/cmds/misc/generate_bootnode_enr.d.ts.map +1 -0
- package/dest/cmds/misc/generate_bootnode_enr.js +5 -0
- package/dest/cmds/misc/generate_p2p_private_key.d.ts +3 -0
- package/dest/cmds/misc/generate_p2p_private_key.d.ts.map +1 -0
- package/dest/cmds/misc/generate_p2p_private_key.js +7 -0
- package/dest/cmds/misc/generate_secret_key.d.ts +5 -0
- package/dest/cmds/misc/generate_secret_key.d.ts.map +1 -0
- package/dest/cmds/misc/generate_secret_key.js +6 -0
- package/dest/cmds/misc/index.d.ts +4 -0
- package/dest/cmds/misc/index.d.ts.map +1 -0
- package/dest/cmds/misc/index.js +32 -0
- package/dest/cmds/misc/update/common.d.ts +17 -0
- package/dest/cmds/misc/update/common.d.ts.map +1 -0
- package/dest/cmds/misc/update/common.js +3 -0
- package/dest/cmds/misc/update/github.d.ts +3 -0
- package/dest/cmds/misc/update/github.d.ts.map +1 -0
- package/dest/cmds/misc/update/github.js +2 -0
- package/dest/cmds/misc/update/noir.d.ts +10 -0
- package/dest/cmds/misc/update/noir.d.ts.map +1 -0
- package/dest/cmds/misc/update/noir.js +45 -0
- package/dest/cmds/misc/update/npm.d.ts +34 -0
- package/dest/cmds/misc/update/npm.d.ts.map +1 -0
- package/dest/cmds/misc/update/npm.js +123 -0
- package/dest/cmds/misc/update/utils.d.ts +14 -0
- package/dest/cmds/misc/update/utils.d.ts.map +1 -0
- package/dest/cmds/misc/update/utils.js +38 -0
- package/dest/cmds/misc/update.d.ts +3 -0
- package/dest/cmds/misc/update.d.ts.map +1 -0
- package/dest/cmds/misc/update.js +51 -0
- package/dest/cmds/validator_keys/add.d.ts +5 -0
- package/dest/cmds/validator_keys/add.d.ts.map +1 -0
- package/dest/cmds/validator_keys/add.js +83 -0
- package/dest/cmds/validator_keys/eth_json_v3_worker.d.ts +2 -0
- package/dest/cmds/validator_keys/eth_json_v3_worker.d.ts.map +1 -0
- package/dest/cmds/validator_keys/eth_json_v3_worker.js +27 -0
- package/dest/cmds/validator_keys/generate_bls_keypair.d.ts +12 -0
- package/dest/cmds/validator_keys/generate_bls_keypair.d.ts.map +1 -0
- package/dest/cmds/validator_keys/generate_bls_keypair.js +27 -0
- package/dest/cmds/validator_keys/index.d.ts +4 -0
- package/dest/cmds/validator_keys/index.d.ts.map +1 -0
- package/dest/cmds/validator_keys/index.js +33 -0
- package/dest/cmds/validator_keys/new.d.ts +35 -0
- package/dest/cmds/validator_keys/new.d.ts.map +1 -0
- package/dest/cmds/validator_keys/new.js +220 -0
- package/dest/cmds/validator_keys/set_funding_account.d.ts +14 -0
- package/dest/cmds/validator_keys/set_funding_account.d.ts.map +1 -0
- package/dest/cmds/validator_keys/set_funding_account.js +37 -0
- package/dest/cmds/validator_keys/shared.d.ts +81 -0
- package/dest/cmds/validator_keys/shared.d.ts.map +1 -0
- package/dest/cmds/validator_keys/shared.js +352 -0
- package/dest/cmds/validator_keys/staker.d.ts +38 -0
- package/dest/cmds/validator_keys/staker.d.ts.map +1 -0
- package/dest/cmds/validator_keys/staker.js +210 -0
- package/dest/cmds/validator_keys/utils.d.ts +35 -0
- package/dest/cmds/validator_keys/utils.d.ts.map +1 -0
- package/dest/cmds/validator_keys/utils.js +86 -0
- package/dest/config/cached_fetch.d.ts +27 -0
- package/dest/config/cached_fetch.d.ts.map +1 -0
- package/dest/config/cached_fetch.js +132 -0
- package/dest/config/chain_l2_config.d.ts +19 -0
- package/dest/config/chain_l2_config.d.ts.map +1 -0
- package/dest/config/chain_l2_config.js +60 -0
- package/dest/config/enrich_env.d.ts +4 -0
- package/dest/config/enrich_env.d.ts.map +1 -0
- package/dest/config/enrich_env.js +12 -0
- package/dest/config/generated/networks.d.ts +236 -0
- package/dest/config/generated/networks.d.ts.map +1 -0
- package/dest/config/generated/networks.js +237 -0
- package/dest/config/get_l1_config.d.ts +9 -0
- package/dest/config/get_l1_config.d.ts.map +1 -0
- package/dest/config/get_l1_config.js +24 -0
- package/dest/config/index.d.ts +5 -0
- package/dest/config/index.d.ts.map +1 -0
- package/dest/config/index.js +4 -0
- package/dest/config/network_config.d.ts +22 -0
- package/dest/config/network_config.d.ts.map +1 -0
- package/dest/config/network_config.js +119 -0
- package/dest/utils/aztec.d.ts +56 -0
- package/dest/utils/aztec.d.ts.map +1 -0
- package/dest/utils/aztec.js +161 -0
- package/dest/utils/commands.d.ts +161 -0
- package/dest/utils/commands.d.ts.map +1 -0
- package/dest/utils/commands.js +341 -0
- package/dest/utils/encoding.d.ts +15 -0
- package/dest/utils/encoding.d.ts.map +1 -0
- package/dest/utils/encoding.js +103 -0
- package/dest/utils/github.d.ts +3 -0
- package/dest/utils/github.d.ts.map +1 -0
- package/dest/utils/github.js +2 -0
- package/dest/utils/index.d.ts +6 -0
- package/dest/utils/index.d.ts.map +1 -0
- package/dest/utils/index.js +5 -0
- package/dest/utils/inspect.d.ts +11 -0
- package/dest/utils/inspect.d.ts.map +1 -0
- package/dest/utils/inspect.js +90 -0
- package/dest/utils/setup_contracts.d.ts +3 -0
- package/dest/utils/setup_contracts.d.ts.map +1 -0
- package/dest/utils/setup_contracts.js +16 -0
- package/package.json +141 -0
- package/public_include_metric_prefixes.json +1 -0
- package/src/cmds/aztec_node/block_number.ts +9 -0
- package/src/cmds/aztec_node/get_block.ts +11 -0
- package/src/cmds/aztec_node/get_current_min_fee.ts +9 -0
- package/src/cmds/aztec_node/get_l1_to_l2_message_witness.ts +27 -0
- package/src/cmds/aztec_node/get_logs.ts +100 -0
- package/src/cmds/aztec_node/get_node_info.ts +61 -0
- package/src/cmds/aztec_node/index.ts +91 -0
- package/src/cmds/infrastructure/index.ts +51 -0
- package/src/cmds/infrastructure/sequencers.ts +122 -0
- package/src/cmds/infrastructure/setup_l2_contract.ts +40 -0
- package/src/cmds/l1/advance_epoch.ts +14 -0
- package/src/cmds/l1/assume_proven_through.ts +20 -0
- package/src/cmds/l1/compute_genesis_values.ts +29 -0
- package/src/cmds/l1/create_l1_account.ts +16 -0
- package/src/cmds/l1/deploy_l1_contracts_cmd.ts +105 -0
- package/src/cmds/l1/deploy_new_rollup.ts +65 -0
- package/src/cmds/l1/get_l1_addresses.ts +31 -0
- package/src/cmds/l1/get_l1_balance.ts +44 -0
- package/src/cmds/l1/governance_utils.ts +183 -0
- package/src/cmds/l1/index.ts +499 -0
- package/src/cmds/l1/prover_stats.ts +213 -0
- package/src/cmds/l1/trigger_seed_snapshot.ts +32 -0
- package/src/cmds/l1/update_l1_validators.ts +358 -0
- package/src/cmds/misc/generate_bootnode_enr.ts +13 -0
- package/src/cmds/misc/generate_p2p_private_key.ts +9 -0
- package/src/cmds/misc/generate_secret_key.ts +5 -0
- package/src/cmds/misc/index.ts +67 -0
- package/src/cmds/misc/update/common.ts +16 -0
- package/src/cmds/misc/update/github.ts +2 -0
- package/src/cmds/misc/update/noir.ts +56 -0
- package/src/cmds/misc/update/npm.ts +148 -0
- package/src/cmds/misc/update/utils.ts +49 -0
- package/src/cmds/misc/update.ts +71 -0
- package/src/cmds/validator_keys/add.ts +122 -0
- package/src/cmds/validator_keys/eth_json_v3_worker.ts +30 -0
- package/src/cmds/validator_keys/generate_bls_keypair.ts +33 -0
- package/src/cmds/validator_keys/index.ts +181 -0
- package/src/cmds/validator_keys/new.ts +326 -0
- package/src/cmds/validator_keys/set_funding_account.ts +54 -0
- package/src/cmds/validator_keys/shared.ts +414 -0
- package/src/cmds/validator_keys/staker.ts +300 -0
- package/src/cmds/validator_keys/utils.ts +124 -0
- package/src/config/cached_fetch.ts +154 -0
- package/src/config/chain_l2_config.ts +71 -0
- package/src/config/enrich_env.ts +15 -0
- package/src/config/generated/networks.ts +241 -0
- package/src/config/get_l1_config.ts +31 -0
- package/src/config/index.ts +4 -0
- package/src/config/network_config.ts +150 -0
- package/src/utils/aztec.ts +203 -0
- package/src/utils/commands.ts +434 -0
- package/src/utils/encoding.ts +117 -0
- package/src/utils/github.ts +2 -0
- package/src/utils/index.ts +5 -0
- package/src/utils/inspect.ts +111 -0
- package/src/utils/setup_contracts.ts +19 -0
|
@@ -0,0 +1,213 @@
|
|
|
1
|
+
import { RollupAbi } from '@aztec/l1-artifacts';
|
|
2
|
+
|
|
3
|
+
import { retrieveL2ProofVerifiedEvents } from '@aztec-labs/archiver';
|
|
4
|
+
import { createEthereumChain } from '@aztec-labs/ethereum/chain';
|
|
5
|
+
import type { ViemPublicClient } from '@aztec-labs/ethereum/types';
|
|
6
|
+
import { compactArray, mapValues, unique } from '@aztec-labs/foundation/collection';
|
|
7
|
+
import { EthAddress } from '@aztec-labs/foundation/eth-address';
|
|
8
|
+
import { type LogFn, type Logger, createLogger } from '@aztec-labs/foundation/log';
|
|
9
|
+
import { createAztecNodeClient } from '@aztec-labs/stdlib/interfaces/client';
|
|
10
|
+
import chunk from 'lodash.chunk';
|
|
11
|
+
import groupBy from 'lodash.groupby';
|
|
12
|
+
import { createPublicClient, fallback, getAbiItem, getAddress, http } from 'viem';
|
|
13
|
+
|
|
14
|
+
export async function proverStats(opts: {
|
|
15
|
+
l1RpcUrls: string[];
|
|
16
|
+
chainId: number;
|
|
17
|
+
l1RollupAddress: string | undefined;
|
|
18
|
+
nodeUrl: string | undefined;
|
|
19
|
+
log: LogFn;
|
|
20
|
+
startBlock: bigint;
|
|
21
|
+
endBlock: bigint | undefined;
|
|
22
|
+
batchSize: bigint;
|
|
23
|
+
provingTimeout: bigint | undefined;
|
|
24
|
+
rawLogs: boolean;
|
|
25
|
+
}) {
|
|
26
|
+
const debugLog = createLogger('cli:prover_stats');
|
|
27
|
+
const {
|
|
28
|
+
startBlock,
|
|
29
|
+
chainId,
|
|
30
|
+
l1RpcUrls,
|
|
31
|
+
l1RollupAddress,
|
|
32
|
+
batchSize,
|
|
33
|
+
nodeUrl,
|
|
34
|
+
provingTimeout,
|
|
35
|
+
endBlock,
|
|
36
|
+
rawLogs,
|
|
37
|
+
log,
|
|
38
|
+
} = opts;
|
|
39
|
+
if (!l1RollupAddress && !nodeUrl) {
|
|
40
|
+
throw new Error('Either L1 rollup address or node URL must be set');
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
const rollup = l1RollupAddress
|
|
44
|
+
? EthAddress.fromString(l1RollupAddress)
|
|
45
|
+
: await createAztecNodeClient(nodeUrl!)
|
|
46
|
+
.getL1ContractAddresses()
|
|
47
|
+
.then(a => a.rollupAddress);
|
|
48
|
+
|
|
49
|
+
const chain = createEthereumChain(l1RpcUrls, chainId).chainInfo;
|
|
50
|
+
const publicClient = createPublicClient({
|
|
51
|
+
chain,
|
|
52
|
+
transport: fallback(l1RpcUrls.map(url => http(url, { batch: false }))),
|
|
53
|
+
});
|
|
54
|
+
const lastBlockNum = endBlock ?? (await publicClient.getBlockNumber());
|
|
55
|
+
debugLog.verbose(`Querying events on rollup at ${rollup.toString()} from ${startBlock} up to ${lastBlockNum}`);
|
|
56
|
+
|
|
57
|
+
// Get all events for L2 proof submissions
|
|
58
|
+
const events = await getL2ProofVerifiedEvents(startBlock, lastBlockNum, batchSize, debugLog, publicClient, rollup);
|
|
59
|
+
|
|
60
|
+
// If we only care for raw logs, output them
|
|
61
|
+
if (rawLogs && !provingTimeout) {
|
|
62
|
+
log(`l1_block_number, checkpoint_number, prover_id, tx_hash`);
|
|
63
|
+
for (const event of events) {
|
|
64
|
+
const { l1BlockNumber, checkpointNumber, proverId, txHash } = event;
|
|
65
|
+
log(`${l1BlockNumber}, ${checkpointNumber}, ${proverId}, ${txHash}`);
|
|
66
|
+
}
|
|
67
|
+
return;
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
// If we don't have a proving timeout, we can just count the number of unique checkpoints per prover
|
|
71
|
+
if (!provingTimeout) {
|
|
72
|
+
const stats = groupBy(events, 'proverId');
|
|
73
|
+
log(`prover_id, total_checkpoints_proven`);
|
|
74
|
+
for (const proverId in stats) {
|
|
75
|
+
const uniqueCheckpoints = new Set(stats[proverId].map(e => e.checkpointNumber));
|
|
76
|
+
log(`${proverId}, ${uniqueCheckpoints.size}`);
|
|
77
|
+
}
|
|
78
|
+
return;
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
// But if we do, fetch the events for each checkpoint submitted, so we can look up their timestamp
|
|
82
|
+
const checkpointEvents = await getCheckpointProposedEvents(
|
|
83
|
+
startBlock,
|
|
84
|
+
lastBlockNum,
|
|
85
|
+
batchSize,
|
|
86
|
+
debugLog,
|
|
87
|
+
publicClient,
|
|
88
|
+
rollup,
|
|
89
|
+
);
|
|
90
|
+
debugLog.verbose(
|
|
91
|
+
`First checkpoint within range is ${checkpointEvents[0]?.args.checkpointNumber} at L1 block ${checkpointEvents[0]?.blockNumber}`,
|
|
92
|
+
);
|
|
93
|
+
|
|
94
|
+
// Get the timestamps for every block on every log, both for proof and block submissions
|
|
95
|
+
const l1BlockNumbers = unique([...events.map(e => e.l1BlockNumber), ...checkpointEvents.map(e => e.blockNumber)]);
|
|
96
|
+
const l1BlockTimestamps: Record<string, bigint> = {};
|
|
97
|
+
for (const l1Batch of chunk(l1BlockNumbers, Number(batchSize))) {
|
|
98
|
+
const blocks = await Promise.all(
|
|
99
|
+
l1Batch.map(blockNumber => publicClient.getBlock({ includeTransactions: false, blockNumber })),
|
|
100
|
+
);
|
|
101
|
+
debugLog.verbose(`Queried ${blocks.length} L1 blocks between ${l1Batch[0]} and ${l1Batch[l1Batch.length - 1]}`);
|
|
102
|
+
for (const block of blocks) {
|
|
103
|
+
l1BlockTimestamps[block.number.toString()] = block.timestamp;
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
// Map from checkpoint number to the l1 block in which it was submitted
|
|
108
|
+
const checkpointSubmissions: Record<string, bigint> = {};
|
|
109
|
+
for (const checkpointEvent of checkpointEvents) {
|
|
110
|
+
checkpointSubmissions[checkpointEvent.args.checkpointNumber!.toString()] = checkpointEvent.blockNumber;
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
// If we want raw logs, output them
|
|
114
|
+
if (rawLogs) {
|
|
115
|
+
log(`l1_block_number, checkpoint_number, checkpoint_submission_timestamp, proof_timestamp, prover_id, tx_hash`);
|
|
116
|
+
for (const event of events) {
|
|
117
|
+
const { l1BlockNumber, checkpointNumber, proverId, txHash } = event;
|
|
118
|
+
const uploadedBlockNumber = checkpointSubmissions[checkpointNumber.toString()];
|
|
119
|
+
if (!uploadedBlockNumber) {
|
|
120
|
+
continue;
|
|
121
|
+
}
|
|
122
|
+
const uploadedTimestamp = l1BlockTimestamps[uploadedBlockNumber.toString()];
|
|
123
|
+
const provenTimestamp = l1BlockTimestamps[l1BlockNumber.toString()];
|
|
124
|
+
log(`${l1BlockNumber}, ${checkpointNumber}, ${uploadedTimestamp}, ${provenTimestamp}, ${proverId}, ${txHash}`);
|
|
125
|
+
}
|
|
126
|
+
return;
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
// Or calculate stats per prover
|
|
130
|
+
const stats = mapValues(groupBy(events, 'proverId'), (checkpoints, proverId) =>
|
|
131
|
+
compactArray(
|
|
132
|
+
checkpoints.map(e => {
|
|
133
|
+
const provenTimestamp = l1BlockTimestamps[e.l1BlockNumber.toString()];
|
|
134
|
+
const uploadedBlockNumber = checkpointSubmissions[e.checkpointNumber.toString()];
|
|
135
|
+
if (!uploadedBlockNumber) {
|
|
136
|
+
debugLog.verbose(
|
|
137
|
+
`Skipping ${proverId}'s proof for checkpoint ${e.checkpointNumber} as it was before the start block`,
|
|
138
|
+
);
|
|
139
|
+
return undefined;
|
|
140
|
+
}
|
|
141
|
+
const uploadedTimestamp = l1BlockTimestamps[uploadedBlockNumber.toString()];
|
|
142
|
+
const provingTime = provenTimestamp - uploadedTimestamp;
|
|
143
|
+
debugLog.debug(
|
|
144
|
+
`prover=${e.proverId} checkpointNumber=${e.checkpointNumber} uploaded=${uploadedTimestamp} proven=${provenTimestamp} time=${provingTime}`,
|
|
145
|
+
);
|
|
146
|
+
return { provenTimestamp, uploadedTimestamp, provingTime, ...e };
|
|
147
|
+
}),
|
|
148
|
+
),
|
|
149
|
+
);
|
|
150
|
+
|
|
151
|
+
log(`prover_id, blocks_proven_within_timeout, total_blocks_proven, avg_proving_time`);
|
|
152
|
+
for (const proverId in stats) {
|
|
153
|
+
const blocks = stats[proverId];
|
|
154
|
+
const withinTimeout = blocks.filter(b => b.provingTime <= provingTimeout);
|
|
155
|
+
const uniqueBlocksWithinTimeout = new Set(withinTimeout.map(e => e.checkpointNumber));
|
|
156
|
+
const uniqueBlocks = new Set(blocks.map(e => e.checkpointNumber));
|
|
157
|
+
const avgProvingTime =
|
|
158
|
+
blocks.length === 0 ? 0 : Math.ceil(Number(blocks.reduce((acc, b) => acc + b.provingTime, 0n)) / blocks.length);
|
|
159
|
+
|
|
160
|
+
log(`${proverId}, ${uniqueBlocksWithinTimeout.size}, ${uniqueBlocks.size}, ${avgProvingTime}`);
|
|
161
|
+
}
|
|
162
|
+
return;
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
async function getL2ProofVerifiedEvents(
|
|
166
|
+
startBlock: bigint,
|
|
167
|
+
lastBlockNum: bigint,
|
|
168
|
+
batchSize: bigint,
|
|
169
|
+
debugLog: Logger,
|
|
170
|
+
publicClient: ViemPublicClient,
|
|
171
|
+
rollup: EthAddress,
|
|
172
|
+
) {
|
|
173
|
+
let blockNum = startBlock;
|
|
174
|
+
const events = [];
|
|
175
|
+
while (blockNum <= lastBlockNum) {
|
|
176
|
+
const end = blockNum + batchSize > lastBlockNum + 1n ? lastBlockNum + 1n : blockNum + batchSize;
|
|
177
|
+
const newEvents = await retrieveL2ProofVerifiedEvents(publicClient, rollup, blockNum, end);
|
|
178
|
+
events.push(...newEvents);
|
|
179
|
+
debugLog.verbose(`Got ${newEvents.length} events querying l2 proof verified from block ${blockNum} to ${end}`);
|
|
180
|
+
blockNum += batchSize;
|
|
181
|
+
}
|
|
182
|
+
return events;
|
|
183
|
+
}
|
|
184
|
+
|
|
185
|
+
async function getCheckpointProposedEvents(
|
|
186
|
+
startBlock: bigint,
|
|
187
|
+
lastBlockNum: bigint,
|
|
188
|
+
batchSize: bigint,
|
|
189
|
+
debugLog: Logger,
|
|
190
|
+
publicClient: ViemPublicClient,
|
|
191
|
+
rollup: EthAddress,
|
|
192
|
+
) {
|
|
193
|
+
let blockNum = startBlock;
|
|
194
|
+
const events = [];
|
|
195
|
+
while (blockNum <= lastBlockNum) {
|
|
196
|
+
const end = blockNum + batchSize > lastBlockNum + 1n ? lastBlockNum + 1n : blockNum + batchSize;
|
|
197
|
+
|
|
198
|
+
const newEvents = await publicClient.getLogs({
|
|
199
|
+
address: getAddress(rollup.toString()),
|
|
200
|
+
event: getAbiItem({
|
|
201
|
+
abi: RollupAbi,
|
|
202
|
+
name: 'CheckpointProposed',
|
|
203
|
+
}),
|
|
204
|
+
fromBlock: blockNum,
|
|
205
|
+
toBlock: end,
|
|
206
|
+
});
|
|
207
|
+
|
|
208
|
+
events.push(...newEvents);
|
|
209
|
+
debugLog.verbose(`Got ${newEvents.length} events querying checkpoints submitted from block ${blockNum} to ${end}`);
|
|
210
|
+
blockNum += batchSize;
|
|
211
|
+
}
|
|
212
|
+
return events;
|
|
213
|
+
}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import { RollupAbi } from '@aztec/l1-artifacts/RollupAbi';
|
|
2
|
+
|
|
3
|
+
import { createEthereumChain } from '@aztec-labs/ethereum/chain';
|
|
4
|
+
import { createExtendedL1Client } from '@aztec-labs/ethereum/client';
|
|
5
|
+
import type { LogFn } from '@aztec-labs/foundation/log';
|
|
6
|
+
import { getContract } from 'viem';
|
|
7
|
+
|
|
8
|
+
import type { RollupCommandArgs } from './update_l1_validators.js';
|
|
9
|
+
|
|
10
|
+
export async function triggerSeedSnapshot({
|
|
11
|
+
rpcUrls,
|
|
12
|
+
chainId,
|
|
13
|
+
privateKey,
|
|
14
|
+
mnemonic,
|
|
15
|
+
rollupAddress,
|
|
16
|
+
log,
|
|
17
|
+
}: RollupCommandArgs & { log: LogFn }) {
|
|
18
|
+
const chain = createEthereumChain(rpcUrls, chainId);
|
|
19
|
+
const client = createExtendedL1Client(rpcUrls, privateKey ?? mnemonic!, chain.chainInfo);
|
|
20
|
+
|
|
21
|
+
const rollup = getContract({
|
|
22
|
+
address: rollupAddress.toString(),
|
|
23
|
+
abi: RollupAbi,
|
|
24
|
+
client,
|
|
25
|
+
});
|
|
26
|
+
|
|
27
|
+
log('Triggering seed snapshot for next epoch');
|
|
28
|
+
const txHash = await rollup.write.checkpointRandao();
|
|
29
|
+
log(`Sent! | Seed snapshot setup for next epoch | tx hash: ${txHash}`);
|
|
30
|
+
const receipt = await client.waitForTransactionReceipt({ hash: txHash });
|
|
31
|
+
log(`Done! | Seed snapshot setup for next epoch | tx hash: ${txHash} | status: ${receipt.status}`);
|
|
32
|
+
}
|
|
@@ -0,0 +1,358 @@
|
|
|
1
|
+
import { RollupAbi, StakingAssetHandlerAbi, TestERC20Abi } from '@aztec/l1-artifacts';
|
|
2
|
+
|
|
3
|
+
import { createEthereumChain, isAnvilTestChain } from '@aztec-labs/ethereum/chain';
|
|
4
|
+
import { createExtendedL1Client, getPublicClient } from '@aztec-labs/ethereum/client';
|
|
5
|
+
import { getL1ContractsConfigEnvVars } from '@aztec-labs/ethereum/config';
|
|
6
|
+
import { GSEContract, RollupContract } from '@aztec-labs/ethereum/contracts';
|
|
7
|
+
import { createL1TxUtils } from '@aztec-labs/ethereum/l1-tx-utils';
|
|
8
|
+
import { EthCheatCodes } from '@aztec-labs/ethereum/test';
|
|
9
|
+
import type { EthAddress } from '@aztec-labs/foundation/eth-address';
|
|
10
|
+
import type { LogFn, Logger } from '@aztec-labs/foundation/log';
|
|
11
|
+
import { DateProvider } from '@aztec-labs/foundation/timer';
|
|
12
|
+
import { ZkPassportProofParams } from '@aztec-labs/stdlib/zkpassport';
|
|
13
|
+
import { encodeFunctionData, formatEther, getContract, maxUint256 } from 'viem';
|
|
14
|
+
import { generatePrivateKey, mnemonicToAccount, privateKeyToAccount } from 'viem/accounts';
|
|
15
|
+
|
|
16
|
+
export interface RollupCommandArgs {
|
|
17
|
+
rpcUrls: string[];
|
|
18
|
+
chainId: number;
|
|
19
|
+
privateKey?: string;
|
|
20
|
+
mnemonic?: string;
|
|
21
|
+
rollupAddress: EthAddress;
|
|
22
|
+
withdrawerAddress?: EthAddress;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
export interface StakingAssetHandlerCommandArgs {
|
|
26
|
+
rpcUrls: string[];
|
|
27
|
+
chainId: number;
|
|
28
|
+
privateKey?: string;
|
|
29
|
+
mnemonic?: string;
|
|
30
|
+
stakingAssetHandlerAddress: EthAddress;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
export interface LoggerArgs {
|
|
34
|
+
log: LogFn;
|
|
35
|
+
debugLogger: Logger;
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
export function generateL1Account() {
|
|
39
|
+
const privateKey = generatePrivateKey();
|
|
40
|
+
const account = privateKeyToAccount(privateKey);
|
|
41
|
+
return {
|
|
42
|
+
privateKey,
|
|
43
|
+
address: account.address,
|
|
44
|
+
};
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
export async function addL1Validator({
|
|
48
|
+
rpcUrls,
|
|
49
|
+
chainId,
|
|
50
|
+
privateKey,
|
|
51
|
+
mnemonic,
|
|
52
|
+
attesterAddress,
|
|
53
|
+
withdrawerAddress,
|
|
54
|
+
stakingAssetHandlerAddress,
|
|
55
|
+
proofParams,
|
|
56
|
+
blsSecretKey,
|
|
57
|
+
log,
|
|
58
|
+
debugLogger,
|
|
59
|
+
}: StakingAssetHandlerCommandArgs &
|
|
60
|
+
LoggerArgs & {
|
|
61
|
+
blsSecretKey: bigint; // scalar field element of BN254
|
|
62
|
+
attesterAddress: EthAddress;
|
|
63
|
+
withdrawerAddress: EthAddress;
|
|
64
|
+
proofParams: Buffer;
|
|
65
|
+
}) {
|
|
66
|
+
const dualLog = makeDualLog(log, debugLogger);
|
|
67
|
+
const account = getAccount(privateKey, mnemonic);
|
|
68
|
+
const chain = createEthereumChain(rpcUrls, chainId);
|
|
69
|
+
const l1Client = createExtendedL1Client(rpcUrls, account, chain.chainInfo);
|
|
70
|
+
|
|
71
|
+
const stakingAssetHandler = getContract({
|
|
72
|
+
address: stakingAssetHandlerAddress.toString(),
|
|
73
|
+
abi: StakingAssetHandlerAbi,
|
|
74
|
+
client: l1Client,
|
|
75
|
+
});
|
|
76
|
+
|
|
77
|
+
const rollupAddress = await stakingAssetHandler.read.getRollup();
|
|
78
|
+
dualLog(`Adding validator ${attesterAddress} to rollup ${rollupAddress.toString()}`);
|
|
79
|
+
|
|
80
|
+
const rollup = getContract({
|
|
81
|
+
address: rollupAddress,
|
|
82
|
+
abi: RollupAbi,
|
|
83
|
+
client: l1Client,
|
|
84
|
+
});
|
|
85
|
+
|
|
86
|
+
const gseAddress = await rollup.read.getGSE();
|
|
87
|
+
const gse = new GSEContract(l1Client, gseAddress);
|
|
88
|
+
const registrationTuple = await gse.makeRegistrationTuple(blsSecretKey);
|
|
89
|
+
|
|
90
|
+
const l1TxUtils = createL1TxUtils(l1Client, { logger: debugLogger });
|
|
91
|
+
const proofParamsObj = ZkPassportProofParams.fromBuffer(proofParams);
|
|
92
|
+
|
|
93
|
+
// Step 1: Claim STK tokens from the faucet
|
|
94
|
+
dualLog(`Claiming STK tokens from faucet`);
|
|
95
|
+
const { receipt: claimReceipt } = await l1TxUtils.sendAndMonitorTransaction({
|
|
96
|
+
to: stakingAssetHandlerAddress.toString(),
|
|
97
|
+
data: encodeFunctionData({
|
|
98
|
+
abi: StakingAssetHandlerAbi,
|
|
99
|
+
functionName: 'claim',
|
|
100
|
+
args: [proofParamsObj.toViem()],
|
|
101
|
+
}),
|
|
102
|
+
abi: StakingAssetHandlerAbi,
|
|
103
|
+
});
|
|
104
|
+
dualLog(`Claim transaction hash: ${claimReceipt.transactionHash}`);
|
|
105
|
+
await l1Client.waitForTransactionReceipt({ hash: claimReceipt.transactionHash });
|
|
106
|
+
|
|
107
|
+
// Step 2: Approve the rollup to spend STK tokens
|
|
108
|
+
const stakingAssetAddress = await stakingAssetHandler.read.STAKING_ASSET();
|
|
109
|
+
dualLog(`Approving rollup to spend STK tokens`);
|
|
110
|
+
const { receipt: approveReceipt } = await l1TxUtils.sendAndMonitorTransaction({
|
|
111
|
+
to: stakingAssetAddress,
|
|
112
|
+
data: encodeFunctionData({
|
|
113
|
+
abi: TestERC20Abi,
|
|
114
|
+
functionName: 'approve',
|
|
115
|
+
args: [rollupAddress, maxUint256],
|
|
116
|
+
}),
|
|
117
|
+
abi: TestERC20Abi,
|
|
118
|
+
});
|
|
119
|
+
await l1Client.waitForTransactionReceipt({ hash: approveReceipt.transactionHash });
|
|
120
|
+
|
|
121
|
+
// Step 3: Deposit into the rollup to register as a validator
|
|
122
|
+
dualLog(`Depositing into rollup to register validator`);
|
|
123
|
+
const { receipt } = await l1TxUtils.sendAndMonitorTransaction({
|
|
124
|
+
to: rollupAddress,
|
|
125
|
+
data: encodeFunctionData({
|
|
126
|
+
abi: RollupAbi,
|
|
127
|
+
functionName: 'deposit',
|
|
128
|
+
args: [
|
|
129
|
+
attesterAddress.toString(),
|
|
130
|
+
withdrawerAddress.toString(),
|
|
131
|
+
registrationTuple.publicKeyInG1,
|
|
132
|
+
registrationTuple.publicKeyInG2,
|
|
133
|
+
registrationTuple.proofOfPossession,
|
|
134
|
+
false, // moveWithLatestRollup
|
|
135
|
+
],
|
|
136
|
+
}),
|
|
137
|
+
abi: RollupAbi,
|
|
138
|
+
});
|
|
139
|
+
dualLog(`Deposit transaction hash: ${receipt.transactionHash}`);
|
|
140
|
+
await l1Client.waitForTransactionReceipt({ hash: receipt.transactionHash });
|
|
141
|
+
|
|
142
|
+
if (isAnvilTestChain(chainId)) {
|
|
143
|
+
dualLog(`Funding validator on L1`);
|
|
144
|
+
const cheatCodes = new EthCheatCodes(rpcUrls, new DateProvider(), debugLogger);
|
|
145
|
+
await cheatCodes.setBalance(attesterAddress, 10n ** 20n);
|
|
146
|
+
} else {
|
|
147
|
+
const balance = await l1Client.getBalance({ address: attesterAddress.toString() });
|
|
148
|
+
dualLog(`Validator balance: ${formatEther(balance)} ETH`);
|
|
149
|
+
if (balance === 0n) {
|
|
150
|
+
dualLog(`WARNING: Proposer has no balance. Remember to fund it!`);
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
export async function addL1ValidatorViaRollup({
|
|
156
|
+
rpcUrls,
|
|
157
|
+
chainId,
|
|
158
|
+
privateKey,
|
|
159
|
+
mnemonic,
|
|
160
|
+
attesterAddress,
|
|
161
|
+
withdrawerAddress,
|
|
162
|
+
blsSecretKey,
|
|
163
|
+
moveWithLatestRollup,
|
|
164
|
+
rollupAddress,
|
|
165
|
+
log,
|
|
166
|
+
debugLogger,
|
|
167
|
+
}: RollupCommandArgs &
|
|
168
|
+
LoggerArgs & {
|
|
169
|
+
blsSecretKey: bigint; // scalar field element of BN254
|
|
170
|
+
attesterAddress: EthAddress;
|
|
171
|
+
moveWithLatestRollup: boolean;
|
|
172
|
+
}) {
|
|
173
|
+
const dualLog = makeDualLog(log, debugLogger);
|
|
174
|
+
const account = getAccount(privateKey, mnemonic);
|
|
175
|
+
const chain = createEthereumChain(rpcUrls, chainId);
|
|
176
|
+
const l1Client = createExtendedL1Client(rpcUrls, account, chain.chainInfo);
|
|
177
|
+
|
|
178
|
+
dualLog(`Adding validator ${attesterAddress} to rollup ${rollupAddress.toString()} via direct deposit`);
|
|
179
|
+
|
|
180
|
+
if (!withdrawerAddress) {
|
|
181
|
+
throw new Error(`Withdrawer address required`);
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
const rollup = getContract({
|
|
185
|
+
address: rollupAddress.toString(),
|
|
186
|
+
abi: RollupAbi,
|
|
187
|
+
client: l1Client,
|
|
188
|
+
});
|
|
189
|
+
|
|
190
|
+
const gseAddress = await rollup.read.getGSE();
|
|
191
|
+
|
|
192
|
+
const gse = new GSEContract(l1Client, gseAddress);
|
|
193
|
+
|
|
194
|
+
const registrationTuple = await gse.makeRegistrationTuple(blsSecretKey);
|
|
195
|
+
|
|
196
|
+
const l1TxUtils = createL1TxUtils(l1Client, { logger: debugLogger });
|
|
197
|
+
|
|
198
|
+
const { receipt } = await l1TxUtils.sendAndMonitorTransaction({
|
|
199
|
+
to: rollupAddress.toString(),
|
|
200
|
+
data: encodeFunctionData({
|
|
201
|
+
abi: RollupAbi,
|
|
202
|
+
functionName: 'deposit',
|
|
203
|
+
args: [
|
|
204
|
+
attesterAddress.toString(),
|
|
205
|
+
withdrawerAddress.toString(),
|
|
206
|
+
registrationTuple.publicKeyInG1,
|
|
207
|
+
registrationTuple.publicKeyInG2,
|
|
208
|
+
registrationTuple.proofOfPossession,
|
|
209
|
+
moveWithLatestRollup,
|
|
210
|
+
],
|
|
211
|
+
}),
|
|
212
|
+
abi: StakingAssetHandlerAbi,
|
|
213
|
+
});
|
|
214
|
+
dualLog(`Transaction hash: ${receipt.transactionHash}`);
|
|
215
|
+
await l1Client.waitForTransactionReceipt({ hash: receipt.transactionHash });
|
|
216
|
+
if (isAnvilTestChain(chainId)) {
|
|
217
|
+
dualLog(`Funding validator on L1`);
|
|
218
|
+
const cheatCodes = new EthCheatCodes(rpcUrls, new DateProvider(), debugLogger);
|
|
219
|
+
await cheatCodes.setBalance(attesterAddress, 10n ** 20n);
|
|
220
|
+
} else {
|
|
221
|
+
const balance = await l1Client.getBalance({ address: attesterAddress.toString() });
|
|
222
|
+
dualLog(`Validator balance: ${formatEther(balance)} ETH`);
|
|
223
|
+
if (balance === 0n) {
|
|
224
|
+
dualLog(`WARNING: Proposer has no balance. Remember to fund it!`);
|
|
225
|
+
}
|
|
226
|
+
}
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
export async function removeL1Validator({
|
|
230
|
+
rpcUrls,
|
|
231
|
+
chainId,
|
|
232
|
+
privateKey,
|
|
233
|
+
mnemonic,
|
|
234
|
+
validatorAddress,
|
|
235
|
+
rollupAddress,
|
|
236
|
+
log,
|
|
237
|
+
debugLogger,
|
|
238
|
+
}: RollupCommandArgs & LoggerArgs & { validatorAddress: EthAddress }) {
|
|
239
|
+
const dualLog = makeDualLog(log, debugLogger);
|
|
240
|
+
const account = getAccount(privateKey, mnemonic);
|
|
241
|
+
const chain = createEthereumChain(rpcUrls, chainId);
|
|
242
|
+
const l1Client = createExtendedL1Client(rpcUrls, account, chain.chainInfo);
|
|
243
|
+
const l1TxUtils = createL1TxUtils(l1Client, { logger: debugLogger });
|
|
244
|
+
|
|
245
|
+
dualLog(`Removing validator ${validatorAddress.toString()} from rollup ${rollupAddress.toString()}`);
|
|
246
|
+
const { receipt } = await l1TxUtils.sendAndMonitorTransaction({
|
|
247
|
+
to: rollupAddress.toString(),
|
|
248
|
+
data: encodeFunctionData({
|
|
249
|
+
abi: RollupAbi,
|
|
250
|
+
functionName: 'initiateWithdraw',
|
|
251
|
+
args: [validatorAddress.toString(), validatorAddress.toString()],
|
|
252
|
+
}),
|
|
253
|
+
});
|
|
254
|
+
dualLog(`Transaction hash: ${receipt.transactionHash}`);
|
|
255
|
+
}
|
|
256
|
+
|
|
257
|
+
export async function pruneRollup({
|
|
258
|
+
rpcUrls,
|
|
259
|
+
chainId,
|
|
260
|
+
privateKey,
|
|
261
|
+
mnemonic,
|
|
262
|
+
rollupAddress,
|
|
263
|
+
log,
|
|
264
|
+
debugLogger,
|
|
265
|
+
}: RollupCommandArgs & LoggerArgs) {
|
|
266
|
+
const dualLog = makeDualLog(log, debugLogger);
|
|
267
|
+
const account = getAccount(privateKey, mnemonic);
|
|
268
|
+
const chain = createEthereumChain(rpcUrls, chainId);
|
|
269
|
+
const l1Client = createExtendedL1Client(rpcUrls, account, chain.chainInfo);
|
|
270
|
+
const l1TxUtils = createL1TxUtils(l1Client, { logger: debugLogger });
|
|
271
|
+
|
|
272
|
+
dualLog(`Trying prune`);
|
|
273
|
+
const { receipt } = await l1TxUtils.sendAndMonitorTransaction({
|
|
274
|
+
to: rollupAddress.toString(),
|
|
275
|
+
data: encodeFunctionData({
|
|
276
|
+
abi: RollupAbi,
|
|
277
|
+
functionName: 'prune',
|
|
278
|
+
}),
|
|
279
|
+
});
|
|
280
|
+
dualLog(`Transaction hash: ${receipt.transactionHash}`);
|
|
281
|
+
}
|
|
282
|
+
|
|
283
|
+
export async function fastForwardEpochs({
|
|
284
|
+
rpcUrls,
|
|
285
|
+
chainId,
|
|
286
|
+
rollupAddress,
|
|
287
|
+
numEpochs,
|
|
288
|
+
log,
|
|
289
|
+
debugLogger,
|
|
290
|
+
}: RollupCommandArgs & LoggerArgs & { numEpochs: bigint }) {
|
|
291
|
+
const dualLog = makeDualLog(log, debugLogger);
|
|
292
|
+
const publicClient = getPublicClient({ l1RpcUrls: rpcUrls, l1ChainId: chainId });
|
|
293
|
+
const rollup = getContract({
|
|
294
|
+
address: rollupAddress.toString(),
|
|
295
|
+
abi: RollupAbi,
|
|
296
|
+
client: publicClient,
|
|
297
|
+
});
|
|
298
|
+
|
|
299
|
+
const cheatCodes = new EthCheatCodes(rpcUrls, new DateProvider(), debugLogger);
|
|
300
|
+
const currentSlot = await rollup.read.getCurrentSlot();
|
|
301
|
+
const l2SlotsInEpoch = await rollup.read.getEpochDuration();
|
|
302
|
+
const timestamp = await rollup.read.getTimestampForSlot([currentSlot + l2SlotsInEpoch * numEpochs]);
|
|
303
|
+
dualLog(`Fast forwarding ${numEpochs} epochs to ${timestamp}`);
|
|
304
|
+
try {
|
|
305
|
+
await cheatCodes.warp(Number(timestamp), { resetBlockInterval: true });
|
|
306
|
+
dualLog(`Fast forwarded ${numEpochs} epochs to ${timestamp}`);
|
|
307
|
+
} catch (error) {
|
|
308
|
+
if (error instanceof Error && error.message.includes("is lower than or equal to previous block's timestamp")) {
|
|
309
|
+
dualLog(`Someone else fast forwarded the chain to a point after/equal to the target time`);
|
|
310
|
+
} else {
|
|
311
|
+
// Re-throw other errors
|
|
312
|
+
throw error;
|
|
313
|
+
}
|
|
314
|
+
}
|
|
315
|
+
}
|
|
316
|
+
|
|
317
|
+
export async function debugRollup({ rpcUrls, chainId, rollupAddress, log }: RollupCommandArgs & LoggerArgs) {
|
|
318
|
+
const config = getL1ContractsConfigEnvVars();
|
|
319
|
+
const publicClient = getPublicClient({ l1RpcUrls: rpcUrls, l1ChainId: chainId });
|
|
320
|
+
const rollup = new RollupContract(publicClient, rollupAddress);
|
|
321
|
+
|
|
322
|
+
const pendingNum = await rollup.getCheckpointNumber();
|
|
323
|
+
log(`Pending block num: ${pendingNum}`);
|
|
324
|
+
const provenNum = await rollup.getProvenCheckpointNumber();
|
|
325
|
+
log(`Proven block num: ${provenNum}`);
|
|
326
|
+
const validators = await rollup.getAttesters();
|
|
327
|
+
log(`Validators: ${validators.map(v => v.toString()).join(', ')}`);
|
|
328
|
+
const committee = await rollup.getCurrentEpochCommittee();
|
|
329
|
+
log(`Committee: ${committee?.map(v => v.toString()).join(', ')}`);
|
|
330
|
+
const archive = await rollup.archive();
|
|
331
|
+
log(`Archive: ${archive}`);
|
|
332
|
+
const epochNum = await rollup.getCurrentEpochNumber();
|
|
333
|
+
log(`Current epoch: ${epochNum}`);
|
|
334
|
+
const slot = await rollup.getSlotNumber();
|
|
335
|
+
log(`Current slot: ${slot}`);
|
|
336
|
+
const proposerDuringPrevL1Block = await rollup.getCurrentProposer();
|
|
337
|
+
log(`Proposer during previous L1 block: ${proposerDuringPrevL1Block}`);
|
|
338
|
+
const nextBlockTS = BigInt((await publicClient.getBlock()).timestamp + BigInt(config.ethereumSlotDuration));
|
|
339
|
+
const proposer = await rollup.getProposerAt(nextBlockTS);
|
|
340
|
+
log(`Proposer NOW: ${proposer.toString()}`);
|
|
341
|
+
}
|
|
342
|
+
|
|
343
|
+
function makeDualLog(log: LogFn, debugLogger: Logger) {
|
|
344
|
+
return (msg: string) => {
|
|
345
|
+
log(msg);
|
|
346
|
+
debugLogger.info(msg);
|
|
347
|
+
};
|
|
348
|
+
}
|
|
349
|
+
|
|
350
|
+
function getAccount(privateKey: string | undefined, mnemonic: string | undefined) {
|
|
351
|
+
if (!privateKey && !mnemonic) {
|
|
352
|
+
throw new Error('Either privateKey or mnemonic must be provided to create a wallet client');
|
|
353
|
+
}
|
|
354
|
+
const account = !privateKey
|
|
355
|
+
? mnemonicToAccount(mnemonic!)
|
|
356
|
+
: privateKeyToAccount(`${privateKey.startsWith('0x') ? '' : '0x'}${privateKey}` as `0x${string}`);
|
|
357
|
+
return account;
|
|
358
|
+
}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import type { LogFn } from '@aztec-labs/foundation/log';
|
|
2
|
+
import { createBootnodeENRandPeerId } from '@aztec-labs/p2p/enr';
|
|
3
|
+
|
|
4
|
+
export async function generateEncodedBootnodeENR(
|
|
5
|
+
privateKey: string,
|
|
6
|
+
p2pIp: string,
|
|
7
|
+
p2pPort: number,
|
|
8
|
+
l1ChainId: number,
|
|
9
|
+
log: LogFn,
|
|
10
|
+
) {
|
|
11
|
+
const { enr } = await createBootnodeENRandPeerId(privateKey, p2pIp, p2pPort, l1ChainId);
|
|
12
|
+
log(`ENR: ${enr.encodeTxt()}`);
|
|
13
|
+
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import type { LogFn } from '@aztec-labs/foundation/log';
|
|
2
|
+
import { createSecp256k1PeerId } from '@libp2p/peer-id-factory';
|
|
3
|
+
|
|
4
|
+
export async function generateP2PPrivateKey(log: LogFn) {
|
|
5
|
+
const peerId = await createSecp256k1PeerId();
|
|
6
|
+
const exportedPeerId = Buffer.from(peerId.privateKey!).toString('hex');
|
|
7
|
+
log(`Private key: ${exportedPeerId}`);
|
|
8
|
+
log(`Peer Id: ${peerId}`);
|
|
9
|
+
}
|