From b21a1cfd593a1f8869533e4a4cce308a2fe801cb Mon Sep 17 00:00:00 2001 From: TucksonDev Date: Thu, 21 Dec 2023 13:04:44 +0000 Subject: [PATCH 01/11] feat: add createRollupFetchTransactionHash --- src/createRollup.unit.test.ts | 22 ++++++++++++ src/createRollupFetchTransactionHash.ts | 47 +++++++++++++++++++++++++ 2 files changed, 69 insertions(+) create mode 100644 src/createRollup.unit.test.ts create mode 100644 src/createRollupFetchTransactionHash.ts diff --git a/src/createRollup.unit.test.ts b/src/createRollup.unit.test.ts new file mode 100644 index 00000000..3474fb38 --- /dev/null +++ b/src/createRollup.unit.test.ts @@ -0,0 +1,22 @@ +import { it, expect } from 'vitest'; +import { createRollupFetchTransactionHash } from './createRollupFetchTransactionHash'; +import { createPublicClient, http } from 'viem'; +import { arbitrum } from 'viem/chains'; + +const publicClient = createPublicClient({ + chain: arbitrum, + transport: http(), +}); + +// Temporary test with https://arbiscan.io/tx/0xc8d7afcb2f7f7dc0883a938db4352813e17b7629850cdc54d8cc2eba7e10b095 +it ('finds the transaction hash that created a specified deployed rollup contract', async () => { + const rollupAddress = '0x846387C3D6001F74170455B1074D01f05eB3067a'; + const expectedTransactionHash = '0xc8d7afcb2f7f7dc0883a938db4352813e17b7629850cdc54d8cc2eba7e10b095'; + + const transactionHash = await createRollupFetchTransactionHash( + rollupAddress, + publicClient + ); + + expect(transactionHash).toEqual(expectedTransactionHash); +}); diff --git a/src/createRollupFetchTransactionHash.ts b/src/createRollupFetchTransactionHash.ts new file mode 100644 index 00000000..30fc3626 --- /dev/null +++ b/src/createRollupFetchTransactionHash.ts @@ -0,0 +1,47 @@ +import { deterministicFactoriesDeploymentEstimatedFees } from './constants'; +import { Address, PublicClient } from 'viem'; +import { AbiEvent } from 'abitype' + +const RollupInitializedEventAbi: AbiEvent = { + anonymous: false, + inputs: [ + { + indexed: false, + internalType: "bytes32", + name: "machineHash", + type: "bytes32", + }, + { + indexed: false, + internalType: "uint256", + name: "chainId", + type: "uint256", + }, + ], + name: "RollupInitialized", + type: "event", +}; + +export async function createRollupFetchTransactionHash( + rollupAddress: Address, + publicClient: PublicClient, +) { + // Find the RollupInitialized event from that Rollup contract + const rollupInitializedEvents = await publicClient.getLogs({ + address: rollupAddress, + event: RollupInitializedEventAbi, + fromBlock: 'earliest', + toBlock: 'latest', + }); + if (!rollupInitializedEvents || rollupInitializedEvents.length <= 0) { + throw new Error(`No RollupInitialized event found for rollup address ${rollupAddress}`); + } + + // Get the transaction hash that emitted that event + const transactionHash = rollupInitializedEvents[0].transactionHash; + if (!transactionHash) { + throw new Error(`No transactionHash found in RollupInitialized event for rollup address ${rollupAddress}`); + } + + return transactionHash; +} From ab77ecacd6c8245ae4dffc9fc6b49c1fb94f862d Mon Sep 17 00:00:00 2001 From: TucksonDev Date: Fri, 22 Dec 2023 11:41:48 +0000 Subject: [PATCH 02/11] Added suggestions --- src/createRollup.unit.test.ts | 11 ++--- src/createRollupFetchTransactionHash.ts | 54 ++++++++++++++----------- 2 files changed, 37 insertions(+), 28 deletions(-) diff --git a/src/createRollup.unit.test.ts b/src/createRollup.unit.test.ts index 3474fb38..2804d631 100644 --- a/src/createRollup.unit.test.ts +++ b/src/createRollup.unit.test.ts @@ -9,14 +9,15 @@ const publicClient = createPublicClient({ }); // Temporary test with https://arbiscan.io/tx/0xc8d7afcb2f7f7dc0883a938db4352813e17b7629850cdc54d8cc2eba7e10b095 -it ('finds the transaction hash that created a specified deployed rollup contract', async () => { +it('finds the transaction hash that created a specified deployed rollup contract', async () => { const rollupAddress = '0x846387C3D6001F74170455B1074D01f05eB3067a'; - const expectedTransactionHash = '0xc8d7afcb2f7f7dc0883a938db4352813e17b7629850cdc54d8cc2eba7e10b095'; + const expectedTransactionHash = + '0xc8d7afcb2f7f7dc0883a938db4352813e17b7629850cdc54d8cc2eba7e10b095'; - const transactionHash = await createRollupFetchTransactionHash( + const transactionHash = await createRollupFetchTransactionHash({ rollupAddress, - publicClient - ); + publicClient, + }); expect(transactionHash).toEqual(expectedTransactionHash); }); diff --git a/src/createRollupFetchTransactionHash.ts b/src/createRollupFetchTransactionHash.ts index 30fc3626..9d6051bc 100644 --- a/src/createRollupFetchTransactionHash.ts +++ b/src/createRollupFetchTransactionHash.ts @@ -1,31 +1,35 @@ -import { deterministicFactoriesDeploymentEstimatedFees } from './constants'; import { Address, PublicClient } from 'viem'; -import { AbiEvent } from 'abitype' +import { AbiEvent } from 'abitype'; + +export type CreateRollupFetchTransactionHashParams = { + rollupAddress: Address; + publicClient: PublicClient; +}; const RollupInitializedEventAbi: AbiEvent = { anonymous: false, inputs: [ - { - indexed: false, - internalType: "bytes32", - name: "machineHash", - type: "bytes32", - }, - { - indexed: false, - internalType: "uint256", - name: "chainId", - type: "uint256", - }, + { + indexed: false, + internalType: 'bytes32', + name: 'machineHash', + type: 'bytes32', + }, + { + indexed: false, + internalType: 'uint256', + name: 'chainId', + type: 'uint256', + }, ], - name: "RollupInitialized", - type: "event", + name: 'RollupInitialized', + type: 'event', }; -export async function createRollupFetchTransactionHash( - rollupAddress: Address, - publicClient: PublicClient, -) { +export async function createRollupFetchTransactionHash({ + rollupAddress, + publicClient, +}: CreateRollupFetchTransactionHashParams) { // Find the RollupInitialized event from that Rollup contract const rollupInitializedEvents = await publicClient.getLogs({ address: rollupAddress, @@ -33,14 +37,18 @@ export async function createRollupFetchTransactionHash( fromBlock: 'earliest', toBlock: 'latest', }); - if (!rollupInitializedEvents || rollupInitializedEvents.length <= 0) { - throw new Error(`No RollupInitialized event found for rollup address ${rollupAddress}`); + if (rollupInitializedEvents.length !== 1) { + throw new Error( + `Expected to find 1 RollupInitialized event for rollup address ${rollupAddress} but found ${rollupInitializedEvents.length}`, + ); } // Get the transaction hash that emitted that event const transactionHash = rollupInitializedEvents[0].transactionHash; if (!transactionHash) { - throw new Error(`No transactionHash found in RollupInitialized event for rollup address ${rollupAddress}`); + throw new Error( + `No transactionHash found in RollupInitialized event for rollup address ${rollupAddress}`, + ); } return transactionHash; From 5d0f5dee80b30bd322212e24a3ffcbe0eeb106f6 Mon Sep 17 00:00:00 2001 From: TucksonDev Date: Fri, 22 Dec 2023 12:16:54 +0000 Subject: [PATCH 03/11] Add test to integration test file --- src/createRollup.integration.test.ts | 36 ++++++++++++++++++++++------ 1 file changed, 29 insertions(+), 7 deletions(-) diff --git a/src/createRollup.integration.test.ts b/src/createRollup.integration.test.ts index 15893e18..167220c3 100644 --- a/src/createRollup.integration.test.ts +++ b/src/createRollup.integration.test.ts @@ -1,5 +1,5 @@ import { it, expect } from 'vitest'; -import { createPublicClient, http, parseGwei, zeroAddress } from 'viem'; +import { Address, createPublicClient, http, parseGwei, zeroAddress } from 'viem'; import { nitroTestnodeL2 } from './chains'; import { generateChainId } from './utils'; @@ -10,17 +10,25 @@ import { createRollupPrepareTransactionRequest } from './createRollupPrepareTran import { createRollupPrepareTransactionReceipt } from './createRollupPrepareTransactionReceipt'; import { getTestPrivateKeyAccount } from './testHelpers'; - -const deployer = getTestPrivateKeyAccount(); - -const batchPoster = deployer.address; -const validators = [deployer.address]; +import { createRollupFetchTransactionHash } from './createRollupFetchTransactionHash'; const publicClient = createPublicClient({ chain: nitroTestnodeL2, transport: http(), }); +// Test inputs +const deployer = getTestPrivateKeyAccount(); +const batchPoster = deployer.address; +const validators = [deployer.address]; + +// Test outputs (information of the created rollup, for next tests) +type CreatedRollupInformation = { + rollupAddress: Address; + createdAtTransactionHash: `0x${string}`; +}; +let createdRollupInformation: CreatedRollupInformation; + it(`successfully deploys core contracts through rollup creator`, async () => { // generate a random chain id const chainId = generateChainId(); @@ -72,5 +80,19 @@ it(`successfully deploys core contracts through rollup creator`, async () => { ); expect(txReceipt.status).toEqual('success'); - expect(() => txReceipt.getCoreContracts()).not.toThrowError(); + const coreContracts = txReceipt.getCoreContracts(); + expect(coreContracts).toBeDefined(); + + // store rollup information for next tests + createdRollupInformation.rollupAddress = coreContracts.rollup; + createdRollupInformation.createdAtTransactionHash = txReceipt.transactionHash; +}); + +it('finds the transaction hash that created a specified deployed rollup contract', async () => { + const transactionHash = await createRollupFetchTransactionHash({ + rollupAddress: createdRollupInformation.rollupAddress, + publicClient, + }); + + expect(transactionHash).toEqual(createdRollupInformation.createdAtTransactionHash); }); From 34ce718f0803d5436f0057770c120b2bc894e13a Mon Sep 17 00:00:00 2001 From: TucksonDev Date: Fri, 22 Dec 2023 12:29:26 +0000 Subject: [PATCH 04/11] Test fix --- src/createRollup.integration.test.ts | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/createRollup.integration.test.ts b/src/createRollup.integration.test.ts index 167220c3..66038102 100644 --- a/src/createRollup.integration.test.ts +++ b/src/createRollup.integration.test.ts @@ -24,10 +24,10 @@ const validators = [deployer.address]; // Test outputs (information of the created rollup, for next tests) type CreatedRollupInformation = { - rollupAddress: Address; - createdAtTransactionHash: `0x${string}`; + rollupAddress?: Address; + createdAtTransactionHash?: `0x${string}`; }; -let createdRollupInformation: CreatedRollupInformation; +const createdRollupInformation: CreatedRollupInformation = {}; it(`successfully deploys core contracts through rollup creator`, async () => { // generate a random chain id @@ -90,7 +90,7 @@ it(`successfully deploys core contracts through rollup creator`, async () => { it('finds the transaction hash that created a specified deployed rollup contract', async () => { const transactionHash = await createRollupFetchTransactionHash({ - rollupAddress: createdRollupInformation.rollupAddress, + rollupAddress: createdRollupInformation.rollupAddress!, publicClient, }); From a93024a09ae4112bb7b7068ae8ee1cf4f64aa8ee Mon Sep 17 00:00:00 2001 From: TucksonDev Date: Fri, 22 Dec 2023 16:15:42 +0000 Subject: [PATCH 05/11] Add test helper and improve integration test --- src/createRollup.integration.test.ts | 115 +++++++++------------------ src/createRollup.unit.test.ts | 23 ------ src/utils/testHelpers.ts | 78 ++++++++++++++++++ 3 files changed, 114 insertions(+), 102 deletions(-) delete mode 100644 src/createRollup.unit.test.ts create mode 100644 src/utils/testHelpers.ts diff --git a/src/createRollup.integration.test.ts b/src/createRollup.integration.test.ts index 66038102..c7d9afdb 100644 --- a/src/createRollup.integration.test.ts +++ b/src/createRollup.integration.test.ts @@ -1,98 +1,55 @@ -import { it, expect } from 'vitest'; -import { Address, createPublicClient, http, parseGwei, zeroAddress } from 'viem'; +import { describe, it, expect } from 'vitest'; +import { createPublicClient, http, parseGwei, zeroAddress } from 'viem'; import { nitroTestnodeL2 } from './chains'; -import { generateChainId } from './utils'; -import { prepareChainConfig } from './prepareChainConfig'; -import { createRollupPrepareConfig } from './createRollupPrepareConfig'; -import { createRollupPrepareTransaction } from './createRollupPrepareTransaction'; -import { createRollupPrepareTransactionRequest } from './createRollupPrepareTransactionRequest'; -import { createRollupPrepareTransactionReceipt } from './createRollupPrepareTransactionReceipt'; - import { getTestPrivateKeyAccount } from './testHelpers'; import { createRollupFetchTransactionHash } from './createRollupFetchTransactionHash'; +import { createTestRollup } from './utils/testHelpers'; +// public client const publicClient = createPublicClient({ chain: nitroTestnodeL2, transport: http(), }); -// Test inputs +// test inputs const deployer = getTestPrivateKeyAccount(); const batchPoster = deployer.address; const validators = [deployer.address]; -// Test outputs (information of the created rollup, for next tests) -type CreatedRollupInformation = { - rollupAddress?: Address; - createdAtTransactionHash?: `0x${string}`; -}; -const createdRollupInformation: CreatedRollupInformation = {}; - -it(`successfully deploys core contracts through rollup creator`, async () => { - // generate a random chain id - const chainId = generateChainId(); - - // create the chain config - const chainConfig = prepareChainConfig({ - chainId, - arbitrum: { InitialChainOwner: deployer.address }, - }); - - const config = createRollupPrepareConfig({ - chainId: BigInt(chainId), - owner: deployer.address, - chainConfig, +describe(`createRollup`, async () => { + // create test rollup + const createRollupInformation = await createTestRollup({ + deployer, + batchPoster, + validators, + publicClient }); - // prepare the transaction for deploying the core contracts - const request = await createRollupPrepareTransactionRequest({ - params: { - config, - batchPoster, - validators, - }, - account: deployer.address, - publicClient, + it(`successfully deploys core contracts through rollup creator`, async () => { + // assert all inputs are correct + const [arg] = createRollupInformation.transaction.getInputs(); + expect(arg.config).toEqual(createRollupInformation.config); + expect(arg.batchPoster).toEqual(batchPoster); + expect(arg.validators).toEqual(validators); + expect(arg.maxDataSize).toEqual(104_857n); + expect(arg.nativeToken).toEqual(zeroAddress); + expect(arg.deployFactoriesToL2).toEqual(true); + expect(arg.maxFeePerGasForRetryables).toEqual(parseGwei('0.1')); + + // assert the transaction executed successfully + expect(createRollupInformation.transactionReceipt.status).toEqual('success'); + + // assert the core contracts were successfully obtained + expect(createRollupInformation.coreContracts).toBeDefined(); }); - - // sign and send the transaction - const txHash = await publicClient.sendRawTransaction({ - serializedTransaction: await deployer.signTransaction(request), + + it('finds the transaction hash that created a specified deployed rollup contract', async () => { + const transactionHash = await createRollupFetchTransactionHash({ + rollupAddress: createRollupInformation.coreContracts.rollup, + publicClient, + }); + + expect(transactionHash).toEqual(createRollupInformation.transactionReceipt.transactionHash); }); - - // get the transaction - const tx = createRollupPrepareTransaction(await publicClient.getTransaction({ hash: txHash })); - - const [arg] = tx.getInputs(); - // assert all inputs are correct - expect(arg.config).toEqual(config); - expect(arg.batchPoster).toEqual(batchPoster); - expect(arg.validators).toEqual(validators); - expect(arg.maxDataSize).toEqual(104_857n); - expect(arg.nativeToken).toEqual(zeroAddress); - expect(arg.deployFactoriesToL2).toEqual(true); - expect(arg.maxFeePerGasForRetryables).toEqual(parseGwei('0.1')); - - // get the transaction receipt after waiting for the transaction to complete - const txReceipt = createRollupPrepareTransactionReceipt( - await publicClient.waitForTransactionReceipt({ hash: txHash }), - ); - - expect(txReceipt.status).toEqual('success'); - const coreContracts = txReceipt.getCoreContracts(); - expect(coreContracts).toBeDefined(); - - // store rollup information for next tests - createdRollupInformation.rollupAddress = coreContracts.rollup; - createdRollupInformation.createdAtTransactionHash = txReceipt.transactionHash; -}); - -it('finds the transaction hash that created a specified deployed rollup contract', async () => { - const transactionHash = await createRollupFetchTransactionHash({ - rollupAddress: createdRollupInformation.rollupAddress!, - publicClient, - }); - - expect(transactionHash).toEqual(createdRollupInformation.createdAtTransactionHash); }); diff --git a/src/createRollup.unit.test.ts b/src/createRollup.unit.test.ts deleted file mode 100644 index 2804d631..00000000 --- a/src/createRollup.unit.test.ts +++ /dev/null @@ -1,23 +0,0 @@ -import { it, expect } from 'vitest'; -import { createRollupFetchTransactionHash } from './createRollupFetchTransactionHash'; -import { createPublicClient, http } from 'viem'; -import { arbitrum } from 'viem/chains'; - -const publicClient = createPublicClient({ - chain: arbitrum, - transport: http(), -}); - -// Temporary test with https://arbiscan.io/tx/0xc8d7afcb2f7f7dc0883a938db4352813e17b7629850cdc54d8cc2eba7e10b095 -it('finds the transaction hash that created a specified deployed rollup contract', async () => { - const rollupAddress = '0x846387C3D6001F74170455B1074D01f05eB3067a'; - const expectedTransactionHash = - '0xc8d7afcb2f7f7dc0883a938db4352813e17b7629850cdc54d8cc2eba7e10b095'; - - const transactionHash = await createRollupFetchTransactionHash({ - rollupAddress, - publicClient, - }); - - expect(transactionHash).toEqual(expectedTransactionHash); -}); diff --git a/src/utils/testHelpers.ts b/src/utils/testHelpers.ts new file mode 100644 index 00000000..c4d4461b --- /dev/null +++ b/src/utils/testHelpers.ts @@ -0,0 +1,78 @@ +import { Address, PrivateKeyAccount, PublicClient } from "viem"; +import { CreateRollupPrepareConfigResult, createRollupPrepareConfig } from "../createRollupPrepareConfig"; +import { createRollupPrepareTransactionRequest } from "../createRollupPrepareTransactionRequest"; +import { prepareChainConfig } from "../prepareChainConfig"; +import { generateChainId } from "./generateChainId"; +import { CreateRollupTransaction, createRollupPrepareTransaction } from "../createRollupPrepareTransaction"; +import { CreateRollupTransactionReceipt, createRollupPrepareTransactionReceipt } from "../createRollupPrepareTransactionReceipt"; +import { CoreContracts } from "../types/CoreContracts"; + +export type CreateTestRollupParams = { + deployer: PrivateKeyAccount; + batchPoster: Address; + validators: Address[]; + publicClient: PublicClient; +}; + +export type CreateTestRollupResult = { + config: CreateRollupPrepareConfigResult; + transaction: CreateRollupTransaction; + transactionReceipt: CreateRollupTransactionReceipt; + coreContracts: CoreContracts; +}; + +export async function createTestRollup({ + deployer, + batchPoster, + validators, + publicClient +}: CreateTestRollupParams): Promise { + // generate a random chain id + const chainId = generateChainId(); + + // create the chain config + const chainConfig = prepareChainConfig({ + chainId, + arbitrum: { InitialChainOwner: deployer.address }, + }); + + const config = createRollupPrepareConfig({ + chainId: BigInt(chainId), + owner: deployer.address, + chainConfig, + }); + + // prepare the transaction for deploying the core contracts + const request = await createRollupPrepareTransactionRequest({ + params: { + config, + batchPoster, + validators, + }, + account: deployer.address, + publicClient, + }); + + // sign and send the transaction + const txHash = await publicClient.sendRawTransaction({ + serializedTransaction: await deployer.signTransaction(request), + }); + + // get the transaction + const tx = createRollupPrepareTransaction(await publicClient.getTransaction({ hash: txHash })); + + // get the transaction receipt after waiting for the transaction to complete + const txReceipt = createRollupPrepareTransactionReceipt( + await publicClient.waitForTransactionReceipt({ hash: txHash }), + ); + + const coreContracts = txReceipt.getCoreContracts(); + + + return { + config, + transaction: tx, + transactionReceipt: txReceipt, + coreContracts, + } +}; From dcb9b61faec45b126e5b8fb80895b11a13147f4b Mon Sep 17 00:00:00 2001 From: TucksonDev Date: Fri, 22 Dec 2023 16:29:46 +0000 Subject: [PATCH 06/11] Format and add deploymentBlockNumber to wagmi config --- src/createRollup.integration.test.ts | 8 ++-- src/utils/testHelpers.ts | 56 ++++++++++++++++------------ wagmi.config.ts | 19 ++++++++++ 3 files changed, 55 insertions(+), 28 deletions(-) diff --git a/src/createRollup.integration.test.ts b/src/createRollup.integration.test.ts index c7d9afdb..978d3359 100644 --- a/src/createRollup.integration.test.ts +++ b/src/createRollup.integration.test.ts @@ -23,7 +23,7 @@ describe(`createRollup`, async () => { deployer, batchPoster, validators, - publicClient + publicClient, }); it(`successfully deploys core contracts through rollup creator`, async () => { @@ -36,20 +36,20 @@ describe(`createRollup`, async () => { expect(arg.nativeToken).toEqual(zeroAddress); expect(arg.deployFactoriesToL2).toEqual(true); expect(arg.maxFeePerGasForRetryables).toEqual(parseGwei('0.1')); - + // assert the transaction executed successfully expect(createRollupInformation.transactionReceipt.status).toEqual('success'); // assert the core contracts were successfully obtained expect(createRollupInformation.coreContracts).toBeDefined(); }); - + it('finds the transaction hash that created a specified deployed rollup contract', async () => { const transactionHash = await createRollupFetchTransactionHash({ rollupAddress: createRollupInformation.coreContracts.rollup, publicClient, }); - + expect(transactionHash).toEqual(createRollupInformation.transactionReceipt.transactionHash); }); }); diff --git a/src/utils/testHelpers.ts b/src/utils/testHelpers.ts index c4d4461b..1857d5de 100644 --- a/src/utils/testHelpers.ts +++ b/src/utils/testHelpers.ts @@ -1,33 +1,42 @@ -import { Address, PrivateKeyAccount, PublicClient } from "viem"; -import { CreateRollupPrepareConfigResult, createRollupPrepareConfig } from "../createRollupPrepareConfig"; -import { createRollupPrepareTransactionRequest } from "../createRollupPrepareTransactionRequest"; -import { prepareChainConfig } from "../prepareChainConfig"; -import { generateChainId } from "./generateChainId"; -import { CreateRollupTransaction, createRollupPrepareTransaction } from "../createRollupPrepareTransaction"; -import { CreateRollupTransactionReceipt, createRollupPrepareTransactionReceipt } from "../createRollupPrepareTransactionReceipt"; -import { CoreContracts } from "../types/CoreContracts"; +import { Address, PrivateKeyAccount, PublicClient } from 'viem'; +import { + CreateRollupPrepareConfigResult, + createRollupPrepareConfig, +} from '../createRollupPrepareConfig'; +import { createRollupPrepareTransactionRequest } from '../createRollupPrepareTransactionRequest'; +import { prepareChainConfig } from '../prepareChainConfig'; +import { generateChainId } from './generateChainId'; +import { + CreateRollupTransaction, + createRollupPrepareTransaction, +} from '../createRollupPrepareTransaction'; +import { + CreateRollupTransactionReceipt, + createRollupPrepareTransactionReceipt, +} from '../createRollupPrepareTransactionReceipt'; +import { CoreContracts } from '../types/CoreContracts'; export type CreateTestRollupParams = { - deployer: PrivateKeyAccount; - batchPoster: Address; - validators: Address[]; - publicClient: PublicClient; + deployer: PrivateKeyAccount; + batchPoster: Address; + validators: Address[]; + publicClient: PublicClient; }; export type CreateTestRollupResult = { - config: CreateRollupPrepareConfigResult; - transaction: CreateRollupTransaction; - transactionReceipt: CreateRollupTransactionReceipt; - coreContracts: CoreContracts; + config: CreateRollupPrepareConfigResult; + transaction: CreateRollupTransaction; + transactionReceipt: CreateRollupTransactionReceipt; + coreContracts: CoreContracts; }; export async function createTestRollup({ - deployer, - batchPoster, - validators, - publicClient + deployer, + batchPoster, + validators, + publicClient, }: CreateTestRollupParams): Promise { - // generate a random chain id + // generate a random chain id const chainId = generateChainId(); // create the chain config @@ -68,11 +77,10 @@ export async function createTestRollup({ const coreContracts = txReceipt.getCoreContracts(); - return { config, transaction: tx, transactionReceipt: txReceipt, coreContracts, - } -}; + }; +} diff --git a/wagmi.config.ts b/wagmi.config.ts index ee9b3546..34ae4c0c 100644 --- a/wagmi.config.ts +++ b/wagmi.config.ts @@ -37,6 +37,7 @@ type ContractConfig = { name: string; version?: string; address: Record | `0x${string}`; + deploymentBlockNumber: Record | bigint; }; const contracts: ContractConfig[] = [ @@ -51,6 +52,14 @@ const contracts: ContractConfig[] = [ [nitroTestnodeL1.id]: '0x596eabe0291d4cdafac7ef53d16c92bf6922b5e0', [nitroTestnodeL2.id]: '0x3BaF9f08bAD68869eEdEa90F2Cc546Bd80F1A651', }, + deploymentBlockNumber: { + // testnet + [sepolia.id]: 4741823n, + [arbitrumSepolia.id]: 654628n, + // local nitro-testnode (on "use-tokenbridge-creator" branch with --tokenbridge --l3node --l3-token-bridge flags) + [nitroTestnodeL1.id]: 0n, + [nitroTestnodeL2.id]: 0n, + }, }, { name: 'TokenBridgeCreator', @@ -63,14 +72,24 @@ const contracts: ContractConfig[] = [ [nitroTestnodeL1.id]: '0x4a2ba922052ba54e29c5417bc979daaf7d5fe4f4', [nitroTestnodeL2.id]: '0x38f35af53bf913c439eab06a367e09d6eb253492', }, + deploymentBlockNumber: { + // testnet + [sepolia.id]: 4840577n, + [arbitrumSepolia.id]: 1633247n, + // local nitro-testnode (on "use-tokenbridge-creator" branch with --tokenbridge --l3node --l3-token-bridge flags) + [nitroTestnodeL1.id]: 0n, + [nitroTestnodeL2.id]: 0n, + }, }, { name: 'ArbOwner', address: '0x0000000000000000000000000000000000000070', + deploymentBlockNumber: 0n, }, { name: 'ArbOwnerPublic', address: '0x000000000000000000000000000000000000006b', + deploymentBlockNumber: 0n, }, ]; From 52b339312a8ad02cd201bfaf0a719ab3dfe681e0 Mon Sep 17 00:00:00 2001 From: TucksonDev Date: Wed, 27 Dec 2023 14:56:27 +0000 Subject: [PATCH 07/11] Export deployment block from wagmi config and use to fetch RollupInitialized events --- src/createRollupFetchTransactionHash.ts | 9 +++++- wagmi.config.ts | 37 +++++++++++++++++++++++++ 2 files changed, 45 insertions(+), 1 deletion(-) diff --git a/src/createRollupFetchTransactionHash.ts b/src/createRollupFetchTransactionHash.ts index 9d6051bc..7f0fe0e6 100644 --- a/src/createRollupFetchTransactionHash.ts +++ b/src/createRollupFetchTransactionHash.ts @@ -1,5 +1,7 @@ import { Address, PublicClient } from 'viem'; import { AbiEvent } from 'abitype'; +import { deploymentBlockNumber } from './generated'; +import { ParentChainId } from './types/ParentChain'; export type CreateRollupFetchTransactionHashParams = { rollupAddress: Address; @@ -31,10 +33,15 @@ export async function createRollupFetchTransactionHash({ publicClient, }: CreateRollupFetchTransactionHashParams) { // Find the RollupInitialized event from that Rollup contract + const chainId = await publicClient.getChainId(); + const fromBlock = (chainId in Object.keys(deploymentBlockNumber.RollupCreator)) + ? deploymentBlockNumber.RollupCreator[chainId as ParentChainId] + : 'earliest'; + const rollupInitializedEvents = await publicClient.getLogs({ address: rollupAddress, event: RollupInitializedEventAbi, - fromBlock: 'earliest', + fromBlock, toBlock: 'latest', }); if (rollupInitializedEvents.length !== 1) { diff --git a/wagmi.config.ts b/wagmi.config.ts index 34ae4c0c..4dcd7f71 100644 --- a/wagmi.config.ts +++ b/wagmi.config.ts @@ -1,4 +1,6 @@ +import { Plugin } from '@wagmi/cli'; import { erc, etherscan } from '@wagmi/cli/plugins'; +import dedent from "dedent"; import dotenv from 'dotenv'; import { ParentChainId } from './src'; @@ -123,6 +125,38 @@ export async function assertContractAbisMatch(contract: ContractConfig) { console.log(`- ${contract.name} ✔`); } +// https://wagmi.sh/cli/plugins#creating-plugins +type DeploymentBlockNumberPluginConfig = { + contracts: ContractConfig[]; +}; +type DeploymentBlockNumberPluginResult = Required> & Omit; + +function deploymentBlockNumberPlugin(config: DeploymentBlockNumberPluginConfig): DeploymentBlockNumberPluginResult { + return { + name: "DeploymentBlockNumber", + async run({ contracts, isTypeScript, outputs }) { + const pluginOutput = dedent` + export const deploymentBlockNumber = { + ${config.contracts.map((contract) => { + return (typeof contract.deploymentBlockNumber === 'bigint') + ? `${contract.name}: ${contract.deploymentBlockNumber}n` + : dedent` + ${contract.name}: { + ${Object.keys(contract.deploymentBlockNumber).map((parentChainId) => { + return `${parentChainId}: ${contract.deploymentBlockNumber[parentChainId]}n`; + })} + }` + })} + } as const + `; + + return { + content: pluginOutput, + }; + } + } +} + export default async function () { console.log(`Checking if contract ABIs match...`); @@ -145,6 +179,9 @@ export default async function () { contracts, cacheDuration: 0, }), + deploymentBlockNumberPlugin({ + contracts + }) ], }; } From fc9e6a7d76710dacd846eb1f3a4ca69d3e6dbb35 Mon Sep 17 00:00:00 2001 From: TucksonDev Date: Wed, 27 Dec 2023 14:58:07 +0000 Subject: [PATCH 08/11] Format --- src/createRollupFetchTransactionHash.ts | 9 +++++---- wagmi.config.ts | 20 +++++++++++--------- 2 files changed, 16 insertions(+), 13 deletions(-) diff --git a/src/createRollupFetchTransactionHash.ts b/src/createRollupFetchTransactionHash.ts index 7f0fe0e6..23537ff6 100644 --- a/src/createRollupFetchTransactionHash.ts +++ b/src/createRollupFetchTransactionHash.ts @@ -34,10 +34,11 @@ export async function createRollupFetchTransactionHash({ }: CreateRollupFetchTransactionHashParams) { // Find the RollupInitialized event from that Rollup contract const chainId = await publicClient.getChainId(); - const fromBlock = (chainId in Object.keys(deploymentBlockNumber.RollupCreator)) - ? deploymentBlockNumber.RollupCreator[chainId as ParentChainId] - : 'earliest'; - + const fromBlock = + chainId in Object.keys(deploymentBlockNumber.RollupCreator) + ? deploymentBlockNumber.RollupCreator[chainId as ParentChainId] + : 'earliest'; + const rollupInitializedEvents = await publicClient.getLogs({ address: rollupAddress, event: RollupInitializedEventAbi, diff --git a/wagmi.config.ts b/wagmi.config.ts index 4dcd7f71..6700e749 100644 --- a/wagmi.config.ts +++ b/wagmi.config.ts @@ -1,6 +1,6 @@ import { Plugin } from '@wagmi/cli'; import { erc, etherscan } from '@wagmi/cli/plugins'; -import dedent from "dedent"; +import dedent from 'dedent'; import dotenv from 'dotenv'; import { ParentChainId } from './src'; @@ -131,21 +131,23 @@ type DeploymentBlockNumberPluginConfig = { }; type DeploymentBlockNumberPluginResult = Required> & Omit; -function deploymentBlockNumberPlugin(config: DeploymentBlockNumberPluginConfig): DeploymentBlockNumberPluginResult { +function deploymentBlockNumberPlugin( + config: DeploymentBlockNumberPluginConfig, +): DeploymentBlockNumberPluginResult { return { - name: "DeploymentBlockNumber", + name: 'DeploymentBlockNumber', async run({ contracts, isTypeScript, outputs }) { const pluginOutput = dedent` export const deploymentBlockNumber = { ${config.contracts.map((contract) => { - return (typeof contract.deploymentBlockNumber === 'bigint') + return typeof contract.deploymentBlockNumber === 'bigint' ? `${contract.name}: ${contract.deploymentBlockNumber}n` : dedent` ${contract.name}: { ${Object.keys(contract.deploymentBlockNumber).map((parentChainId) => { return `${parentChainId}: ${contract.deploymentBlockNumber[parentChainId]}n`; })} - }` + }`; })} } as const `; @@ -153,8 +155,8 @@ function deploymentBlockNumberPlugin(config: DeploymentBlockNumberPluginConfig): return { content: pluginOutput, }; - } - } + }, + }; } export default async function () { @@ -180,8 +182,8 @@ export default async function () { cacheDuration: 0, }), deploymentBlockNumberPlugin({ - contracts - }) + contracts, + }), ], }; } From 4fd4bc6d73da2e31d0a6e7364bfb11976b0b8699 Mon Sep 17 00:00:00 2001 From: TucksonDev Date: Wed, 24 Jan 2024 11:57:48 +0000 Subject: [PATCH 09/11] Move deploymentBlockNumber to createRollupFetchTransactionHash --- src/createRollupFetchTransactionHash.ts | 14 +++++-- wagmi.config.ts | 56 ------------------------- 2 files changed, 11 insertions(+), 59 deletions(-) diff --git a/src/createRollupFetchTransactionHash.ts b/src/createRollupFetchTransactionHash.ts index 23537ff6..b8f3dd04 100644 --- a/src/createRollupFetchTransactionHash.ts +++ b/src/createRollupFetchTransactionHash.ts @@ -1,7 +1,7 @@ import { Address, PublicClient } from 'viem'; import { AbiEvent } from 'abitype'; -import { deploymentBlockNumber } from './generated'; import { ParentChainId } from './types/ParentChain'; +import { sepolia, arbitrumSepolia, nitroTestnodeL1, nitroTestnodeL2 } from './chains'; export type CreateRollupFetchTransactionHashParams = { rollupAddress: Address; @@ -28,6 +28,14 @@ const RollupInitializedEventAbi: AbiEvent = { type: 'event', }; +const earliestRollupCreatorDeploymentBlockNumber = { + // testnet + [sepolia.id]: 4741823n, + [arbitrumSepolia.id]: 654628n, + [nitroTestnodeL1.id]: 0n, + [nitroTestnodeL2.id]: 0n, +}; + export async function createRollupFetchTransactionHash({ rollupAddress, publicClient, @@ -35,8 +43,8 @@ export async function createRollupFetchTransactionHash({ // Find the RollupInitialized event from that Rollup contract const chainId = await publicClient.getChainId(); const fromBlock = - chainId in Object.keys(deploymentBlockNumber.RollupCreator) - ? deploymentBlockNumber.RollupCreator[chainId as ParentChainId] + chainId in Object.keys(earliestRollupCreatorDeploymentBlockNumber) + ? earliestRollupCreatorDeploymentBlockNumber[chainId as ParentChainId] : 'earliest'; const rollupInitializedEvents = await publicClient.getLogs({ diff --git a/wagmi.config.ts b/wagmi.config.ts index 6700e749..6e2216d0 100644 --- a/wagmi.config.ts +++ b/wagmi.config.ts @@ -39,7 +39,6 @@ type ContractConfig = { name: string; version?: string; address: Record | `0x${string}`; - deploymentBlockNumber: Record | bigint; }; const contracts: ContractConfig[] = [ @@ -54,14 +53,6 @@ const contracts: ContractConfig[] = [ [nitroTestnodeL1.id]: '0x596eabe0291d4cdafac7ef53d16c92bf6922b5e0', [nitroTestnodeL2.id]: '0x3BaF9f08bAD68869eEdEa90F2Cc546Bd80F1A651', }, - deploymentBlockNumber: { - // testnet - [sepolia.id]: 4741823n, - [arbitrumSepolia.id]: 654628n, - // local nitro-testnode (on "use-tokenbridge-creator" branch with --tokenbridge --l3node --l3-token-bridge flags) - [nitroTestnodeL1.id]: 0n, - [nitroTestnodeL2.id]: 0n, - }, }, { name: 'TokenBridgeCreator', @@ -74,24 +65,14 @@ const contracts: ContractConfig[] = [ [nitroTestnodeL1.id]: '0x4a2ba922052ba54e29c5417bc979daaf7d5fe4f4', [nitroTestnodeL2.id]: '0x38f35af53bf913c439eab06a367e09d6eb253492', }, - deploymentBlockNumber: { - // testnet - [sepolia.id]: 4840577n, - [arbitrumSepolia.id]: 1633247n, - // local nitro-testnode (on "use-tokenbridge-creator" branch with --tokenbridge --l3node --l3-token-bridge flags) - [nitroTestnodeL1.id]: 0n, - [nitroTestnodeL2.id]: 0n, - }, }, { name: 'ArbOwner', address: '0x0000000000000000000000000000000000000070', - deploymentBlockNumber: 0n, }, { name: 'ArbOwnerPublic', address: '0x000000000000000000000000000000000000006b', - deploymentBlockNumber: 0n, }, ]; @@ -125,40 +106,6 @@ export async function assertContractAbisMatch(contract: ContractConfig) { console.log(`- ${contract.name} ✔`); } -// https://wagmi.sh/cli/plugins#creating-plugins -type DeploymentBlockNumberPluginConfig = { - contracts: ContractConfig[]; -}; -type DeploymentBlockNumberPluginResult = Required> & Omit; - -function deploymentBlockNumberPlugin( - config: DeploymentBlockNumberPluginConfig, -): DeploymentBlockNumberPluginResult { - return { - name: 'DeploymentBlockNumber', - async run({ contracts, isTypeScript, outputs }) { - const pluginOutput = dedent` - export const deploymentBlockNumber = { - ${config.contracts.map((contract) => { - return typeof contract.deploymentBlockNumber === 'bigint' - ? `${contract.name}: ${contract.deploymentBlockNumber}n` - : dedent` - ${contract.name}: { - ${Object.keys(contract.deploymentBlockNumber).map((parentChainId) => { - return `${parentChainId}: ${contract.deploymentBlockNumber[parentChainId]}n`; - })} - }`; - })} - } as const - `; - - return { - content: pluginOutput, - }; - }, - }; -} - export default async function () { console.log(`Checking if contract ABIs match...`); @@ -181,9 +128,6 @@ export default async function () { contracts, cacheDuration: 0, }), - deploymentBlockNumberPlugin({ - contracts, - }), ], }; } From c1f97be1e7fb8c42700f22dead58a740099986a0 Mon Sep 17 00:00:00 2001 From: TucksonDev Date: Wed, 24 Jan 2024 12:01:29 +0000 Subject: [PATCH 10/11] Export new functions at index --- src/createRollup.integration.test.ts | 2 +- src/createRollupFetchTransactionHash.ts | 10 +++++----- src/index.ts | 6 ++++++ 3 files changed, 12 insertions(+), 6 deletions(-) diff --git a/src/createRollup.integration.test.ts b/src/createRollup.integration.test.ts index 978d3359..682a921e 100644 --- a/src/createRollup.integration.test.ts +++ b/src/createRollup.integration.test.ts @@ -46,7 +46,7 @@ describe(`createRollup`, async () => { it('finds the transaction hash that created a specified deployed rollup contract', async () => { const transactionHash = await createRollupFetchTransactionHash({ - rollupAddress: createRollupInformation.coreContracts.rollup, + rollup: createRollupInformation.coreContracts.rollup, publicClient, }); diff --git a/src/createRollupFetchTransactionHash.ts b/src/createRollupFetchTransactionHash.ts index b8f3dd04..1c759a07 100644 --- a/src/createRollupFetchTransactionHash.ts +++ b/src/createRollupFetchTransactionHash.ts @@ -4,7 +4,7 @@ import { ParentChainId } from './types/ParentChain'; import { sepolia, arbitrumSepolia, nitroTestnodeL1, nitroTestnodeL2 } from './chains'; export type CreateRollupFetchTransactionHashParams = { - rollupAddress: Address; + rollup: Address; publicClient: PublicClient; }; @@ -37,7 +37,7 @@ const earliestRollupCreatorDeploymentBlockNumber = { }; export async function createRollupFetchTransactionHash({ - rollupAddress, + rollup, publicClient, }: CreateRollupFetchTransactionHashParams) { // Find the RollupInitialized event from that Rollup contract @@ -48,14 +48,14 @@ export async function createRollupFetchTransactionHash({ : 'earliest'; const rollupInitializedEvents = await publicClient.getLogs({ - address: rollupAddress, + address: rollup, event: RollupInitializedEventAbi, fromBlock, toBlock: 'latest', }); if (rollupInitializedEvents.length !== 1) { throw new Error( - `Expected to find 1 RollupInitialized event for rollup address ${rollupAddress} but found ${rollupInitializedEvents.length}`, + `Expected to find 1 RollupInitialized event for rollup address ${rollup} but found ${rollupInitializedEvents.length}`, ); } @@ -63,7 +63,7 @@ export async function createRollupFetchTransactionHash({ const transactionHash = rollupInitializedEvents[0].transactionHash; if (!transactionHash) { throw new Error( - `No transactionHash found in RollupInitialized event for rollup address ${rollupAddress}`, + `No transactionHash found in RollupInitialized event for rollup address ${rollup}`, ); } diff --git a/src/index.ts b/src/index.ts index 6f5adbd3..2cb41fca 100644 --- a/src/index.ts +++ b/src/index.ts @@ -22,6 +22,10 @@ import { createRollupPrepareTransactionReceipt, CreateRollupTransactionReceipt, } from './createRollupPrepareTransactionReceipt'; +import { + createRollupFetchTransactionHash, + CreateRollupFetchTransactionHashParams, +} from './createRollupFetchTransactionHash'; import { setValidKeyset, SetValidKeysetParams } from './setValidKeyset'; import { setValidKeysetPrepareTransactionRequest, @@ -58,6 +62,8 @@ export { CreateRollupTransaction, createRollupPrepareTransactionReceipt, CreateRollupTransactionReceipt, + createRollupFetchTransactionHash, + CreateRollupFetchTransactionHashParams, setValidKeyset, SetValidKeysetParams, setValidKeysetPrepareTransactionRequest, From 1e5a164ccc9a9bd71cc1e939b48804fdf09c1a28 Mon Sep 17 00:00:00 2001 From: TucksonDev Date: Wed, 24 Jan 2024 12:12:33 +0000 Subject: [PATCH 11/11] Clean wagmi unused imports --- wagmi.config.ts | 2 -- 1 file changed, 2 deletions(-) diff --git a/wagmi.config.ts b/wagmi.config.ts index 6e2216d0..ee9b3546 100644 --- a/wagmi.config.ts +++ b/wagmi.config.ts @@ -1,6 +1,4 @@ -import { Plugin } from '@wagmi/cli'; import { erc, etherscan } from '@wagmi/cli/plugins'; -import dedent from 'dedent'; import dotenv from 'dotenv'; import { ParentChainId } from './src';