diff --git a/packages/plugin-hardhat/src/index.ts b/packages/plugin-hardhat/src/index.ts index 836593dcb..6f170b6df 100644 --- a/packages/plugin-hardhat/src/index.ts +++ b/packages/plugin-hardhat/src/index.ts @@ -2,6 +2,7 @@ import '@nomicfoundation/hardhat-ethers'; import './type-extensions'; +import { TASK_VERIFY_ETHERSCAN } from '@nomicfoundation/hardhat-verify/internal/task-names'; import { subtask, extendEnvironment, extendConfig } from 'hardhat/config'; import { TASK_COMPILE_SOLIDITY, TASK_COMPILE_SOLIDITY_COMPILE } from 'hardhat/builtin-tasks/task-names'; import { lazyObject } from 'hardhat/plugins'; @@ -193,7 +194,7 @@ extendConfig((config: HardhatConfig) => { }); if (tryRequire('@nomicfoundation/hardhat-verify')) { - subtask('verify:etherscan').setAction(async (args, hre, runSuper) => { + subtask(TASK_VERIFY_ETHERSCAN).setAction(async (args, hre, runSuper) => { const { verify } = await import('./verify-proxy'); return await verify(args, hre, runSuper); }); diff --git a/packages/plugin-hardhat/src/utils/deploy-impl.ts b/packages/plugin-hardhat/src/utils/deploy-impl.ts index 94e9d971b..4c6005e5d 100644 --- a/packages/plugin-hardhat/src/utils/deploy-impl.ts +++ b/packages/plugin-hardhat/src/utils/deploy-impl.ts @@ -11,6 +11,7 @@ import { } from '@openzeppelin/upgrades-core'; import type { ContractFactory, ethers } from 'ethers'; import type { EthereumProvider, HardhatRuntimeEnvironment } from 'hardhat/types'; +import { runVerify } from '../verify-proxy'; import { deploy } from './deploy'; import { GetTxResponse, DefenderDeployOptions, StandaloneOptions, UpgradeOptions, withDefaults } from './options'; import { getRemoteDeployment } from '../defender/utils'; @@ -132,7 +133,7 @@ async function deployImpl( remoteDeploymentId => getRemoteDeployment(hre, remoteDeploymentId), ); - let txResponse; + let txResponse: ethers.TransactionResponse | undefined; if (opts.getTxResponse) { if ('deployTransaction' in deployment) { txResponse = deployment.deployTransaction ?? undefined; @@ -141,5 +142,10 @@ async function deployImpl( } } + if (txResponse) { + await txResponse.wait(1); + await runVerify(hre, deployment.address, opts.constructorArgs); + } + return { impl: deployment.address, txResponse }; } diff --git a/packages/plugin-hardhat/src/utils/deploy.ts b/packages/plugin-hardhat/src/utils/deploy.ts index fab957310..985a112e7 100644 --- a/packages/plugin-hardhat/src/utils/deploy.ts +++ b/packages/plugin-hardhat/src/utils/deploy.ts @@ -2,27 +2,38 @@ import type { Deployment, RemoteDeploymentId } from '@openzeppelin/upgrades-core import type { ethers, ContractFactory, ContractMethodArgs } from 'ethers'; import { HardhatRuntimeEnvironment } from 'hardhat/types'; import { defenderDeploy } from '../defender/deploy'; +import { runVerify } from '../verify-proxy'; import { EthersDeployOptions, DefenderDeployOptions, UpgradeOptions } from './options'; export interface DeployTransaction { deployTransaction?: ethers.TransactionResponse; } +export type DeployResponse = Required & DeployTransaction & RemoteDeploymentId; + export async function deploy( hre: HardhatRuntimeEnvironment, opts: UpgradeOptions & EthersDeployOptions & DefenderDeployOptions, factory: ContractFactory, ...args: unknown[] -): Promise & DeployTransaction & RemoteDeploymentId> { +): Promise { // defender always includes RemoteDeploymentId, while ethers always includes DeployTransaction + let response: DeployResponse; if (opts?.useDefenderDeploy) { - return await defenderDeploy(hre, factory, opts, ...args); + response = await defenderDeploy(hre, factory, opts, ...args); } else { if (opts.txOverrides !== undefined) { args.push(opts.txOverrides); } - return await ethersDeploy(factory, ...args); + response = await ethersDeploy(factory, ...args); + } + + if (response.deployTransaction) { + await response.deployTransaction.wait(1); + await runVerify(hre, response.address, opts.constructorArgs); } + + return response; } async function ethersDeploy( diff --git a/packages/plugin-hardhat/src/verify-proxy.ts b/packages/plugin-hardhat/src/verify-proxy.ts index 173126208..b0e443e3f 100644 --- a/packages/plugin-hardhat/src/verify-proxy.ts +++ b/packages/plugin-hardhat/src/verify-proxy.ts @@ -1,3 +1,4 @@ +import { TASK_VERIFY_VERIFY } from '@nomicfoundation/hardhat-verify/internal/task-names'; import { getTransactionByHash, getImplementationAddress, @@ -11,6 +12,7 @@ import { isEmptySlot, } from '@openzeppelin/upgrades-core'; import artifactsBuildInfo from '@openzeppelin/upgrades-core/artifacts/build-info.json'; +import { HARDHAT_NETWORK_NAME } from 'hardhat/plugins'; import { HardhatRuntimeEnvironment, RunSuperFunction } from 'hardhat/types'; @@ -61,6 +63,21 @@ const verifiableContracts = { proxyAdmin: { artifact: ProxyAdmin, event: 'OwnershipTransferred(address,address)' }, }; +export async function runVerify(hre: HardhatRuntimeEnvironment, address: string, constructorArguments: unknown[] = []) { + if (hre.network.name === HARDHAT_NETWORK_NAME) { + // Don't verify on hardhat network + return; + } + try { + await hre.run(TASK_VERIFY_VERIFY, { + address, + constructorArguments, + }); + } catch (e) { + // fail silently + } +} + /** * Overrides hardhat-verify's verify:etherscan subtask to fully verify a proxy or beacon. *