hardhat-ignition-deploy-everything v1.1.1
hardhat-deploy-everything
A hardhat plugin providing the ability to list and manage a bunch of hardhat-ignition deployments to execute at once (even conditional deployment modules).
Installation
Run this command to install it from NPM:
npm install --save-dev hardhat-common-tools@^1.4.0 hardhat-enquirer-plus@^1.4.0 hardhat-ignition-deploy-everything@^1.1.0Usage
This is a hardhat plugin, so the first thing to do is to install it in your hardhat.config.ts file:
require("hardhat-common-tools");
require("hardhat-enquirer-plus");
require("hardhat-ignition-deploy-everything");Once there, you can make use of it (this supports both viem-enabled and ethers-enabled projects):
This package works entirely on top of hardhat-ignition, so you'll also need it (along with the viem/ethers plugin) in your project.
There are some arguments not documented here: most of them belongs to the ignition package and some others belong to this one:
--force-non-interactivecauses the command to fail if it starts prompting for data to the user.--external(in add/remove/check sub-commands) tells that the involved file does not belong to the project but it is, instead, a package-path (suitable for a directrequirecall without./prefix) file.
Listing all the registered ignition modules
In order to list which ignition module files are registered in your project, run this command:
npx hardhat ignition deploy-everything listYou will see something like this one (or a message telling that no modules are registered):
These modules are added to the full deployment:
- Project file: ignition/modules/Lock.js
Results: {LockModule#Lock}
- Project file: ignition/modules/MyModule.js
Results: {MyModule#MyContract}In this example, my deploy-everything settings are set to only two modules: The Lock.js module (which comes by default in new JavaScript projects; it will be Lock.ts on TypeScript projects) and the MyModule.js file (which stands for an example module with just one contract).
Registering an ignition module into the deploy-everything settings
The following command adds the new module:
npx hardhat ignition deploy-everything add --module ignition/modules/SomeOtherModule.jsYou'll then see it when running the list command.
The following command removes a previously added module instead:
npx hardhat ignition deploy-everything remove --module ignition/modules/SomeOtherModule.jsChecking whether a module is added to the deploy-everything settings
The following command will tell whether a file is already added to the deploy-everything settings:
npx hardhat ignition deploy-everything check --module ignition/modules/SomeOtherModule.jsExecuting the whole deploy-everything settings
This implies executing all the modules defined there. Since this is already on top of hardhat-ignition, the modules that were previously run are kept and not re-run again.
The command to execute the full deployment is:
npx hardhat ignition deploy-everything runIf you want to set the parameters, use the --parameters argument for that. Actually: also take a look to the help:
npx hardhat ignition deploy-everything run --helpIt will list all the hardhat-ignition-related optional arguments (e.g. --reset and --verify). They will work as expected/detailed in hardhat-ignition's documentation.
Network-dependent deployments
While hardhat-ignition does not support network-dependent or network-conditional deployments, this is a useful feature when dealing with multiple chains.
For example, it might happen that you'd like to have a Chainlink's PriceFeed contract in your local network, but they are only present in external networks (testnets or mainnets, and not all of them). In this case, Chainlink provides a mock (as of today: something they call Aggregator V3 Mock). Still, you have to be careful when deploying it vs. when dealing with an external reference (this, in testnets and mainnets) when not having something like network-conditional deployments.
However, deploy-everything supports network-conditional deployments while executing the run task. In order to make
use of this feature for one (or more, perhaps) of your modules, you have to follow these steps:
- Let's say that you have your
AwesomeInterfacewhich is implemented in some testnet/mainnet you care about. - Let's also say that you have your
AwesomeMockimplementing theAwesomeInterface.- This is a local contract you want to use in your local network (that you'll somehow mock).
- You'll create a deployment module for your mock (as a new contract).
- You'll name it
MyAwesomeModuleand will typically make use ofm.contractfuture, using theAwesomeMockartifact. The extension might be.tsor.jsdepending on your needs.
- You'll name it
- You'll create a deployment module for the existing contracts:
- You'll name it
MyAwesomeModule-XXXXwhere XXXX is the intended target chain's id. For example, for Polygon Amoy your module file will be named:MyAwesomeModule-80002.js(or ending in.tsif TypeScript). - However the internal module name will still be
MyAwesomeModuleto keep conditional compatibility with the ignition deployment process (i.e.module.exports = buildModule("MyAwesomeModule", ...);) in each case. - The contents, in this case, will involve the
m.contractAtcall instead. - You can have conditional modules for many chain ids, not just one. For example: you might have modules for networks: Ethereum Mainnet (1), Polygon Mainnet (137), Ethereum Sepolia Testnet (11155111) and Polygon Amoy Testnet (80002), for a total of 4 extra conditional modules, while also needing the base, non-conditional, module.
- You'll name it
- You'll add all the modules you want to the deploy-everything settings, and only the MyAwesomeModule module (as if you were not doing conditional deployment at all).
- When you execute the
runtask, you'll specify the--networkoption (and perhaps --deployment-id) as usual with ignition deployments. If the chosen network matches the id of a conditional module (in our example: the Amoy / 80002 chain id) then the alternate module (in our example: MyAwesomeModule-80002.js) will be executed instead of the main one (in our example: MyAwesomeModule.js).
Manually invoking the deploy-everything utilities
While the tasks do the job, you can invoke the utilities to deal with deploy-everything in your own code.
This is done in two alternatives:
- Run them as a hardhat task (scope:
ignition, task:deploy-everything, first positional argument: either"list","check","add","remove"or"run"). Run them through direct/manual
hre.ignition.deployEverythingutilities:addDeployEverythingModule(file: string, external: boolean)to add one file (in-project or in-external-package).removeDeployEverythingModule(file: string, external: boolean)to remove it.listDeployEverythingModules()to list them (it is an asynchronous function).isModuleInDeployEverything(file: string, external: boolean)to tell whether it is added (this does not test the conditional modules, however).runDeployEverythingModules(reset, args)to execute them (it is an asynchronous function).resettells whether the deployment will be reset (for the current --network / --deployment-id).argsare directly passed tohre.ignition.deploycalls, properly including the arguments, if any.Notice how
verifyis not passed here. This is an external ignition task. Invoke it with:await hre.run( { scope: "ignition", task: "verify" }, { deploymentId: someOptionalDeploymentId } );