diff --git a/typescript/infra/config/environments/mainnet2/middleware/accounts/verification.json b/typescript/infra/config/environments/mainnet2/middleware/accounts/verification.json index d96754dd0..d5aafe437 100644 --- a/typescript/infra/config/environments/mainnet2/middleware/accounts/verification.json +++ b/typescript/infra/config/environments/mainnet2/middleware/accounts/verification.json @@ -17,6 +17,12 @@ "address": "0xFCA9d3C334F12D2Ae30cdEC6283A1928A988BC55", "constructorArguments": "0000000000000000000000000000000000000000000000000000000000000038000000000000000000000000f9a4e3ba5e532906c241310f6832d2ee8d1c5609", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x1d3Bdf44887744007C7C62c85924c445C9e825DE", + "constructorArguments": "00000000000000000000000035231d4c2d8b8adcb5617a638a0c4548684c7c70", + "isProxy": false } ], "avalanche": [ @@ -37,6 +43,12 @@ "address": "0xbAD979697E99d722B4B0295a45D59D8371B7E9bd", "constructorArguments": "000000000000000000000000000000000000000000000000000000000000a86a00000000000000000000000077c509140a45b4b85e1a28f8c21aaeb3ca8788b3", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x88C01B64dCe0032796a1967E2b3447B397c6c7AC", + "constructorArguments": "00000000000000000000000035231d4c2d8b8adcb5617a638a0c4548684c7c70", + "isProxy": false } ], "polygon": [ @@ -57,6 +69,12 @@ "address": "0x4C96a1abc44dc846775CE702C9E9BE821D3b487c", "constructorArguments": "00000000000000000000000000000000000000000000000000000000000000890000000000000000000000004a4d878c41c7f71ecff182f526b7691adc6e4150", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0xCd8ACf2254641bD3Eaa32C1B8D36f0983de8C0E6", + "constructorArguments": "00000000000000000000000035231d4c2d8b8adcb5617a638a0c4548684c7c70", + "isProxy": false } ], "celo": [ @@ -77,6 +95,12 @@ "address": "0x155332Fad14bdE126255E6Ab6A09Fe88D2864294", "constructorArguments": "000000000000000000000000000000000000000000000000000000000000a4ec000000000000000000000000b193ebf06fad5d66492bb41dbbcd202640ae83ff", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x5e8ee6840caa4f367aff1FF28aA36D5B1b836d35", + "constructorArguments": "00000000000000000000000035231d4c2d8b8adcb5617a638a0c4548684c7c70", + "isProxy": false } ], "arbitrum": [ @@ -97,6 +121,12 @@ "address": "0xc67ABC50E7557609077E03e6aeA6834f3E4cf4cE", "constructorArguments": "000000000000000000000000000000000000000000000000000000000000a4b1000000000000000000000000ac2be81884c66e6c05b80c05c907b54c74ea2c49", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0xC1d10a99C382Dd224d7F513C7e0f74D7689071f4", + "constructorArguments": "00000000000000000000000035231d4c2d8b8adcb5617a638a0c4548684c7c70", + "isProxy": false } ], "optimism": [ @@ -117,6 +147,12 @@ "address": "0x5e8ee6840caa4f367aff1FF28aA36D5B1b836d35", "constructorArguments": "000000000000000000000000000000000000000000000000000000000000000a000000000000000000000000652e2f475af7b1154817e09f5408f9011037492a", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x3de63b62BeF9Da290F51f856cA9F3dB4225EDc05", + "constructorArguments": "00000000000000000000000035231d4c2d8b8adcb5617a638a0c4548684c7c70", + "isProxy": false } ], "ethereum": [ @@ -137,6 +173,12 @@ "address": "0x7fd95Df406dDF612597F1B2C52340d7D96aeD071", "constructorArguments": "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000005fd075c2157567f7f80e6cb20ddd75f40905bd87", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x943303Ad7D2B87BB363E0BACC901486337d9B316", + "constructorArguments": "00000000000000000000000035231d4c2d8b8adcb5617a638a0c4548684c7c70", + "isProxy": false } ], "moonbeam": [ @@ -157,6 +199,12 @@ "address": "0x859aD208A717F707bc57FD1fAfEa74311E5a3EeD", "constructorArguments": "00000000000000000000000000000000000000000000000000000000000005040000000000000000000000005b6311e0417cfd3fb10318108897e63777cfe8d7", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x88d346eEc75b6D22428bbaB569b6eBB0bE183c4F", + "constructorArguments": "00000000000000000000000035231d4c2d8b8adcb5617a638a0c4548684c7c70", + "isProxy": false } ], "gnosis": [ @@ -171,6 +219,12 @@ "address": "0x632b4F32d65F7b25B37a27C57dD510f8e4a58Bf9", "constructorArguments": "000000000000000000000000000000000000000000000000000000000000006400000000000000000000000032e77b20bf0cf034eb80ea9dd02de881016b01b3", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x8AB7A6FaC052518A39628497735C855a2Beb515B", + "constructorArguments": "00000000000000000000000035231d4c2d8b8adcb5617a638a0c4548684c7c70", + "isProxy": false } ] } diff --git a/typescript/infra/config/environments/testnet3/middleware/accounts/verification.json b/typescript/infra/config/environments/testnet3/middleware/accounts/verification.json index ae67dc089..cad5000f1 100644 --- a/typescript/infra/config/environments/testnet3/middleware/accounts/verification.json +++ b/typescript/infra/config/environments/testnet3/middleware/accounts/verification.json @@ -17,6 +17,12 @@ "address": "0x06d237b73a1f353B14475f15012e4309580C5395", "constructorArguments": "000000000000000000000000000000000000000000000000000000000000aef3000000000000000000000000db91d575f17d8aaf1afec0eadbd5ac9e5cef4ad0", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x0aA320a1bD450152B4C500613335CeBA4f6073cF", + "constructorArguments": "000000000000000000000000cc737a94fecaec165abcf12ded095bb13f037685", + "isProxy": false } ], "fuji": [ @@ -37,6 +43,12 @@ "address": "0x7D7D885ebeb3B46340E9CF9bD0cA847492C16D4a", "constructorArguments": "000000000000000000000000000000000000000000000000000000000000a869000000000000000000000000f82b58bf348a6cea6e19413e9de040db1a363128", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x333C9A8c70Ea4F0498Fb58bEe40DEa40e63a9962", + "constructorArguments": "000000000000000000000000cc737a94fecaec165abcf12ded095bb13f037685", + "isProxy": false } ], "mumbai": [ @@ -57,6 +69,12 @@ "address": "0x01E05434f5D5e8B0BA6a0d05AdDeD777Cc1ac8c3", "constructorArguments": "00000000000000000000000000000000000000000000000000000000000138810000000000000000000000006a9ced0e13e738517558aa283da0e93e5904d49b", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x40c2d6cA6F5A8857705C128b2c1A5f0Ae20880dc", + "constructorArguments": "000000000000000000000000cc737a94fecaec165abcf12ded095bb13f037685", + "isProxy": false } ], "bsctestnet": [ @@ -77,6 +95,12 @@ "address": "0x91B08a1b96d6ac153eB102Bd9Eb9F2D416d449A1", "constructorArguments": "0000000000000000000000000000000000000000000000000000000000000061000000000000000000000000951c74d83a85833b53a448caab7397bd3fa6cfb2", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x9034f60Dec10cFa162369444081685F542d0C24D", + "constructorArguments": "000000000000000000000000cc737a94fecaec165abcf12ded095bb13f037685", + "isProxy": false } ], "goerli": [ @@ -97,6 +121,12 @@ "address": "0xA748586f78dD2a4A90b02aD72ddc014Cc05C19b1", "constructorArguments": "0000000000000000000000000000000000000000000000000000000000000005000000000000000000000000cb0ba89f564e31180a101df54b7971206e03ee9b", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x70835F3C2845394842DEA9f40cbe8087b2cE5712", + "constructorArguments": "000000000000000000000000cc737a94fecaec165abcf12ded095bb13f037685", + "isProxy": false } ], "moonbasealpha": [ @@ -117,6 +147,12 @@ "address": "0x443f8614728327Ce0cAb864DD463Fe2702b57597", "constructorArguments": "0000000000000000000000000000000000000000000000000000000000000507000000000000000000000000209ccdbe13bb913104117b1d6f7801684e98fa1f", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0xD699ff94f3FFd60A3a09bBff96181325B6C73FB8", + "constructorArguments": "000000000000000000000000cc737a94fecaec165abcf12ded095bb13f037685", + "isProxy": false } ], "optimismgoerli": [ @@ -137,6 +173,12 @@ "address": "0x860EDf9C38875ad7444BD6e6331866450c9589e4", "constructorArguments": "00000000000000000000000000000000000000000000000000000000000001a400000000000000000000000012ebd8cb561c68b587c392e0c5405b9866fd5820", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x82F5a960a4e4Cc0614253e4977bb3BE10344a30C", + "constructorArguments": "000000000000000000000000cc737a94fecaec165abcf12ded095bb13f037685", + "isProxy": false } ], "arbitrumgoerli": [ @@ -157,6 +199,12 @@ "address": "0x759c4Eb4575B651a9f0Fb46653dd7B2F32fD7310", "constructorArguments": "0000000000000000000000000000000000000000000000000000000000066eed0000000000000000000000004266d8dd66d8eb3934c8942968d1e54214d072d3", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0xA8978fdB093b1C5b892291A36e8527b34B749d6f", + "constructorArguments": "000000000000000000000000cc737a94fecaec165abcf12ded095bb13f037685", + "isProxy": false } ], "sepolia": [ @@ -171,6 +219,12 @@ "address": "0xe0B988062A0C6492177d64823Ab95a9c256c2a5F", "constructorArguments": "0000000000000000000000000000000000000000000000000000000000aa36a7000000000000000000000000b057fb841027a8554521dccdec3c3474cac99ab5", "isProxy": false + }, + { + "name": "InterchainAccountIsm", + "address": "0x7483faD0Bc297667664A43A064bA7c9911659f57", + "constructorArguments": "000000000000000000000000cc737a94fecaec165abcf12ded095bb13f037685", + "isProxy": false } ] } diff --git a/typescript/infra/scripts/check-deploy.ts b/typescript/infra/scripts/check-deploy.ts index ecb5c3067..e5ed29a13 100644 --- a/typescript/infra/scripts/check-deploy.ts +++ b/typescript/infra/scripts/check-deploy.ts @@ -14,8 +14,7 @@ import { deployEnvToSdkEnv } from '../src/config/environment'; import { HyperlaneAppGovernor } from '../src/govern/HyperlaneAppGovernor'; import { HyperlaneCoreGovernor } from '../src/govern/HyperlaneCoreGovernor'; import { HyperlaneIgpGovernor } from '../src/govern/HyperlaneIgpGovernor'; -import { InterchainAccountGovernor } from '../src/govern/InterchainAccountGovernor'; -import { InterchainQueryGovernor } from '../src/govern/InterchainQueryGovernor'; +import { ProxiedRouterGovernor } from '../src/govern/ProxiedRouterGovernor'; import { impersonateAccount, useLocalProvider } from '../src/utils/fork'; import { @@ -60,15 +59,23 @@ async function check() { const checker = new HyperlaneIgpChecker(multiProvider, igp, config.igp); governor = new HyperlaneIgpGovernor(checker, config.owners); } else if (module === Modules.INTERCHAIN_ACCOUNTS) { - const config = await getRouterConfig(environment, multiProvider); + const routerConfig = await getRouterConfig(environment, multiProvider); const ica = InterchainAccount.fromEnvironment(env, multiProvider); - const checker = new InterchainAccountChecker(multiProvider, ica, config); - governor = new InterchainAccountGovernor(checker, config.owners); + const checker = new InterchainAccountChecker( + multiProvider, + ica, + routerConfig, + ); + governor = new ProxiedRouterGovernor(checker, config.owners); } else if (module === Modules.INTERCHAIN_QUERY_SYSTEM) { - const config = await getRouterConfig(environment, multiProvider); + const routerConfig = await getRouterConfig(environment, multiProvider); const iqs = InterchainQuery.fromEnvironment(env, multiProvider); - const checker = new InterchainQueryChecker(multiProvider, iqs, config); - governor = new InterchainQueryGovernor(checker, config.owners); + const checker = new InterchainQueryChecker( + multiProvider, + iqs, + routerConfig, + ); + governor = new ProxiedRouterGovernor(checker, config.owners); } else { console.log(`Skipping ${module}, checker or governor unimplemented`); return; diff --git a/typescript/infra/src/govern/HyperlaneAppGovernor.ts b/typescript/infra/src/govern/HyperlaneAppGovernor.ts index adf4e98d6..4a8313433 100644 --- a/typescript/infra/src/govern/HyperlaneAppGovernor.ts +++ b/typescript/infra/src/govern/HyperlaneAppGovernor.ts @@ -148,7 +148,7 @@ export abstract class HyperlaneAppGovernor< const signer = multiProvider.getSigner(chain); const signerAddress = await signer.getAddress(); - const canUseSubmissionType = async ( + const transactionSucceedsFromSender = async ( submitterAddress: types.Address, ): Promise => { try { @@ -158,7 +158,7 @@ export abstract class HyperlaneAppGovernor< return false; }; - if (await canUseSubmissionType(signerAddress)) { + if (await transactionSucceedsFromSender(signerAddress)) { return SubmissionType.SIGNER; } @@ -179,11 +179,11 @@ export abstract class HyperlaneAppGovernor< ), ); } - // 2b. Check if calling from the owner/safeAddress will succeed. if ( - this.canPropose[chain].get(safeAddress) && - (await canUseSubmissionType(safeAddress)) + (this.canPropose[chain].get(safeAddress) && + (await transactionSucceedsFromSender(safeAddress))) || + chain === 'moonbeam' ) { return SubmissionType.SAFE; } @@ -198,7 +198,7 @@ export abstract class HyperlaneAppGovernor< 'transferOwnership', [violation.expected], ), - description: `Transfer ownership of ${violation.contract.address} to ${violation.expected}`, + description: `Transfer ownership of ${violation.name} at ${violation.contract.address} to ${violation.expected}`, }); } } diff --git a/typescript/infra/src/govern/InterchainAccountGovernor.ts b/typescript/infra/src/govern/InterchainAccountGovernor.ts deleted file mode 100644 index 0dd7a603d..000000000 --- a/typescript/infra/src/govern/InterchainAccountGovernor.ts +++ /dev/null @@ -1,25 +0,0 @@ -import { - ChainMap, - InterchainAccount, - InterchainAccountChecker, - InterchainAccountConfig, -} from '@hyperlane-xyz/sdk'; -import { types } from '@hyperlane-xyz/utils'; - -import { HyperlaneAppGovernor } from './HyperlaneAppGovernor'; - -export class InterchainAccountGovernor extends HyperlaneAppGovernor< - InterchainAccount, - InterchainAccountConfig -> { - constructor( - checker: InterchainAccountChecker, - owners: ChainMap, - ) { - super(checker, owners); - } - - protected async mapViolationsToCalls() { - throw new Error('governor not implemented for account middleware'); - } -} diff --git a/typescript/infra/src/govern/InterchainQueryGovernor.ts b/typescript/infra/src/govern/InterchainQueryGovernor.ts deleted file mode 100644 index de5b625f2..000000000 --- a/typescript/infra/src/govern/InterchainQueryGovernor.ts +++ /dev/null @@ -1,25 +0,0 @@ -import { - ChainMap, - InterchainQuery, - InterchainQueryChecker, - InterchainQueryConfig, -} from '@hyperlane-xyz/sdk'; -import { types } from '@hyperlane-xyz/utils'; - -import { HyperlaneAppGovernor } from './HyperlaneAppGovernor'; - -export class InterchainQueryGovernor extends HyperlaneAppGovernor< - InterchainQuery, - InterchainQueryConfig -> { - constructor( - checker: InterchainQueryChecker, - owners: ChainMap, - ) { - super(checker, owners); - } - - protected async mapViolationsToCalls() { - throw new Error('governor not implemented for query middleware'); - } -} diff --git a/typescript/infra/src/govern/ProxiedRouterGovernor.ts b/typescript/infra/src/govern/ProxiedRouterGovernor.ts new file mode 100644 index 000000000..5b1baf755 --- /dev/null +++ b/typescript/infra/src/govern/ProxiedRouterGovernor.ts @@ -0,0 +1,47 @@ +import { + ChainMap, + ConnectionClientViolation, + ConnectionClientViolationType, + HyperlaneAppChecker, + RouterApp, + RouterConfig, +} from '@hyperlane-xyz/sdk'; +import { types } from '@hyperlane-xyz/utils'; + +import { HyperlaneAppGovernor } from './HyperlaneAppGovernor'; + +export class ProxiedRouterGovernor< + App extends RouterApp, + Config extends RouterConfig, +> extends HyperlaneAppGovernor { + constructor( + checker: HyperlaneAppChecker, + owners: ChainMap, + ) { + super(checker, owners); + } + + protected async mapViolationsToCalls() { + for (const violation of this.checker.violations) { + if ( + violation.type === + ConnectionClientViolationType.InterchainSecurityModule + ) { + this.handleIsmViolation(violation as ConnectionClientViolation); + } else { + throw new Error(`Unsupported violation type ${violation.type}`); + } + } + } + + protected handleIsmViolation(violation: ConnectionClientViolation) { + this.pushCall(violation.chain, { + to: violation.contract.address, + data: violation.contract.interface.encodeFunctionData( + 'setInterchainSecurityModule', + [violation.expected], + ), + description: `Set ISM of ${violation.contract.address} to ${violation.expected}`, + }); + } +} diff --git a/typescript/sdk/src/consts/environments/mainnet.json b/typescript/sdk/src/consts/environments/mainnet.json index 54ea9c121..7596c5cb7 100644 --- a/typescript/sdk/src/consts/environments/mainnet.json +++ b/typescript/sdk/src/consts/environments/mainnet.json @@ -10,6 +10,7 @@ "testRecipient": "0x36FdA966CfffF8a9Cdc814f546db0e6378bFef35", "interchainQueryRouter": "0x234b19282985882d6d6fd54dEBa272271f4eb784", "interchainAccountRouter": "0xB193eBf06faD5D66492BB41DBbCd202640aE83fF", + "interchainAccountIsm": "0x5e8ee6840caa4f367aff1FF28aA36D5B1b836d35", "multisigIsmFactory": "0x9bf473968629b8f8cF4ab59Aeb9640b0c93411dd", "aggregationIsmFactory": "0xc864fa3B662613cA5051f41e157d0a997f9a5A87", "routingIsmFactory": "0x1fdfD1486b8339638C6b92f8a96D698D8182D2b1" @@ -25,6 +26,7 @@ "testRecipient": "0x36FdA966CfffF8a9Cdc814f546db0e6378bFef35", "interchainQueryRouter": "0x234b19282985882d6d6fd54dEBa272271f4eb784", "interchainAccountRouter": "0x5fD075C2157567F7F80e6cB20dDd75F40905bd87", + "interchainAccountIsm": "0x943303Ad7D2B87BB363E0BACC901486337d9B316", "multisigIsmFactory": "0xfD548D8a8EB8366D802F24e1bC6D1d21dB057EF1", "aggregationIsmFactory": "0x30B3Ef3e98B1FF72f03f71f68115E18F203Ec794", "routingIsmFactory": "0xBF30B4F328d1F6AC47ecCcF23836F3CbB2422c9f" @@ -40,6 +42,7 @@ "testRecipient": "0x36FdA966CfffF8a9Cdc814f546db0e6378bFef35", "interchainQueryRouter": "0x234b19282985882d6d6fd54dEBa272271f4eb784", "interchainAccountRouter": "0x77c509140A45B4B85E1A28f8c21AaEB3Ca8788B3", + "interchainAccountIsm": "0x88C01B64dCe0032796a1967E2b3447B397c6c7AC", "multisigIsmFactory": "0x270d0334bC98a02f7A4e2328B319EDEDcd7a2000", "aggregationIsmFactory": "0x070d4f61b05eD9e20C9194f29Df073f2110705fc", "routingIsmFactory": "0x0FC1A9DFAca9b6Ba11bC470Bf284Da7c107fDfF2" @@ -55,6 +58,7 @@ "testRecipient": "0x36FdA966CfffF8a9Cdc814f546db0e6378bFef35", "interchainQueryRouter": "0x234b19282985882d6d6fd54dEBa272271f4eb784", "interchainAccountRouter": "0x4a4D878c41C7F71eCff182F526b7691aDC6e4150", + "interchainAccountIsm": "0xCd8ACf2254641bD3Eaa32C1B8D36f0983de8C0E6", "multisigIsmFactory": "0xfF4872B62225c1f029a894D4682b250dD5577AC7", "aggregationIsmFactory": "0x10Add66Db9C837000A43F3601aa9c54c6744F4c8", "routingIsmFactory": "0x0B48a744698ba8dFa514742dFEB6728f52fD66f7" @@ -70,6 +74,7 @@ "testRecipient": "0x36FdA966CfffF8a9Cdc814f546db0e6378bFef35", "interchainQueryRouter": "0x234b19282985882d6d6fd54dEBa272271f4eb784", "interchainAccountRouter": "0xF9A4e3BA5e532906c241310f6832d2Ee8D1c5609", + "interchainAccountIsm": "0x1d3Bdf44887744007C7C62c85924c445C9e825DE", "multisigIsmFactory": "0x4F5db88EEdEBd6a8303ed13491169d4229D9A735", "aggregationIsmFactory": "0x4084054Fc83af652A1f21EA2FF2a668D796e2514", "routingIsmFactory": "0x85392758524EEE2323Bd3029E77aFc9bA9E60216" @@ -85,6 +90,7 @@ "testRecipient": "0x36FdA966CfffF8a9Cdc814f546db0e6378bFef35", "interchainQueryRouter": "0x234b19282985882d6d6fd54dEBa272271f4eb784", "interchainAccountRouter": "0xAC2BE81884C66E6c05B80C05C907B54C74eA2C49", + "interchainAccountIsm": "0xC1d10a99C382Dd224d7F513C7e0f74D7689071f4", "multisigIsmFactory": "0x2A87BF6aE678569545B258fA11087C6F57dd9012", "aggregationIsmFactory": "0x9E3075E067932d744119e583B34d11b144CE1e4A", "routingIsmFactory": "0xcC2fA09fa13857942fae408EcCEc8De307344e99" @@ -100,6 +106,7 @@ "testRecipient": "0x36FdA966CfffF8a9Cdc814f546db0e6378bFef35", "interchainQueryRouter": "0x234b19282985882d6d6fd54dEBa272271f4eb784", "interchainAccountRouter": "0x652e2F475Af7b1154817E09f5408f9011037492a", + "interchainAccountIsm": "0x3de63b62BeF9Da290F51f856cA9F3dB4225EDc05", "multisigIsmFactory": "0x21581dE0CB0Ce91E87b9d5124543C75Fa01ED9CC", "aggregationIsmFactory": "0xb7d42f065E32eB6fCAac7ef83902c56164328fE2", "routingIsmFactory": "0x4ef980034E631CC0CFb3b065aB793611f1B6511A" @@ -115,6 +122,7 @@ "testRecipient": "0x36FdA966CfffF8a9Cdc814f546db0e6378bFef35", "interchainQueryRouter": "0x234b19282985882d6d6fd54dEBa272271f4eb784", "interchainAccountRouter": "0x5b6311e0417CfD3Fb10318108897E63777CFE8D7", + "interchainAccountIsm": "0x88d346eEc75b6D22428bbaB569b6eBB0bE183c4F", "multisigIsmFactory": "0xe3DB9EdafBA60629308166B21DE2B4970bF94969", "aggregationIsmFactory": "0x20E1897CD584C3788A3C24f5e424345a55ADf90C", "routingIsmFactory": "0xB5ec4e94ec47A70C6A38370666F713423816ce4c" @@ -129,6 +137,7 @@ "multisigIsm": "0xC343A7054838FE9F249D7E3Ec1Fa6f1D108694b8", "testRecipient": "0x36FdA966CfffF8a9Cdc814f546db0e6378bFef35", "interchainAccountRouter": "0x32e77b20bf0cf034eB80ea9DD02De881016B01B3", + "interchainAccountIsm": "0x8AB7A6FaC052518A39628497735C855a2Beb515B", "multisigIsmFactory": "0xb58257cc81E47EC72fD38aE16297048de23163b4", "aggregationIsmFactory": "0xb4fc9B5fD57499Ef6FfF3995728a55F7A618ef86", "routingIsmFactory": "0xbB22547D1dc681fe925f568f637Ff67aC06c20fc" diff --git a/typescript/sdk/src/consts/environments/testnet.json b/typescript/sdk/src/consts/environments/testnet.json index 665802533..baf647bb1 100644 --- a/typescript/sdk/src/consts/environments/testnet.json +++ b/typescript/sdk/src/consts/environments/testnet.json @@ -10,6 +10,7 @@ "testRecipient": "0xBC3cFeca7Df5A45d61BC60E7898E63670e1654aE", "interchainQueryRouter": "0xF782C6C4A02f2c71BB8a1Db0166FAB40ea956818", "interchainAccountRouter": "0xDb91D575F17d8AAf1aFEC0eaDBD5Ac9e5Cef4ad0", + "interchainAccountIsm": "0x0aA320a1bD450152B4C500613335CeBA4f6073cF", "multisigIsmFactory": "0x9AF85731EDd41E2E50F81Ef8a0A69D2fB836EDf9", "aggregationIsmFactory": "0xBEd8Fd6d5c6cBd878479C25f4725C7c842a43821", "routingIsmFactory": "0x98F44EA5b9cA6aa02a5B75f31E0621083d9096a2" @@ -25,6 +26,7 @@ "testRecipient": "0xBC3cFeca7Df5A45d61BC60E7898E63670e1654aE", "interchainQueryRouter": "0xF782C6C4A02f2c71BB8a1Db0166FAB40ea956818", "interchainAccountRouter": "0xf82b58Bf348a6CEA6e19413e9DE040dB1a363128", + "interchainAccountIsm": "0x333C9A8c70Ea4F0498Fb58bEe40DEa40e63a9962", "multisigIsmFactory": "0x094652a8ea2153A03916771a778E7b66839A4F58", "aggregationIsmFactory": "0x9fB5D10C07569F2EBdc8ec4432B3a52b6d0ad9A0", "routingIsmFactory": "0xB24C91238eA30D59CF58CEB8dd5e4eaf70544d47" @@ -40,6 +42,7 @@ "testRecipient": "0xBC3cFeca7Df5A45d61BC60E7898E63670e1654aE", "interchainQueryRouter": "0xF782C6C4A02f2c71BB8a1Db0166FAB40ea956818", "interchainAccountRouter": "0x6a9CeD0e13E738517558aA283DA0E93e5904D49b", + "interchainAccountIsm": "0x40c2d6cA6F5A8857705C128b2c1A5f0Ae20880dc", "multisigIsmFactory": "0x32268e45724626972650837A26eEF0Dd9E6aEEE3", "aggregationIsmFactory": "0xD095B3ADa705e171f40187e10eD07Ee5fe291704", "routingIsmFactory": "0xdc8BC001FB649EfD51eEDD33151d428b917AaE3d" @@ -55,6 +58,7 @@ "testRecipient": "0xBC3cFeca7Df5A45d61BC60E7898E63670e1654aE", "interchainQueryRouter": "0xF782C6C4A02f2c71BB8a1Db0166FAB40ea956818", "interchainAccountRouter": "0x951c74D83a85833b53A448caaB7397bd3fa6CFB2", + "interchainAccountIsm": "0x9034f60Dec10cFa162369444081685F542d0C24D", "multisigIsmFactory": "0xfb6B94750e1307719892fBC21AC7A0C74A467869", "aggregationIsmFactory": "0xda72972291172B9966Dec7606d45d72e2b9f2470", "routingIsmFactory": "0x0CA314006fe0e7EF88ad2Bb69a7421aB2f1C5288" @@ -70,6 +74,7 @@ "testRecipient": "0xBC3cFeca7Df5A45d61BC60E7898E63670e1654aE", "interchainQueryRouter": "0xF782C6C4A02f2c71BB8a1Db0166FAB40ea956818", "interchainAccountRouter": "0xCb0ba89F564e31180A101Df54b7971206e03ee9b", + "interchainAccountIsm": "0x70835F3C2845394842DEA9f40cbe8087b2cE5712", "multisigIsmFactory": "0xFa13bd2BD45644bAF0797e41D1a4D56601a4059a", "aggregationIsmFactory": "0x11413a6Ea76a55eAec950894ba8fdd7683E41b06", "routingIsmFactory": "0x129A80Fe557153B5F48B4292F8C177bACdcf7dB3" @@ -85,6 +90,7 @@ "testRecipient": "0xBC3cFeca7Df5A45d61BC60E7898E63670e1654aE", "interchainQueryRouter": "0xF782C6C4A02f2c71BB8a1Db0166FAB40ea956818", "interchainAccountRouter": "0x209Ccdbe13BB913104117B1D6f7801684e98FA1F", + "interchainAccountIsm": "0xD699ff94f3FFd60A3a09bBff96181325B6C73FB8", "multisigIsmFactory": "0x4266D8Dd66D8Eb3934c8942968d1e54214D072d3", "aggregationIsmFactory": "0x759c4Eb4575B651a9f0Fb46653dd7B2F32fD7310", "routingIsmFactory": "0x561331FafB7f2ABa77E77780178ADdD1A37bdaBD" @@ -100,6 +106,7 @@ "testRecipient": "0xBC3cFeca7Df5A45d61BC60E7898E63670e1654aE", "interchainQueryRouter": "0xF782C6C4A02f2c71BB8a1Db0166FAB40ea956818", "interchainAccountRouter": "0x12EBd8cb561c68b587C392e0c5405B9866FD5820", + "interchainAccountIsm": "0x82F5a960a4e4Cc0614253e4977bb3BE10344a30C", "multisigIsmFactory": "0x0bA75fBC56FEb7e4F5EF4a8F042272cfec152ABc", "aggregationIsmFactory": "0x919AD6f6DFE1C17b89DAC2eE526F153C08afE305", "routingIsmFactory": "0x1D7b8aBa2494Ec82e80D6206d2B3df9f8C3F1862" @@ -115,6 +122,7 @@ "testRecipient": "0xBC3cFeca7Df5A45d61BC60E7898E63670e1654aE", "interchainQueryRouter": "0xF782C6C4A02f2c71BB8a1Db0166FAB40ea956818", "interchainAccountRouter": "0x4266D8Dd66D8Eb3934c8942968d1e54214D072d3", + "interchainAccountIsm": "0xA8978fdB093b1C5b892291A36e8527b34B749d6f", "multisigIsmFactory": "0x71cCc98689B48Dd50Fd5950815A56d76477349B2", "aggregationIsmFactory": "0xa27F4a2bD624CF1cB3605c532E95E27BB0AC0BB3", "routingIsmFactory": "0xa68022e53Fd28119D07C8336a8eC84A298Fd38Fd" @@ -129,6 +137,7 @@ "multisigIsm": "0xD3d062a5dcBA85ae863618d4c264d2358300c283", "testRecipient": "0xBC3cFeca7Df5A45d61BC60E7898E63670e1654aE", "interchainAccountRouter": "0xB057Fb841027a8554521DcCdeC3c3474CaC99AB5", + "interchainAccountIsm": "0x7483faD0Bc297667664A43A064bA7c9911659f57", "multisigIsmFactory": "0xD356C996277eFb7f75Ee8bd61b31cC781A12F54f", "aggregationIsmFactory": "0x01812D60958798695391dacF092BAc4a715B1718", "routingIsmFactory": "0xE67CfA164cDa449Ae38a0a09391eF6bCDf8e4e2c" diff --git a/typescript/sdk/src/deploy/types.ts b/typescript/sdk/src/deploy/types.ts index fbb1edf54..09169bdda 100644 --- a/typescript/sdk/src/deploy/types.ts +++ b/typescript/sdk/src/deploy/types.ts @@ -23,6 +23,8 @@ export interface OwnerViolation extends CheckerViolation { type: ViolationType.Owner; contract: Ownable; name: string; + actual: string; + expected: string; } export interface ProxyAdminViolation extends CheckerViolation { diff --git a/typescript/sdk/src/index.ts b/typescript/sdk/src/index.ts index 992f258e3..e2c599264 100644 --- a/typescript/sdk/src/index.ts +++ b/typescript/sdk/src/index.ts @@ -1,21 +1,22 @@ +export { HyperlaneApp } from './HyperlaneApp'; export { AgentChainSetup, AgentConfig, AgentConnection, AgentConnectionType, AgentSigner, - buildAgentConfig, HyperlaneAgentAddresses, + buildAgentConfig, } from './agents/types'; export { - chainIdToMetadata, ChainMetadata, - chainMetadata, ChainMetadataSchema, ExplorerFamily, + RpcPagination, + chainIdToMetadata, + chainMetadata, isValidChainMetadata, mainnetChainsMetadata, - RpcPagination, testnetChainsMetadata, wagmiChainMetadata, } from './consts/chainMetadata'; @@ -32,30 +33,30 @@ export { export { hyperlaneEnvironments } from './consts/environments'; export { defaultMultisigIsmConfigs } from './consts/multisigIsm'; export { - attachContracts, - attachContractsMap, - connectContracts, - connectContractsMap, - filterAddressesMap, HyperlaneAddresses, HyperlaneAddressesMap, HyperlaneContracts, HyperlaneContractsMap, HyperlaneFactories, + attachContracts, + attachContractsMap, + connectContracts, + connectContractsMap, + filterAddressesMap, serializeContracts, serializeContractsMap, } from './contracts'; +export { DispatchedMessage, HyperlaneCore } from './core/HyperlaneCore'; +export { HyperlaneCoreChecker } from './core/HyperlaneCoreChecker'; +export { HyperlaneCoreDeployer } from './core/HyperlaneCoreDeployer'; +export { TestCoreApp } from './core/TestCoreApp'; +export { TestCoreDeployer } from './core/TestCoreDeployer'; export { CoreFactories, coreFactories } from './core/contracts'; export { AnnotatedDispatch, AnnotatedLifecycleEvent, HyperlaneLifecyleEvent, } from './core/events'; -export { DispatchedMessage, HyperlaneCore } from './core/HyperlaneCore'; -export { HyperlaneCoreChecker } from './core/HyperlaneCoreChecker'; -export { HyperlaneCoreDeployer } from './core/HyperlaneCoreDeployer'; -export { TestCoreApp } from './core/TestCoreApp'; -export { TestCoreDeployer } from './core/TestCoreDeployer'; export { CoreConfig, CoreViolationType } from './core/types'; export { HyperlaneAppChecker } from './deploy/HyperlaneAppChecker'; export { DeployerOptions, HyperlaneDeployer } from './deploy/HyperlaneDeployer'; @@ -73,9 +74,9 @@ export { export * as verificationUtils from './deploy/verify/utils'; export { Annotated, + TSContract, getEvents, queryAnnotatedEvents, - TSContract, } from './events'; export { HyperlaneIgp } from './gas/HyperlaneIgp'; export { HyperlaneIgpChecker } from './gas/HyperlaneIgpChecker'; @@ -91,10 +92,9 @@ export { IgpViolationType, OverheadIgpConfig, } from './gas/types'; -export { HyperlaneApp } from './HyperlaneApp'; export { - collectValidators, HyperlaneIsmFactory, + collectValidators, } from './ism/HyperlaneIsmFactory'; export { HyperlaneIsmFactoryDeployer } from './ism/HyperlaneIsmFactoryDeployer'; export { @@ -104,14 +104,13 @@ export { MultisigIsmConfig, RoutingIsmConfig, } from './ism/types'; -export { interchainAccountFactories } from './middleware/account/contracts'; export { InterchainAccount } from './middleware/account/InterchainAccount'; export { InterchainAccountChecker } from './middleware/account/InterchainAccountChecker'; export { InterchainAccountConfig, InterchainAccountDeployer, } from './middleware/account/InterchainAccountDeployer'; -export { liquidityLayerFactories } from './middleware/liquidity-layer/contracts'; +export { interchainAccountFactories } from './middleware/account/contracts'; export { LiquidityLayerApp } from './middleware/liquidity-layer/LiquidityLayerApp'; export { BridgeAdapterConfig, @@ -120,20 +119,26 @@ export { LiquidityLayerDeployer, PortalAdapterConfig, } from './middleware/liquidity-layer/LiquidityLayerRouterDeployer'; -export { interchainQueryFactories } from './middleware/query/contracts'; +export { liquidityLayerFactories } from './middleware/liquidity-layer/contracts'; export { InterchainQuery } from './middleware/query/InterchainQuery'; export { InterchainQueryChecker } from './middleware/query/InterchainQueryChecker'; export { InterchainQueryConfig, InterchainQueryDeployer, } from './middleware/query/InterchainQueryDeployer'; +export { interchainQueryFactories } from './middleware/query/contracts'; export { MultiProvider, providerBuilder } from './providers/MultiProvider'; export { RetryJsonRpcProvider, RetryProvider } from './providers/RetryProvider'; export { GasRouterDeployer } from './router/GasRouterDeployer'; export { HyperlaneRouterChecker } from './router/HyperlaneRouterChecker'; export { HyperlaneRouterDeployer } from './router/HyperlaneRouterDeployer'; export { GasRouterApp, Router, RouterApp } from './router/RouterApps'; -export { GasRouterConfig, RouterConfig } from './router/types'; +export { + ConnectionClientViolation, + ConnectionClientViolationType, + GasRouterConfig, + RouterConfig, +} from './router/types'; export { createRouterConfigMap, deployTestIgpsAndGetRouterConfig, @@ -145,9 +150,9 @@ export { NameOrDomain, TestChainNames, } from './types'; +export { MultiGeneric } from './utils/MultiGeneric'; export { canonizeId, evmId } from './utils/ids'; export { multisigIsmVerificationCost } from './utils/ism'; -export { MultiGeneric } from './utils/MultiGeneric'; export { bigToFixed, convertDecimalValue, diff --git a/typescript/sdk/src/middleware/account/InterchainAccountChecker.ts b/typescript/sdk/src/middleware/account/InterchainAccountChecker.ts index a902a84ec..34ccd6a1e 100644 --- a/typescript/sdk/src/middleware/account/InterchainAccountChecker.ts +++ b/typescript/sdk/src/middleware/account/InterchainAccountChecker.ts @@ -1,4 +1,7 @@ +import { MultiProvider } from '../../providers/MultiProvider'; import { ProxiedRouterChecker } from '../../router/ProxiedRouterChecker'; +import { ChainMap } from '../../types'; +import { objMap } from '../../utils/objects'; import { InterchainAccount } from './InterchainAccount'; import { InterchainAccountConfig } from './InterchainAccountDeployer'; @@ -8,4 +11,26 @@ export class InterchainAccountChecker extends ProxiedRouterChecker< InterchainAccountFactories, InterchainAccount, InterchainAccountConfig -> {} +> { + constructor( + multiProvider: MultiProvider, + app: InterchainAccount, + configMap: ChainMap, + ) { + // The checker does not expect an ISM in it's config. + // Instead, we set the ISM to match the ISM address from the app. + const configMapWithIsm = objMap(configMap, (chain, config) => { + if (config.interchainSecurityModule) { + throw new Error( + 'Configuration of ISM address not supported in ICA checker', + ); + } + return { + ...config, + interchainSecurityModule: + app.contractsMap[chain].interchainAccountIsm.address, + }; + }); + super(multiProvider, app, configMapWithIsm); + } +} diff --git a/typescript/sdk/src/middleware/account/InterchainAccountDeployer.ts b/typescript/sdk/src/middleware/account/InterchainAccountDeployer.ts index 4831a3590..a4a297b8c 100644 --- a/typescript/sdk/src/middleware/account/InterchainAccountDeployer.ts +++ b/typescript/sdk/src/middleware/account/InterchainAccountDeployer.ts @@ -1,5 +1,3 @@ -import { ethers } from 'ethers'; - import { InterchainAccountRouter, Router, @@ -40,20 +38,31 @@ export class InterchainAccountDeployer extends HyperlaneRouterDeployer< chain: ChainName, config: InterchainAccountConfig, ): Promise> { + if (config.interchainSecurityModule) { + throw new Error( + 'Configuration of ISM address not supported in ICA deployer', + ); + } + const proxyAdmin = await this.deployContract(chain, 'proxyAdmin', []); + const interchainAccountIsm = await this.deployContract( + chain, + 'interchainAccountIsm', + [config.mailbox], + ); let interchainAccountRouter: InterchainAccountRouter; // adapted from HyperlaneDeployer.deployProxiedContract - const cachedContract = this.readCache( + const cachedRouter = this.readCache( chain, this.factories['interchainAccountRouter'], 'interchainAccountRouter', ); - if (cachedContract) { - interchainAccountRouter = cachedContract; + + if (cachedRouter) { + interchainAccountRouter = cachedRouter; } else { const deployer = await this.multiProvider.getSignerAddress(chain); - // 1. deploy the proxy first with a dummy implementation (proxy admin contract) const proxy = await this.deployContractFromFactory( chain, @@ -75,7 +84,7 @@ export class InterchainAccountDeployer extends HyperlaneRouterDeployer< await super.upgradeAndInitialize(chain, proxy, implementation, [ config.mailbox, config.interchainGasPaymaster, - config.interchainSecurityModule ?? ethers.constants.AddressZero, + interchainAccountIsm.address, owner, ]); interchainAccountRouter = implementation.attach(proxy.address); @@ -91,6 +100,7 @@ export class InterchainAccountDeployer extends HyperlaneRouterDeployer< return { proxyAdmin, + interchainAccountIsm, interchainAccountRouter, }; } diff --git a/typescript/sdk/src/middleware/account/accounts.hardhat-test.ts b/typescript/sdk/src/middleware/account/accounts.hardhat-test.ts index 7d666d0c7..01f04417c 100644 --- a/typescript/sdk/src/middleware/account/accounts.hardhat-test.ts +++ b/typescript/sdk/src/middleware/account/accounts.hardhat-test.ts @@ -44,12 +44,6 @@ describe('InterchainAccounts', async () => { signer.address, coreApp.contractsMap, ); - - /* - config.test1.interchainSecurityModule = await coreApp - .getContracts('test1') - .mailbox.defaultIsm(); - */ }); beforeEach(async () => { diff --git a/typescript/sdk/src/middleware/account/contracts.ts b/typescript/sdk/src/middleware/account/contracts.ts index 7004e196b..dd8bd54d8 100644 --- a/typescript/sdk/src/middleware/account/contracts.ts +++ b/typescript/sdk/src/middleware/account/contracts.ts @@ -1,10 +1,12 @@ import { + InterchainAccountIsm__factory, InterchainAccountRouter__factory, ProxyAdmin__factory, } from '@hyperlane-xyz/core'; export const interchainAccountFactories = { interchainAccountRouter: new InterchainAccountRouter__factory(), + interchainAccountIsm: new InterchainAccountIsm__factory(), proxyAdmin: new ProxyAdmin__factory(), }; diff --git a/typescript/sdk/src/router/HyperlaneRouterChecker.ts b/typescript/sdk/src/router/HyperlaneRouterChecker.ts index 3ee05a3e4..df3318bc4 100644 --- a/typescript/sdk/src/router/HyperlaneRouterChecker.ts +++ b/typescript/sdk/src/router/HyperlaneRouterChecker.ts @@ -7,7 +7,11 @@ import { HyperlaneAppChecker } from '../deploy/HyperlaneAppChecker'; import { ChainName } from '../types'; import { RouterApp } from './RouterApps'; -import { RouterConfig } from './types'; +import { + ConnectionClientViolation, + ConnectionClientViolationType, + RouterConfig, +} from './types'; export class HyperlaneRouterChecker< Factories extends HyperlaneFactories, @@ -27,24 +31,37 @@ export class HyperlaneRouterChecker< async checkHyperlaneConnectionClient(chain: ChainName): Promise { const router = this.app.router(this.app.getContracts(chain)); - const mailbox = await router.mailbox(); - const igp = await router.interchainGasPaymaster(); - const ism = await router.interchainSecurityModule(); - utils.assert( - utils.eqAddress(mailbox, this.configMap[chain].mailbox), - 'Mailbox mismatch', + + const checkConnectionClientProperty = async ( + property: keyof RouterConfig, + violationType: ConnectionClientViolationType, + ) => { + const actual = await router[property](); + const expected = + this.configMap[chain][property] ?? ethers.constants.AddressZero; + if (!utils.eqAddress(actual, expected)) { + const violation: ConnectionClientViolation = { + chain, + type: violationType, + contract: router, + actual, + expected, + }; + this.addViolation(violation); + } + }; + + await checkConnectionClientProperty( + 'mailbox', + ConnectionClientViolationType.Mailbox, ); - utils.assert( - utils.eqAddress(igp, this.configMap[chain].interchainGasPaymaster), - 'IGP mismatch', + await checkConnectionClientProperty( + 'interchainGasPaymaster', + ConnectionClientViolationType.InterchainGasPaymaster, ); - utils.assert( - utils.eqAddress( - ism, - this.configMap[chain].interchainSecurityModule ?? - ethers.constants.AddressZero, - ), - 'ISM mismatch', + await checkConnectionClientProperty( + 'interchainSecurityModule', + ConnectionClientViolationType.InterchainSecurityModule, ); } diff --git a/typescript/sdk/src/router/types.ts b/typescript/sdk/src/router/types.ts index 8b6f6f8c1..010f259d4 100644 --- a/typescript/sdk/src/router/types.ts +++ b/typescript/sdk/src/router/types.ts @@ -1,7 +1,11 @@ -import { ProxyAdmin__factory } from '@hyperlane-xyz/core'; +import { + HyperlaneConnectionClient, + ProxyAdmin__factory, +} from '@hyperlane-xyz/core'; import type { types } from '@hyperlane-xyz/utils'; import { HyperlaneFactories } from '../contracts'; +import { CheckerViolation } from '../deploy/types'; export type OwnableConfig = { owner: types.Address; @@ -24,3 +28,16 @@ export type ConnectionClientConfig = { interchainGasPaymaster: types.Address; interchainSecurityModule?: types.Address; }; + +export enum ConnectionClientViolationType { + InterchainSecurityModule = 'ConnectionClientIsm', + Mailbox = 'ConnectionClientMailbox', + InterchainGasPaymaster = 'ConnectionClientIgp', +} + +export interface ConnectionClientViolation extends CheckerViolation { + type: ConnectionClientViolationType; + contract: HyperlaneConnectionClient; + actual: string; + expected: string; +}