@aztec/bot 4.0.0-nightly.20250907 → 4.0.0-nightly.20260107
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/dest/amm_bot.d.ts +9 -9
- package/dest/amm_bot.d.ts.map +1 -1
- package/dest/amm_bot.js +23 -20
- package/dest/base_bot.d.ts +11 -8
- package/dest/base_bot.d.ts.map +1 -1
- package/dest/base_bot.js +18 -18
- package/dest/bot.d.ts +8 -9
- package/dest/bot.d.ts.map +1 -1
- package/dest/bot.js +11 -12
- package/dest/config.d.ts +53 -50
- package/dest/config.d.ts.map +1 -1
- package/dest/config.js +27 -25
- package/dest/factory.d.ts +14 -32
- package/dest/factory.d.ts.map +1 -1
- package/dest/factory.js +137 -115
- package/dest/index.d.ts +2 -1
- package/dest/index.d.ts.map +1 -1
- package/dest/index.js +1 -0
- package/dest/interface.d.ts +2 -2
- package/dest/interface.d.ts.map +1 -1
- package/dest/interface.js +1 -1
- package/dest/rpc.d.ts +1 -1
- package/dest/runner.d.ts +12 -13
- package/dest/runner.d.ts.map +1 -1
- package/dest/runner.js +429 -61
- package/dest/store/bot_store.d.ts +44 -0
- package/dest/store/bot_store.d.ts.map +1 -0
- package/dest/store/bot_store.js +107 -0
- package/dest/store/index.d.ts +2 -0
- package/dest/store/index.d.ts.map +1 -0
- package/dest/store/index.js +1 -0
- package/dest/utils.d.ts +4 -4
- package/dest/utils.d.ts.map +1 -1
- package/dest/utils.js +5 -5
- package/package.json +16 -13
- package/src/amm_bot.ts +39 -31
- package/src/base_bot.ts +24 -22
- package/src/bot.ts +25 -14
- package/src/config.ts +64 -64
- package/src/factory.ts +172 -157
- package/src/index.ts +1 -0
- package/src/interface.ts +1 -1
- package/src/runner.ts +19 -23
- package/src/store/bot_store.ts +141 -0
- package/src/store/index.ts +1 -0
- package/src/utils.ts +10 -5
package/dest/config.js
CHANGED
|
@@ -1,8 +1,9 @@
|
|
|
1
|
-
import { booleanConfigHelper, getConfigFromMappings, getDefaultConfig, numberConfigHelper, optionalNumberConfigHelper, secretFrConfigHelper, secretStringConfigHelper } from '@aztec/foundation/config';
|
|
2
|
-
import { Fr } from '@aztec/foundation/
|
|
1
|
+
import { booleanConfigHelper, getConfigFromMappings, getDefaultConfig, numberConfigHelper, optionalNumberConfigHelper, pickConfigMappings, secretFrConfigHelper, secretStringConfigHelper } from '@aztec/foundation/config';
|
|
2
|
+
import { Fr } from '@aztec/foundation/curves/bn254';
|
|
3
|
+
import { dataConfigMappings } from '@aztec/kv-store/config';
|
|
3
4
|
import { getVKTreeRoot } from '@aztec/noir-protocol-circuits-types/vk-tree';
|
|
4
|
-
import {
|
|
5
|
-
import { schemas } from '@aztec/stdlib/schemas';
|
|
5
|
+
import { protocolContractsHash } from '@aztec/protocol-contracts';
|
|
6
|
+
import { schemas, zodFor } from '@aztec/stdlib/schemas';
|
|
6
7
|
import { z } from 'zod';
|
|
7
8
|
const BotFollowChain = [
|
|
8
9
|
'NONE',
|
|
@@ -14,22 +15,21 @@ export var SupportedTokenContracts = /*#__PURE__*/ function(SupportedTokenContra
|
|
|
14
15
|
SupportedTokenContracts["PrivateTokenContract"] = "PrivateTokenContract";
|
|
15
16
|
return SupportedTokenContracts;
|
|
16
17
|
}({});
|
|
17
|
-
export const BotConfigSchema = z.object({
|
|
18
|
+
export const BotConfigSchema = zodFor()(z.object({
|
|
18
19
|
nodeUrl: z.string().optional(),
|
|
19
20
|
nodeAdminUrl: z.string().optional(),
|
|
20
|
-
pxeUrl: z.string().optional(),
|
|
21
21
|
l1RpcUrls: z.array(z.string()).optional(),
|
|
22
22
|
l1Mnemonic: schemas.SecretValue(z.string()).optional(),
|
|
23
23
|
l1PrivateKey: schemas.SecretValue(z.string()).optional(),
|
|
24
24
|
l1ToL2MessageTimeoutSeconds: z.number(),
|
|
25
25
|
senderPrivateKey: schemas.SecretValue(schemas.Fr).optional(),
|
|
26
26
|
senderSalt: schemas.Fr.optional(),
|
|
27
|
-
recipientEncryptionSecret: schemas.SecretValue(schemas.Fr),
|
|
28
27
|
tokenSalt: schemas.Fr,
|
|
29
28
|
txIntervalSeconds: z.number(),
|
|
30
29
|
privateTransfersPerTx: z.number().int().nonnegative(),
|
|
31
30
|
publicTransfersPerTx: z.number().int().nonnegative(),
|
|
32
31
|
feePaymentMethod: z.literal('fee_juice'),
|
|
32
|
+
baseFeePadding: z.number().int().nonnegative(),
|
|
33
33
|
noStart: z.boolean(),
|
|
34
34
|
txMinedWaitSeconds: z.number(),
|
|
35
35
|
followChain: z.enum(BotFollowChain),
|
|
@@ -40,11 +40,12 @@ export const BotConfigSchema = z.object({
|
|
|
40
40
|
contract: z.nativeEnum(SupportedTokenContracts),
|
|
41
41
|
maxConsecutiveErrors: z.number().int().nonnegative(),
|
|
42
42
|
stopWhenUnhealthy: z.boolean(),
|
|
43
|
-
ammTxs: z.boolean().default(false)
|
|
43
|
+
ammTxs: z.boolean().default(false),
|
|
44
|
+
dataDirectory: z.string().optional(),
|
|
45
|
+
dataStoreMapSizeKb: z.number().optional()
|
|
44
46
|
}).transform((config)=>({
|
|
45
47
|
nodeUrl: undefined,
|
|
46
48
|
nodeAdminUrl: undefined,
|
|
47
|
-
pxeUrl: undefined,
|
|
48
49
|
l1RpcUrls: undefined,
|
|
49
50
|
senderSalt: undefined,
|
|
50
51
|
l2GasLimit: undefined,
|
|
@@ -52,8 +53,10 @@ export const BotConfigSchema = z.object({
|
|
|
52
53
|
l1Mnemonic: undefined,
|
|
53
54
|
l1PrivateKey: undefined,
|
|
54
55
|
senderPrivateKey: undefined,
|
|
56
|
+
dataDirectory: undefined,
|
|
57
|
+
dataStoreMapSizeKb: 1_024 * 1_024,
|
|
55
58
|
...config
|
|
56
|
-
}));
|
|
59
|
+
})));
|
|
57
60
|
export const botConfigMappings = {
|
|
58
61
|
nodeUrl: {
|
|
59
62
|
env: 'AZTEC_NODE_URL',
|
|
@@ -63,10 +66,6 @@ export const botConfigMappings = {
|
|
|
63
66
|
env: 'AZTEC_NODE_ADMIN_URL',
|
|
64
67
|
description: 'The URL to the Aztec node admin API to force-flush txs if configured.'
|
|
65
68
|
},
|
|
66
|
-
pxeUrl: {
|
|
67
|
-
env: 'BOT_PXE_URL',
|
|
68
|
-
description: 'URL to the PXE for sending txs, or undefined if an in-proc PXE is used.'
|
|
69
|
-
},
|
|
70
69
|
l1RpcUrls: {
|
|
71
70
|
env: 'ETHEREUM_HOSTS',
|
|
72
71
|
description: 'URL of the ethereum host.',
|
|
@@ -85,7 +84,7 @@ export const botConfigMappings = {
|
|
|
85
84
|
l1ToL2MessageTimeoutSeconds: {
|
|
86
85
|
env: 'BOT_L1_TO_L2_TIMEOUT_SECONDS',
|
|
87
86
|
description: 'How long to wait for L1 to L2 messages to become available on L2',
|
|
88
|
-
...numberConfigHelper(
|
|
87
|
+
...numberConfigHelper(3600)
|
|
89
88
|
},
|
|
90
89
|
senderPrivateKey: {
|
|
91
90
|
env: 'BOT_PRIVATE_KEY',
|
|
@@ -94,18 +93,12 @@ export const botConfigMappings = {
|
|
|
94
93
|
},
|
|
95
94
|
senderSalt: {
|
|
96
95
|
env: 'BOT_ACCOUNT_SALT',
|
|
97
|
-
description: 'The salt to use to
|
|
96
|
+
description: 'The salt to use to deploy the sender account.',
|
|
98
97
|
parseEnv: (val)=>val ? Fr.fromHexString(val) : undefined
|
|
99
98
|
},
|
|
100
|
-
recipientEncryptionSecret: {
|
|
101
|
-
env: 'BOT_RECIPIENT_ENCRYPTION_SECRET',
|
|
102
|
-
description: 'Encryption secret for a recipient account.',
|
|
103
|
-
printDefault: (sv)=>sv?.getValue(),
|
|
104
|
-
...secretFrConfigHelper(Fr.fromHexString('0xcafecafe'))
|
|
105
|
-
},
|
|
106
99
|
tokenSalt: {
|
|
107
100
|
env: 'BOT_TOKEN_SALT',
|
|
108
|
-
description: '
|
|
101
|
+
description: 'The salt to use to deploy the token contract.',
|
|
109
102
|
parseEnv: (val)=>Fr.fromHexString(val),
|
|
110
103
|
defaultValue: Fr.fromHexString('1')
|
|
111
104
|
},
|
|
@@ -130,6 +123,11 @@ export const botConfigMappings = {
|
|
|
130
123
|
parseEnv: (val)=>val || undefined,
|
|
131
124
|
defaultValue: 'fee_juice'
|
|
132
125
|
},
|
|
126
|
+
baseFeePadding: {
|
|
127
|
+
env: 'BOT_BASE_FEE_PADDING',
|
|
128
|
+
description: 'How much is the bot willing to overpay vs. the current base fee',
|
|
129
|
+
...numberConfigHelper(3)
|
|
130
|
+
},
|
|
133
131
|
noStart: {
|
|
134
132
|
env: 'BOT_NO_START',
|
|
135
133
|
description: 'True to not automatically setup or start the bot on initialization.',
|
|
@@ -196,7 +194,11 @@ export const botConfigMappings = {
|
|
|
196
194
|
env: 'BOT_AMM_TXS',
|
|
197
195
|
description: 'Deploy an AMM and send swaps to it',
|
|
198
196
|
...booleanConfigHelper(false)
|
|
199
|
-
}
|
|
197
|
+
},
|
|
198
|
+
...pickConfigMappings(dataConfigMappings, [
|
|
199
|
+
'dataStoreMapSizeKb',
|
|
200
|
+
'dataDirectory'
|
|
201
|
+
])
|
|
200
202
|
};
|
|
201
203
|
export function getBotConfigFromEnv() {
|
|
202
204
|
return getConfigFromMappings(botConfigMappings);
|
|
@@ -206,7 +208,7 @@ export function getBotDefaultConfig() {
|
|
|
206
208
|
}
|
|
207
209
|
export function getVersions() {
|
|
208
210
|
return {
|
|
209
|
-
|
|
211
|
+
l2ProtocolContractsHash: protocolContractsHash.toString(),
|
|
210
212
|
l2CircuitsVkTreeRoot: getVKTreeRoot().toString()
|
|
211
213
|
};
|
|
212
214
|
}
|
package/dest/factory.d.ts
CHANGED
|
@@ -1,55 +1,41 @@
|
|
|
1
|
-
import { AztecAddress
|
|
1
|
+
import { AztecAddress } from '@aztec/aztec.js/addresses';
|
|
2
2
|
import { AMMContract } from '@aztec/noir-contracts.js/AMM';
|
|
3
3
|
import { PrivateTokenContract } from '@aztec/noir-contracts.js/PrivateToken';
|
|
4
4
|
import { TokenContract } from '@aztec/noir-contracts.js/Token';
|
|
5
5
|
import type { AztecNode, AztecNodeAdmin } from '@aztec/stdlib/interfaces/client';
|
|
6
|
+
import { TestWallet } from '@aztec/test-wallet/server';
|
|
6
7
|
import { type BotConfig } from './config.js';
|
|
8
|
+
import type { BotStore } from './store/index.js';
|
|
7
9
|
export declare class BotFactory {
|
|
8
10
|
private readonly config;
|
|
9
|
-
private
|
|
10
|
-
private
|
|
11
|
-
private
|
|
11
|
+
private readonly wallet;
|
|
12
|
+
private readonly store;
|
|
13
|
+
private readonly aztecNode;
|
|
14
|
+
private readonly aztecNodeAdmin?;
|
|
12
15
|
private log;
|
|
13
|
-
constructor(config: BotConfig,
|
|
14
|
-
pxe?: PXE;
|
|
15
|
-
nodeAdmin?: AztecNodeAdmin;
|
|
16
|
-
node?: AztecNode;
|
|
17
|
-
});
|
|
16
|
+
constructor(config: BotConfig, wallet: TestWallet, store: BotStore, aztecNode: AztecNode, aztecNodeAdmin?: AztecNodeAdmin | undefined);
|
|
18
17
|
/**
|
|
19
18
|
* Initializes a new bot by setting up the sender account, registering the recipient,
|
|
20
19
|
* deploying the token contract, and minting tokens if necessary.
|
|
21
20
|
*/
|
|
22
21
|
setup(): Promise<{
|
|
23
|
-
wallet:
|
|
22
|
+
wallet: TestWallet;
|
|
24
23
|
defaultAccountAddress: AztecAddress;
|
|
25
24
|
token: TokenContract | PrivateTokenContract;
|
|
26
|
-
|
|
25
|
+
node: AztecNode;
|
|
27
26
|
recipient: AztecAddress;
|
|
28
27
|
}>;
|
|
29
28
|
setupAmm(): Promise<{
|
|
30
|
-
wallet:
|
|
29
|
+
wallet: TestWallet;
|
|
31
30
|
defaultAccountAddress: AztecAddress;
|
|
32
31
|
amm: AMMContract;
|
|
33
32
|
token0: TokenContract;
|
|
34
33
|
token1: TokenContract;
|
|
35
|
-
|
|
34
|
+
node: AztecNode;
|
|
36
35
|
}>;
|
|
37
|
-
/**
|
|
38
|
-
* Checks if the sender account contract is initialized, and initializes it if necessary.
|
|
39
|
-
* @returns The sender wallet.
|
|
40
|
-
*/
|
|
41
36
|
private setupAccount;
|
|
42
37
|
private setupAccountWithPrivateKey;
|
|
43
38
|
private setupTestAccount;
|
|
44
|
-
/**
|
|
45
|
-
* Registers the recipient for txs in the pxe.
|
|
46
|
-
*/
|
|
47
|
-
private registerRecipient;
|
|
48
|
-
/**
|
|
49
|
-
* Checks if the token contract is deployed and deploys it if necessary.
|
|
50
|
-
* @param wallet - Wallet to deploy the token contract from.
|
|
51
|
-
* @returns The TokenContract instance.
|
|
52
|
-
*/
|
|
53
39
|
private setupToken;
|
|
54
40
|
/**
|
|
55
41
|
* Checks if the token contract is deployed and deploys it if necessary.
|
|
@@ -60,13 +46,9 @@ export declare class BotFactory {
|
|
|
60
46
|
private setupAmmContract;
|
|
61
47
|
private fundAmm;
|
|
62
48
|
private registerOrDeployContract;
|
|
63
|
-
/**
|
|
64
|
-
* Mints private and public tokens for the sender if their balance is below the minimum.
|
|
65
|
-
* @param token - Token contract.
|
|
66
|
-
*/
|
|
67
49
|
private mintTokens;
|
|
50
|
+
private getOrCreateBridgeClaim;
|
|
68
51
|
private bridgeL1FeeJuice;
|
|
69
52
|
private withNoMinTxsPerBlock;
|
|
70
|
-
private advanceL2Block;
|
|
71
53
|
}
|
|
72
|
-
//# sourceMappingURL=
|
|
54
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZmFjdG9yeS5kLnRzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vc3JjL2ZhY3RvcnkudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBRUEsT0FBTyxFQUFFLFlBQVksRUFBRSxNQUFNLDJCQUEyQixDQUFDO0FBa0J6RCxPQUFPLEVBQUUsV0FBVyxFQUFFLE1BQU0sOEJBQThCLENBQUM7QUFDM0QsT0FBTyxFQUFFLG9CQUFvQixFQUFFLE1BQU0sdUNBQXVDLENBQUM7QUFDN0UsT0FBTyxFQUFFLGFBQWEsRUFBRSxNQUFNLGdDQUFnQyxDQUFDO0FBRy9ELE9BQU8sS0FBSyxFQUFFLFNBQVMsRUFBRSxjQUFjLEVBQUUsTUFBTSxpQ0FBaUMsQ0FBQztBQUVqRixPQUFPLEVBQUUsVUFBVSxFQUFFLE1BQU0sMkJBQTJCLENBQUM7QUFFdkQsT0FBTyxFQUFFLEtBQUssU0FBUyxFQUEyQixNQUFNLGFBQWEsQ0FBQztBQUN0RSxPQUFPLEtBQUssRUFBRSxRQUFRLEVBQUUsTUFBTSxrQkFBa0IsQ0FBQztBQU1qRCxxQkFBYSxVQUFVO0lBSW5CLE9BQU8sQ0FBQyxRQUFRLENBQUMsTUFBTTtJQUN2QixPQUFPLENBQUMsUUFBUSxDQUFDLE1BQU07SUFDdkIsT0FBTyxDQUFDLFFBQVEsQ0FBQyxLQUFLO0lBQ3RCLE9BQU8sQ0FBQyxRQUFRLENBQUMsU0FBUztJQUMxQixPQUFPLENBQUMsUUFBUSxDQUFDLGNBQWMsQ0FBQztJQVBsQyxPQUFPLENBQUMsR0FBRyxDQUF1QjtJQUVsQyxZQUNtQixNQUFNLEVBQUUsU0FBUyxFQUNqQixNQUFNLEVBQUUsVUFBVSxFQUNsQixLQUFLLEVBQUUsUUFBUSxFQUNmLFNBQVMsRUFBRSxTQUFTLEVBQ3BCLGNBQWMsQ0FBQyw0QkFBZ0IsRUFDOUM7SUFFSjs7O09BR0c7SUFDVSxLQUFLLElBQUksT0FBTyxDQUFDO1FBQzVCLE1BQU0sRUFBRSxVQUFVLENBQUM7UUFDbkIscUJBQXFCLEVBQUUsWUFBWSxDQUFDO1FBQ3BDLEtBQUssRUFBRSxhQUFhLEdBQUcsb0JBQW9CLENBQUM7UUFDNUMsSUFBSSxFQUFFLFNBQVMsQ0FBQztRQUNoQixTQUFTLEVBQUUsWUFBWSxDQUFDO0tBQ3pCLENBQUMsQ0FNRDtJQUVZLFFBQVEsSUFBSSxPQUFPLENBQUM7UUFDL0IsTUFBTSxFQUFFLFVBQVUsQ0FBQztRQUNuQixxQkFBcUIsRUFBRSxZQUFZLENBQUM7UUFDcEMsR0FBRyxFQUFFLFdBQVcsQ0FBQztRQUNqQixNQUFNLEVBQUUsYUFBYSxDQUFDO1FBQ3RCLE1BQU0sRUFBRSxhQUFhLENBQUM7UUFDdEIsSUFBSSxFQUFFLFNBQVMsQ0FBQztLQUNqQixDQUFDLENBc0JEO1lBTWEsWUFBWTtZQVdaLDBCQUEwQjtZQXdDMUIsZ0JBQWdCO1lBZ0JoQixVQUFVO0lBdUN4Qjs7OztPQUlHO0lBQ0gsT0FBTyxDQUFDLGtCQUFrQjtZQVlaLGdCQUFnQjtZQW9CaEIsT0FBTztZQThFUCx3QkFBd0I7WUFzQnhCLFVBQVU7WUF3Q1Ysc0JBQXNCO1lBNEJ0QixnQkFBZ0I7WUFnQ2hCLG9CQUFvQjtDQWVuQyJ9
|
package/dest/factory.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"factory.d.ts","sourceRoot":"","sources":["../src/factory.ts"],"names":[],"mappings":"AAEA,OAAO,
|
|
1
|
+
{"version":3,"file":"factory.d.ts","sourceRoot":"","sources":["../src/factory.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,YAAY,EAAE,MAAM,2BAA2B,CAAC;AAkBzD,OAAO,EAAE,WAAW,EAAE,MAAM,8BAA8B,CAAC;AAC3D,OAAO,EAAE,oBAAoB,EAAE,MAAM,uCAAuC,CAAC;AAC7E,OAAO,EAAE,aAAa,EAAE,MAAM,gCAAgC,CAAC;AAG/D,OAAO,KAAK,EAAE,SAAS,EAAE,cAAc,EAAE,MAAM,iCAAiC,CAAC;AAEjF,OAAO,EAAE,UAAU,EAAE,MAAM,2BAA2B,CAAC;AAEvD,OAAO,EAAE,KAAK,SAAS,EAA2B,MAAM,aAAa,CAAC;AACtE,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAMjD,qBAAa,UAAU;IAInB,OAAO,CAAC,QAAQ,CAAC,MAAM;IACvB,OAAO,CAAC,QAAQ,CAAC,MAAM;IACvB,OAAO,CAAC,QAAQ,CAAC,KAAK;IACtB,OAAO,CAAC,QAAQ,CAAC,SAAS;IAC1B,OAAO,CAAC,QAAQ,CAAC,cAAc,CAAC;IAPlC,OAAO,CAAC,GAAG,CAAuB;IAElC,YACmB,MAAM,EAAE,SAAS,EACjB,MAAM,EAAE,UAAU,EAClB,KAAK,EAAE,QAAQ,EACf,SAAS,EAAE,SAAS,EACpB,cAAc,CAAC,4BAAgB,EAC9C;IAEJ;;;OAGG;IACU,KAAK,IAAI,OAAO,CAAC;QAC5B,MAAM,EAAE,UAAU,CAAC;QACnB,qBAAqB,EAAE,YAAY,CAAC;QACpC,KAAK,EAAE,aAAa,GAAG,oBAAoB,CAAC;QAC5C,IAAI,EAAE,SAAS,CAAC;QAChB,SAAS,EAAE,YAAY,CAAC;KACzB,CAAC,CAMD;IAEY,QAAQ,IAAI,OAAO,CAAC;QAC/B,MAAM,EAAE,UAAU,CAAC;QACnB,qBAAqB,EAAE,YAAY,CAAC;QACpC,GAAG,EAAE,WAAW,CAAC;QACjB,MAAM,EAAE,aAAa,CAAC;QACtB,MAAM,EAAE,aAAa,CAAC;QACtB,IAAI,EAAE,SAAS,CAAC;KACjB,CAAC,CAsBD;YAMa,YAAY;YAWZ,0BAA0B;YAwC1B,gBAAgB;YAgBhB,UAAU;IAuCxB;;;;OAIG;IACH,OAAO,CAAC,kBAAkB;YAYZ,gBAAgB;YAoBhB,OAAO;YA8EP,wBAAwB;YAsBxB,UAAU;YAwCV,sBAAsB;YA4BtB,gBAAgB;YAgChB,oBAAoB;CAenC"}
|
package/dest/factory.js
CHANGED
|
@@ -1,83 +1,71 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
1
|
+
import { SchnorrAccountContract } from '@aztec/accounts/schnorr';
|
|
2
|
+
import { getInitialTestAccountsData } from '@aztec/accounts/testing';
|
|
3
|
+
import { AztecAddress } from '@aztec/aztec.js/addresses';
|
|
4
|
+
import { BatchCall } from '@aztec/aztec.js/contracts';
|
|
5
|
+
import { L1FeeJuicePortalManager } from '@aztec/aztec.js/ethereum';
|
|
6
|
+
import { FeeJuicePaymentMethodWithClaim } from '@aztec/aztec.js/fee';
|
|
7
|
+
import { deriveKeys } from '@aztec/aztec.js/keys';
|
|
8
|
+
import { createLogger } from '@aztec/aztec.js/log';
|
|
9
|
+
import { waitForL1ToL2MessageReady } from '@aztec/aztec.js/messaging';
|
|
10
|
+
import { createEthereumChain } from '@aztec/ethereum/chain';
|
|
11
|
+
import { createExtendedL1Client } from '@aztec/ethereum/client';
|
|
12
|
+
import { Fr } from '@aztec/foundation/curves/bn254';
|
|
6
13
|
import { Timer } from '@aztec/foundation/timer';
|
|
7
14
|
import { AMMContract } from '@aztec/noir-contracts.js/AMM';
|
|
8
15
|
import { PrivateTokenContract } from '@aztec/noir-contracts.js/PrivateToken';
|
|
9
16
|
import { TokenContract } from '@aztec/noir-contracts.js/Token';
|
|
17
|
+
import { GasSettings } from '@aztec/stdlib/gas';
|
|
10
18
|
import { deriveSigningKey } from '@aztec/stdlib/keys';
|
|
11
|
-
import {
|
|
12
|
-
import { SupportedTokenContracts, getVersions } from './config.js';
|
|
19
|
+
import { SupportedTokenContracts } from './config.js';
|
|
13
20
|
import { getBalances, getPrivateBalance, isStandardTokenContract } from './utils.js';
|
|
14
21
|
const MINT_BALANCE = 1e12;
|
|
15
22
|
const MIN_BALANCE = 1e3;
|
|
16
23
|
export class BotFactory {
|
|
17
24
|
config;
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
25
|
+
wallet;
|
|
26
|
+
store;
|
|
27
|
+
aztecNode;
|
|
28
|
+
aztecNodeAdmin;
|
|
21
29
|
log;
|
|
22
|
-
constructor(config,
|
|
30
|
+
constructor(config, wallet, store, aztecNode, aztecNodeAdmin){
|
|
23
31
|
this.config = config;
|
|
32
|
+
this.wallet = wallet;
|
|
33
|
+
this.store = store;
|
|
34
|
+
this.aztecNode = aztecNode;
|
|
35
|
+
this.aztecNodeAdmin = aztecNodeAdmin;
|
|
24
36
|
this.log = createLogger('bot');
|
|
25
|
-
if (config.flushSetupTransactions && !dependencies.nodeAdmin) {
|
|
26
|
-
throw new Error(`Either a node admin client or node admin url must be provided if transaction flushing is requested`);
|
|
27
|
-
}
|
|
28
|
-
if (config.senderPrivateKey && config.senderPrivateKey.getValue() && !dependencies.node) {
|
|
29
|
-
throw new Error(`Either a node client or node url must be provided for bridging L1 fee juice to deploy an account with private key`);
|
|
30
|
-
}
|
|
31
|
-
if (!dependencies.pxe && !config.pxeUrl) {
|
|
32
|
-
throw new Error(`Either a PXE client or a PXE URL must be provided`);
|
|
33
|
-
}
|
|
34
|
-
this.node = dependencies.node;
|
|
35
|
-
this.nodeAdmin = dependencies.nodeAdmin;
|
|
36
|
-
if (dependencies.pxe) {
|
|
37
|
-
this.log.info(`Using local PXE`);
|
|
38
|
-
this.pxe = dependencies.pxe;
|
|
39
|
-
return;
|
|
40
|
-
}
|
|
41
|
-
this.log.info(`Using remote PXE at ${config.pxeUrl}`);
|
|
42
|
-
this.pxe = createPXEClient(config.pxeUrl, getVersions(), makeTracedFetch([
|
|
43
|
-
1,
|
|
44
|
-
2,
|
|
45
|
-
3
|
|
46
|
-
], false));
|
|
47
37
|
}
|
|
48
38
|
/**
|
|
49
39
|
* Initializes a new bot by setting up the sender account, registering the recipient,
|
|
50
40
|
* deploying the token contract, and minting tokens if necessary.
|
|
51
41
|
*/ async setup() {
|
|
52
|
-
const recipient = await this.
|
|
53
|
-
const
|
|
54
|
-
const
|
|
55
|
-
const token = await this.setupToken(wallet, defaultAccountAddress);
|
|
42
|
+
const recipient = (await this.wallet.createAccount()).address;
|
|
43
|
+
const defaultAccountAddress = await this.setupAccount();
|
|
44
|
+
const token = await this.setupToken(defaultAccountAddress);
|
|
56
45
|
await this.mintTokens(token, defaultAccountAddress);
|
|
57
46
|
return {
|
|
58
|
-
wallet,
|
|
47
|
+
wallet: this.wallet,
|
|
59
48
|
defaultAccountAddress,
|
|
60
49
|
token,
|
|
61
|
-
|
|
50
|
+
node: this.aztecNode,
|
|
62
51
|
recipient
|
|
63
52
|
};
|
|
64
53
|
}
|
|
65
54
|
async setupAmm() {
|
|
66
|
-
const
|
|
67
|
-
const
|
|
68
|
-
const
|
|
69
|
-
const
|
|
70
|
-
const
|
|
71
|
-
|
|
72
|
-
await this.fundAmm(wallet, wallet.getAddress(), amm, token0, token1, liquidityToken);
|
|
55
|
+
const defaultAccountAddress = await this.setupAccount();
|
|
56
|
+
const token0 = await this.setupTokenContract(defaultAccountAddress, this.config.tokenSalt, 'BotToken0', 'BOT0');
|
|
57
|
+
const token1 = await this.setupTokenContract(defaultAccountAddress, this.config.tokenSalt, 'BotToken1', 'BOT1');
|
|
58
|
+
const liquidityToken = await this.setupTokenContract(defaultAccountAddress, this.config.tokenSalt, 'BotLPToken', 'BOTLP');
|
|
59
|
+
const amm = await this.setupAmmContract(defaultAccountAddress, this.config.tokenSalt, token0, token1, liquidityToken);
|
|
60
|
+
await this.fundAmm(defaultAccountAddress, defaultAccountAddress, amm, token0, token1, liquidityToken);
|
|
73
61
|
this.log.info(`AMM initialized and funded`);
|
|
74
62
|
return {
|
|
75
|
-
wallet,
|
|
63
|
+
wallet: this.wallet,
|
|
76
64
|
defaultAccountAddress,
|
|
77
65
|
amm,
|
|
78
66
|
token0,
|
|
79
67
|
token1,
|
|
80
|
-
|
|
68
|
+
node: this.aztecNode
|
|
81
69
|
};
|
|
82
70
|
}
|
|
83
71
|
/**
|
|
@@ -86,86 +74,98 @@ export class BotFactory {
|
|
|
86
74
|
*/ async setupAccount() {
|
|
87
75
|
const privateKey = this.config.senderPrivateKey?.getValue();
|
|
88
76
|
if (privateKey) {
|
|
77
|
+
this.log.info(`Setting up account with provided private key`);
|
|
89
78
|
return await this.setupAccountWithPrivateKey(privateKey);
|
|
90
79
|
} else {
|
|
80
|
+
this.log.info(`Setting up test account`);
|
|
91
81
|
return await this.setupTestAccount();
|
|
92
82
|
}
|
|
93
83
|
}
|
|
94
|
-
async setupAccountWithPrivateKey(
|
|
84
|
+
async setupAccountWithPrivateKey(secret) {
|
|
95
85
|
const salt = this.config.senderSalt ?? Fr.ONE;
|
|
96
|
-
const signingKey = deriveSigningKey(
|
|
97
|
-
const
|
|
98
|
-
|
|
86
|
+
const signingKey = deriveSigningKey(secret);
|
|
87
|
+
const accountData = {
|
|
88
|
+
secret,
|
|
89
|
+
salt,
|
|
90
|
+
contract: new SchnorrAccountContract(signingKey)
|
|
91
|
+
};
|
|
92
|
+
const accountManager = await this.wallet.createAccount(accountData);
|
|
93
|
+
const isInit = (await this.wallet.getContractMetadata(accountManager.address)).isContractInitialized;
|
|
99
94
|
if (isInit) {
|
|
100
|
-
this.log.info(`Account at ${
|
|
95
|
+
this.log.info(`Account at ${accountManager.address.toString()} already initialized`);
|
|
101
96
|
const timer = new Timer();
|
|
102
|
-
const
|
|
103
|
-
this.log.info(`Account at ${
|
|
104
|
-
|
|
97
|
+
const address = accountManager.address;
|
|
98
|
+
this.log.info(`Account at ${address} registered. duration=${timer.ms()}`);
|
|
99
|
+
await this.store.deleteBridgeClaim(address);
|
|
100
|
+
return address;
|
|
105
101
|
} else {
|
|
106
|
-
const address =
|
|
102
|
+
const address = accountManager.address;
|
|
107
103
|
this.log.info(`Deploying account at ${address}`);
|
|
108
|
-
const claim = await this.
|
|
109
|
-
|
|
110
|
-
const
|
|
111
|
-
const
|
|
112
|
-
const
|
|
104
|
+
const claim = await this.getOrCreateBridgeClaim(address);
|
|
105
|
+
const paymentMethod = new FeeJuicePaymentMethodWithClaim(accountManager.address, claim);
|
|
106
|
+
const deployMethod = await accountManager.getDeployMethod();
|
|
107
|
+
const maxFeesPerGas = (await this.aztecNode.getCurrentBaseFees()).mul(1 + this.config.baseFeePadding);
|
|
108
|
+
const gasSettings = GasSettings.default({
|
|
109
|
+
maxFeesPerGas
|
|
110
|
+
});
|
|
111
|
+
const sentTx = deployMethod.send({
|
|
112
|
+
from: AztecAddress.ZERO,
|
|
113
113
|
fee: {
|
|
114
|
+
gasSettings,
|
|
114
115
|
paymentMethod
|
|
115
116
|
}
|
|
116
117
|
});
|
|
117
118
|
const txHash = await sentTx.getTxHash();
|
|
118
|
-
// docs:end:claim_and_deploy
|
|
119
119
|
this.log.info(`Sent tx for account deployment with hash ${txHash.toString()}`);
|
|
120
120
|
await this.withNoMinTxsPerBlock(()=>sentTx.wait({
|
|
121
121
|
timeout: this.config.txMinedWaitSeconds
|
|
122
122
|
}));
|
|
123
123
|
this.log.info(`Account deployed at ${address}`);
|
|
124
|
-
|
|
124
|
+
// Clean up the consumed bridge claim
|
|
125
|
+
await this.store.deleteBridgeClaim(address);
|
|
126
|
+
return accountManager.address;
|
|
125
127
|
}
|
|
126
128
|
}
|
|
127
129
|
async setupTestAccount() {
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
this.log.info(`Funded test account registered: ${wallet.getAddress()}`);
|
|
137
|
-
}
|
|
138
|
-
return wallet;
|
|
139
|
-
}
|
|
140
|
-
/**
|
|
141
|
-
* Registers the recipient for txs in the pxe.
|
|
142
|
-
*/ async registerRecipient() {
|
|
143
|
-
const recipient = await this.pxe.registerAccount(this.config.recipientEncryptionSecret.getValue(), Fr.ONE);
|
|
144
|
-
return recipient.address;
|
|
130
|
+
const [initialAccountData] = await getInitialTestAccountsData();
|
|
131
|
+
const accountData = {
|
|
132
|
+
secret: initialAccountData.secret,
|
|
133
|
+
salt: initialAccountData.salt,
|
|
134
|
+
contract: new SchnorrAccountContract(initialAccountData.signingKey)
|
|
135
|
+
};
|
|
136
|
+
const accountManager = await this.wallet.createAccount(accountData);
|
|
137
|
+
return accountManager.address;
|
|
145
138
|
}
|
|
146
139
|
/**
|
|
147
140
|
* Checks if the token contract is deployed and deploys it if necessary.
|
|
148
141
|
* @param wallet - Wallet to deploy the token contract from.
|
|
149
142
|
* @returns The TokenContract instance.
|
|
150
|
-
*/ async setupToken(
|
|
143
|
+
*/ async setupToken(sender) {
|
|
151
144
|
let deploy;
|
|
145
|
+
let tokenInstance;
|
|
152
146
|
const deployOpts = {
|
|
153
147
|
from: sender,
|
|
154
148
|
contractAddressSalt: this.config.tokenSalt,
|
|
155
149
|
universalDeploy: true
|
|
156
150
|
};
|
|
157
151
|
if (this.config.contract === SupportedTokenContracts.TokenContract) {
|
|
158
|
-
deploy = TokenContract.deploy(wallet, sender, 'BotToken', 'BOT', 18);
|
|
152
|
+
deploy = TokenContract.deploy(this.wallet, sender, 'BotToken', 'BOT', 18);
|
|
159
153
|
} else if (this.config.contract === SupportedTokenContracts.PrivateTokenContract) {
|
|
160
|
-
|
|
154
|
+
// Generate keys for the contract since PrivateToken uses SinglePrivateMutable which requires keys
|
|
155
|
+
const tokenSecretKey = Fr.random();
|
|
156
|
+
const tokenPublicKeys = (await deriveKeys(tokenSecretKey)).publicKeys;
|
|
157
|
+
deploy = PrivateTokenContract.deployWithPublicKeys(tokenPublicKeys, this.wallet, MINT_BALANCE, sender);
|
|
161
158
|
deployOpts.skipInstancePublication = true;
|
|
162
159
|
deployOpts.skipClassPublication = true;
|
|
163
160
|
deployOpts.skipInitialization = false;
|
|
161
|
+
// Register the contract with the secret key before deployment
|
|
162
|
+
tokenInstance = await deploy.getInstance(deployOpts);
|
|
163
|
+
await this.wallet.registerContract(tokenInstance, PrivateTokenContract.artifact, tokenSecretKey);
|
|
164
164
|
} else {
|
|
165
165
|
throw new Error(`Unsupported token contract type: ${this.config.contract}`);
|
|
166
166
|
}
|
|
167
|
-
const address = (await deploy.getInstance(deployOpts)).address;
|
|
168
|
-
if ((await this.
|
|
167
|
+
const address = tokenInstance?.address ?? (await deploy.getInstance(deployOpts)).address;
|
|
168
|
+
if ((await this.wallet.getContractMetadata(address)).isContractPublished) {
|
|
169
169
|
this.log.info(`Token at ${address.toString()} already deployed`);
|
|
170
170
|
return deploy.register();
|
|
171
171
|
} else {
|
|
@@ -182,22 +182,22 @@ export class BotFactory {
|
|
|
182
182
|
* Checks if the token contract is deployed and deploys it if necessary.
|
|
183
183
|
* @param wallet - Wallet to deploy the token contract from.
|
|
184
184
|
* @returns The TokenContract instance.
|
|
185
|
-
*/ setupTokenContract(
|
|
185
|
+
*/ setupTokenContract(deployer, contractAddressSalt, name, ticker, decimals = 18) {
|
|
186
186
|
const deployOpts = {
|
|
187
187
|
from: deployer,
|
|
188
188
|
contractAddressSalt,
|
|
189
189
|
universalDeploy: true
|
|
190
190
|
};
|
|
191
|
-
const deploy = TokenContract.deploy(wallet, deployer, name, ticker, decimals);
|
|
191
|
+
const deploy = TokenContract.deploy(this.wallet, deployer, name, ticker, decimals);
|
|
192
192
|
return this.registerOrDeployContract('Token - ' + name, deploy, deployOpts);
|
|
193
193
|
}
|
|
194
|
-
async setupAmmContract(
|
|
194
|
+
async setupAmmContract(deployer, contractAddressSalt, token0, token1, lpToken) {
|
|
195
195
|
const deployOpts = {
|
|
196
196
|
from: deployer,
|
|
197
197
|
contractAddressSalt,
|
|
198
198
|
universalDeploy: true
|
|
199
199
|
};
|
|
200
|
-
const deploy = AMMContract.deploy(wallet, token0.address, token1.address, lpToken.address);
|
|
200
|
+
const deploy = AMMContract.deploy(this.wallet, token0.address, token1.address, lpToken.address);
|
|
201
201
|
const amm = await this.registerOrDeployContract('AMM', deploy, deployOpts);
|
|
202
202
|
this.log.info(`AMM deployed at ${amm.address}`);
|
|
203
203
|
const minterTx = lpToken.methods.set_minter(amm.address, true).send({
|
|
@@ -210,7 +210,7 @@ export class BotFactory {
|
|
|
210
210
|
this.log.info(`Liquidity token initialized`);
|
|
211
211
|
return amm;
|
|
212
212
|
}
|
|
213
|
-
async fundAmm(
|
|
213
|
+
async fundAmm(defaultAccountAddress, liquidityProvider, amm, token0, token1, lpToken) {
|
|
214
214
|
const getPrivateBalances = ()=>Promise.all([
|
|
215
215
|
token0.methods.balance_of_private(liquidityProvider).simulate({
|
|
216
216
|
from: liquidityProvider
|
|
@@ -231,15 +231,15 @@ export class BotFactory {
|
|
|
231
231
|
const [t0Bal, t1Bal, lpBal] = await getPrivateBalances();
|
|
232
232
|
this.log.info(`Minting ${MINT_BALANCE} tokens of each BotToken0 and BotToken1. Current private balances of ${liquidityProvider}: token0=${t0Bal}, token1=${t1Bal}, lp=${lpBal}`);
|
|
233
233
|
// Add authwitnesses for the transfers in AMM::add_liquidity function
|
|
234
|
-
const token0Authwit = await wallet.createAuthWit({
|
|
234
|
+
const token0Authwit = await this.wallet.createAuthWit(defaultAccountAddress, {
|
|
235
235
|
caller: amm.address,
|
|
236
|
-
|
|
236
|
+
call: await token0.methods.transfer_to_public_and_prepare_private_balance_increase(liquidityProvider, amm.address, amount0Max, authwitNonce).getFunctionCall()
|
|
237
237
|
});
|
|
238
|
-
const token1Authwit = await wallet.createAuthWit({
|
|
238
|
+
const token1Authwit = await this.wallet.createAuthWit(defaultAccountAddress, {
|
|
239
239
|
caller: amm.address,
|
|
240
|
-
|
|
240
|
+
call: await token1.methods.transfer_to_public_and_prepare_private_balance_increase(liquidityProvider, amm.address, amount1Max, authwitNonce).getFunctionCall()
|
|
241
241
|
});
|
|
242
|
-
const mintTx = new BatchCall(wallet, [
|
|
242
|
+
const mintTx = new BatchCall(this.wallet, [
|
|
243
243
|
token0.methods.mint_to_private(liquidityProvider, MINT_BALANCE),
|
|
244
244
|
token1.methods.mint_to_private(liquidityProvider, MINT_BALANCE)
|
|
245
245
|
]).send({
|
|
@@ -262,11 +262,11 @@ export class BotFactory {
|
|
|
262
262
|
});
|
|
263
263
|
this.log.info(`Liquidity added`);
|
|
264
264
|
const [newT0Bal, newT1Bal, newLPBal] = await getPrivateBalances();
|
|
265
|
-
this.log.info(`Updated private balances of ${
|
|
265
|
+
this.log.info(`Updated private balances of ${defaultAccountAddress} after minting and funding AMM: token0=${newT0Bal}, token1=${newT1Bal}, lp=${newLPBal}`);
|
|
266
266
|
}
|
|
267
267
|
async registerOrDeployContract(name, deploy, deployOpts) {
|
|
268
268
|
const address = (await deploy.getInstance(deployOpts)).address;
|
|
269
|
-
if ((await this.
|
|
269
|
+
if ((await this.wallet.getContractMetadata(address)).isContractPublished) {
|
|
270
270
|
this.log.info(`Contract ${name} at ${address.toString()} already deployed`);
|
|
271
271
|
return deploy.register();
|
|
272
272
|
} else {
|
|
@@ -313,6 +313,32 @@ export class BotFactory {
|
|
|
313
313
|
timeout: this.config.txMinedWaitSeconds
|
|
314
314
|
}));
|
|
315
315
|
}
|
|
316
|
+
/**
|
|
317
|
+
* Gets or creates a bridge claim for the recipient.
|
|
318
|
+
* Checks if a claim already exists in the store and reuses it if valid.
|
|
319
|
+
* Only creates a new bridge if fee juice balance is below threshold.
|
|
320
|
+
*/ async getOrCreateBridgeClaim(recipient) {
|
|
321
|
+
// Check if we have an existing claim in the store
|
|
322
|
+
const existingClaim = await this.store.getBridgeClaim(recipient);
|
|
323
|
+
if (existingClaim) {
|
|
324
|
+
this.log.info(`Found existing bridge claim for ${recipient.toString()}, checking validity...`);
|
|
325
|
+
// Check if the message is ready on L2
|
|
326
|
+
try {
|
|
327
|
+
const messageHash = Fr.fromHexString(existingClaim.claim.messageHash);
|
|
328
|
+
await this.withNoMinTxsPerBlock(()=>waitForL1ToL2MessageReady(this.aztecNode, messageHash, {
|
|
329
|
+
timeoutSeconds: this.config.l1ToL2MessageTimeoutSeconds,
|
|
330
|
+
forPublicConsumption: false
|
|
331
|
+
}));
|
|
332
|
+
return existingClaim.claim;
|
|
333
|
+
} catch (err) {
|
|
334
|
+
this.log.warn(`Failed to verify existing claim, creating new one: ${err}`);
|
|
335
|
+
await this.store.deleteBridgeClaim(recipient);
|
|
336
|
+
}
|
|
337
|
+
}
|
|
338
|
+
const claim = await this.bridgeL1FeeJuice(recipient);
|
|
339
|
+
await this.store.saveBridgeClaim(recipient, claim);
|
|
340
|
+
return claim;
|
|
341
|
+
}
|
|
316
342
|
async bridgeL1FeeJuice(recipient) {
|
|
317
343
|
const l1RpcUrls = this.config.l1RpcUrls;
|
|
318
344
|
if (!l1RpcUrls?.length) {
|
|
@@ -322,40 +348,36 @@ export class BotFactory {
|
|
|
322
348
|
if (!mnemonicOrPrivateKey) {
|
|
323
349
|
throw new Error('Either a mnemonic or private key of an L1 account is required to bridge the fee juice to fund the deployment of the account.');
|
|
324
350
|
}
|
|
325
|
-
const { l1ChainId } = await this.
|
|
351
|
+
const { l1ChainId } = await this.aztecNode.getNodeInfo();
|
|
326
352
|
const chain = createEthereumChain(l1RpcUrls, l1ChainId);
|
|
327
353
|
const extendedClient = createExtendedL1Client(chain.rpcUrls, mnemonicOrPrivateKey, chain.chainInfo);
|
|
328
|
-
const portal = await L1FeeJuicePortalManager.new(this.
|
|
354
|
+
const portal = await L1FeeJuicePortalManager.new(this.aztecNode, extendedClient, this.log);
|
|
329
355
|
const mintAmount = await portal.getTokenManager().getMintAmount();
|
|
330
356
|
const claim = await portal.bridgeTokensPublic(recipient, mintAmount, true);
|
|
331
|
-
|
|
332
|
-
|
|
357
|
+
await this.withNoMinTxsPerBlock(()=>waitForL1ToL2MessageReady(this.aztecNode, Fr.fromHexString(claim.messageHash), {
|
|
358
|
+
timeoutSeconds: this.config.l1ToL2MessageTimeoutSeconds,
|
|
359
|
+
forPublicConsumption: false
|
|
360
|
+
}));
|
|
333
361
|
this.log.info(`Created a claim for ${mintAmount} L1 fee juice to ${recipient}.`, claim);
|
|
334
|
-
// Progress by 2 L2 blocks so that the l1ToL2Message added above will be available to use on L2.
|
|
335
|
-
await this.advanceL2Block();
|
|
336
|
-
await this.advanceL2Block();
|
|
337
362
|
return claim;
|
|
338
363
|
}
|
|
339
364
|
async withNoMinTxsPerBlock(fn) {
|
|
340
|
-
if (!this.
|
|
365
|
+
if (!this.aztecNodeAdmin || !this.config.flushSetupTransactions) {
|
|
366
|
+
this.log.verbose(`No node admin client or flushing not requested (not setting minTxsPerBlock to 0)`);
|
|
341
367
|
return fn();
|
|
342
368
|
}
|
|
343
|
-
const { minTxsPerBlock } = await this.
|
|
344
|
-
|
|
369
|
+
const { minTxsPerBlock } = await this.aztecNodeAdmin.getConfig();
|
|
370
|
+
this.log.warn(`Setting sequencer minTxsPerBlock to 0 from ${minTxsPerBlock} to flush setup transactions`);
|
|
371
|
+
await this.aztecNodeAdmin.setConfig({
|
|
345
372
|
minTxsPerBlock: 0
|
|
346
373
|
});
|
|
347
374
|
try {
|
|
348
375
|
return await fn();
|
|
349
376
|
} finally{
|
|
350
|
-
|
|
377
|
+
this.log.warn(`Restoring sequencer minTxsPerBlock to ${minTxsPerBlock}`);
|
|
378
|
+
await this.aztecNodeAdmin.setConfig({
|
|
351
379
|
minTxsPerBlock
|
|
352
380
|
});
|
|
353
381
|
}
|
|
354
382
|
}
|
|
355
|
-
async advanceL2Block() {
|
|
356
|
-
await this.withNoMinTxsPerBlock(async ()=>{
|
|
357
|
-
const initialBlockNumber = await this.node.getBlockNumber();
|
|
358
|
-
await retryUntil(async ()=>await this.node.getBlockNumber() >= initialBlockNumber + 1);
|
|
359
|
-
});
|
|
360
|
-
}
|
|
361
383
|
}
|