Skip to content

Commit

Permalink
fix: bootstrapping devnet (#10396)
Browse files Browse the repository at this point in the history
This PR fixes the last issue in bootstrapping devnet: bridging test
assets and funding the FPC.

It also makes bootstrapping a lot faster by only waiting for the final
tx to make it to the proven chain (all other txs accumulate in blocks on
the pending chain)
  • Loading branch information
alexghr authored Dec 4, 2024
1 parent c2c1744 commit f3c7294
Show file tree
Hide file tree
Showing 8 changed files with 45 additions and 20 deletions.
4 changes: 4 additions & 0 deletions yarn-project/aztec.js/src/wallet/account_wallet.ts
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,10 @@ export class AccountWallet extends BaseWallet {
return this.account.getVersion();
}

override isL1ToL2MessageSynced(l1ToL2Message: Fr): Promise<boolean> {
return this.pxe.isL1ToL2MessageSynced(l1ToL2Message);
}

/**
* Computes an authentication witness from either a message hash or an intent.
*
Expand Down
2 changes: 2 additions & 0 deletions yarn-project/aztec.js/src/wallet/base_wallet.ts
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@ import { type IntentAction, type IntentInnerHash } from '../utils/authwit.js';
export abstract class BaseWallet implements Wallet {
constructor(protected readonly pxe: PXE, private scopes?: AztecAddress[]) {}

abstract isL1ToL2MessageSynced(l1ToL2Message: Fr): Promise<boolean>;

abstract getCompleteAddress(): CompleteAddress;

abstract getChainId(): Fr;
Expand Down
4 changes: 4 additions & 0 deletions yarn-project/aztec.js/src/wallet/signerless_wallet.ts
Original file line number Diff line number Diff line change
Expand Up @@ -42,4 +42,8 @@ export class SignerlessWallet extends BaseWallet {
createAuthWit(_intent: Fr | Buffer | IntentInnerHash | IntentAction): Promise<AuthWitness> {
throw new Error('SignerlessWallet: Method createAuthWit not implemented.');
}

override isL1ToL2MessageSynced(l1ToL2Message: Fr): Promise<boolean> {
return this.pxe.isL1ToL2MessageSynced(l1ToL2Message);
}
}
9 changes: 9 additions & 0 deletions yarn-project/circuit-types/src/interfaces/pxe.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,10 @@ describe('PXESchema', () => {
expect([...tested].sort()).toEqual(all.sort());
});

it('isL1ToL2MessageSynced', async () => {
await context.client.isL1ToL2MessageSynced(Fr.random());
});

it('addAuthWitness', async () => {
await context.client.addAuthWitness(AuthWitness.random());
});
Expand Down Expand Up @@ -326,6 +330,11 @@ class MockPXE implements PXE {
private artifact: ContractArtifact,
private instance: ContractInstanceWithAddress,
) {}

isL1ToL2MessageSynced(_l1ToL2Message: Fr): Promise<boolean> {
return Promise.resolve(false);
}

addAuthWitness(authWitness: AuthWitness): Promise<void> {
expect(authWitness).toBeInstanceOf(AuthWitness);
return Promise.resolve();
Expand Down
8 changes: 8 additions & 0 deletions yarn-project/circuit-types/src/interfaces/pxe.ts
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,13 @@ import { type SyncStatus, SyncStatusSchema } from './sync-status.js';
* is exposed to dapps for interacting with the network on behalf of the user.
*/
export interface PXE {
/**
* Returns whether an L1 to L2 message is synced by archiver and if it's ready to be included in a block.
* @param l1ToL2Message - The L1 to L2 message to check.
* @returns Whether the message is synced and ready to be included in a block.
*/
isL1ToL2MessageSynced(l1ToL2Message: Fr): Promise<boolean>;

/**
* Insert an auth witness for a given message hash. Auth witnesses are used to authorize actions on
* behalf of a user. For instance, a token transfer initiated by a different address may request
Expand Down Expand Up @@ -470,6 +477,7 @@ const PXEInfoSchema = z.object({
}) satisfies ZodFor<PXEInfo>;

export const PXESchema: ApiSchemaFor<PXE> = {
isL1ToL2MessageSynced: z.function().args(schemas.Fr).returns(z.boolean()),
addAuthWitness: z.function().args(AuthWitness.schema).returns(z.void()),
getAuthWitness: z
.function()
Expand Down
32 changes: 13 additions & 19 deletions yarn-project/cli/src/cmds/devnet/bootstrap_network.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { getSchnorrAccount } from '@aztec/accounts/schnorr';
import { BatchCall, type PXE, type Wallet, createCompatibleClient } from '@aztec/aztec.js';
import { BatchCall, type PXE, type Wallet, createCompatibleClient, retryUntil } from '@aztec/aztec.js';
import { L1FeeJuicePortalManager } from '@aztec/aztec.js';
import { type AztecAddress, type EthAddress, FEE_FUNDING_FOR_TESTER_ACCOUNT, Fq, Fr } from '@aztec/circuits.js';
import {
Expand Down Expand Up @@ -34,7 +34,7 @@ export async function bootstrapNetwork(

// setup a one-off account contract
const account = getSchnorrAccount(pxe, Fr.random(), Fq.random(), Fr.random());
const wallet = await account.deploy().getWallet({ proven: true, provenTimeout: 600 });
const wallet = await account.deploy().getWallet();

const l1Clients = createL1Clients(
l1Url,
Expand Down Expand Up @@ -142,17 +142,17 @@ async function deployToken(
const { TokenContract, TokenBridgeContract } = await import('@aztec/noir-contracts.js');
const devCoin = await TokenContract.deploy(wallet, wallet.getAddress(), 'DevCoin', 'DEV', 18)
.send({ universalDeploy: true })
.deployed({ proven: true, provenTimeout: 600 });
.deployed();
const bridge = await TokenBridgeContract.deploy(wallet, devCoin.address, l1Portal)
.send({ universalDeploy: true })
.deployed({ proven: true, provenTimeout: 600 });
.deployed();

await new BatchCall(wallet, [
devCoin.methods.set_minter(bridge.address, true).request(),
devCoin.methods.set_admin(bridge.address).request(),
])
.send()
.wait({ proven: true, provenTimeout: 600 });
.wait();

return {
token: {
Expand Down Expand Up @@ -202,9 +202,7 @@ async function deployFPC(
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore - Importing noir-contracts.js even in devDeps results in a circular dependency error. Need to ignore because this line doesn't cause an error in a dev environment
const { FPCContract } = await import('@aztec/noir-contracts.js');
const fpc = await FPCContract.deploy(wallet, tokenAddress, feeRecipient)
.send({ universalDeploy: true })
.deployed({ proven: true, provenTimeout: 600 });
const fpc = await FPCContract.deploy(wallet, tokenAddress, feeRecipient).send({ universalDeploy: true }).deployed();
const info: ContractDeploymentInfo = {
address: fpc.address,
initHash: fpc.instance.initializationHash,
Expand All @@ -219,7 +217,7 @@ async function deployCounter(wallet: Wallet): Promise<ContractDeploymentInfo> {
const { CounterContract } = await import('@aztec/noir-contracts.js');
const counter = await CounterContract.deploy(wallet, 1, wallet.getAddress(), wallet.getAddress())
.send({ universalDeploy: true })
.deployed({ proven: true, provenTimeout: 600 });
.deployed();
const info: ContractDeploymentInfo = {
address: counter.address,
initHash: counter.instance.initializationHash,
Expand Down Expand Up @@ -253,27 +251,23 @@ async function fundFPC(
);

const amount = FEE_FUNDING_FOR_TESTER_ACCOUNT;
const { claimAmount, claimSecret, messageLeafIndex } = await feeJuicePortal.bridgeTokensPublic(
const { claimAmount, claimSecret, messageLeafIndex, messageHash } = await feeJuicePortal.bridgeTokensPublic(
fpcAddress,
amount,
true,
);

await retryUntil(async () => await wallet.isL1ToL2MessageSynced(Fr.fromString(messageHash)), 'message sync', 600, 1);

const counter = await CounterContract.at(counterAddress, wallet);

// TODO (alexg) remove this once sequencer builds blocks continuously
// advance the chain
await counter.methods
.increment(wallet.getAddress(), wallet.getAddress())
.send()
.wait({ proven: true, provenTimeout: 600 });
await counter.methods
.increment(wallet.getAddress(), wallet.getAddress())
.send()
.wait({ proven: true, provenTimeout: 600 });
await counter.methods.increment(wallet.getAddress(), wallet.getAddress()).send().wait();
await counter.methods.increment(wallet.getAddress(), wallet.getAddress()).send().wait();

await feeJuiceContract.methods
.claim(fpcAddress, claimAmount, claimSecret, messageLeafIndex)
.send()
.wait({ proven: true, provenTimeout: 600 });
.wait({ proven: true });
}
2 changes: 1 addition & 1 deletion yarn-project/ethereum/src/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ function tryExtractEvent<
logger?: DebugLogger,
): TEventType | undefined {
for (const log of logs) {
if (log.address === address) {
if (log.address.toLowerCase() === address.toLowerCase()) {
try {
const decodedEvent = decodeEventLog({ abi, ...log });
if (decodedEvent.eventName === eventName) {
Expand Down
4 changes: 4 additions & 0 deletions yarn-project/pxe/src/pxe_service/pxe_service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -137,6 +137,10 @@ export class PXEService implements PXE {
this.log.info('Stopped Synchronizer');
}

isL1ToL2MessageSynced(l1ToL2Message: Fr): Promise<boolean> {
return this.node.isL1ToL2MessageSynced(l1ToL2Message);
}

/** Returns an estimate of the db size in bytes. */
public estimateDbSize() {
return this.db.estimateSize();
Expand Down

0 comments on commit f3c7294

Please sign in to comment.