├── .editorconfig ├── .example.networkconfig ├── .gas-snapshot ├── .github ├── ISSUE_TEMPLATE │ ├── bug_report.yml │ └── feature_request.yml ├── dependabot.yml ├── pull_request_template.md └── workflows │ ├── checks.yml │ ├── codeql.yml │ └── test-contracts.yml ├── .gitignore ├── .gitmodules ├── .prettierignore ├── .prettierrc.yml ├── .solcover.js ├── LICENSE ├── Makefile ├── README.md ├── SECURITY.md ├── abis ├── contracts │ └── src │ │ ├── Create2DeployerLocal.sol │ │ └── Create2DeployerLocal.json │ │ └── Greeter.sol │ │ └── Greeter.json └── xdeployer │ └── src │ └── contracts │ └── CreateX.sol │ └── CreateX.json ├── arguments.js ├── contracts ├── src │ ├── Create2DeployerLocal.sol │ └── Greeter.sol └── test │ └── Greeter.t.sol ├── deploy-args.ts ├── deploy └── deploy-zksync.ts ├── eslint.config.js ├── foundry.toml ├── hardhat.config.ts ├── package.json ├── pnpm-lock.yaml ├── remappings.txt ├── renovate.json ├── scripts ├── deploy.sh ├── deploy.ts ├── deploy_local.sh ├── flatten.sh ├── interact.ts └── verify.sh ├── slippy.config.js ├── slither.config.json ├── test └── Greeter.test.ts └── tsconfig.json /.editorconfig: -------------------------------------------------------------------------------- 1 | root = true 2 | 3 | [*] 4 | charset = utf-8 5 | end_of_line = lf 6 | indent_style = space 7 | indent_size = 2 8 | insert_final_newline = true 9 | trim_trailing_whitespace = false 10 | 11 | [*.sol] 12 | indent_size = 4 13 | max_line_length = 120 14 | -------------------------------------------------------------------------------- /.example.networkconfig: -------------------------------------------------------------------------------- 1 | // An example of the network setup for the `xdeployer` plugin (https://github.com/pcaversaccio/xdeployer) 2 | 3 | networks: ["sepolia", "optimismSepolia", "arbitrumSepolia"], 4 | rpcUrls: [vars.get("ETH_SEPOLIA_TESTNET_URL", "https://rpc.sepolia.org"), vars.get("OPTIMISM_SEPOLIA_URL", "https://sepolia.optimism.io"), vars.get("ARBITRUM_SEPOLIA_URL", "https://sepolia-rollup.arbitrum.io/rpc")], 5 | -------------------------------------------------------------------------------- /.gas-snapshot: -------------------------------------------------------------------------------- 1 | GreeterTest:testCreateGreeter() (gas: 19817) -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/bug_report.yml: -------------------------------------------------------------------------------- 1 | name: "Bug Report" 2 | description: "Report a bug for Hardhat project template." 3 | title: "[Bug-Candidate]: " 4 | labels: 5 | - bug 6 | assignees: 7 | - pcaversaccio 8 | body: 9 | - attributes: 10 | value: | 11 | Please check the [issues tab](https://github.com/pcaversaccio/hardhat-project-template-ts/issues) to avoid duplicates. 12 | Thanks for taking the time to fill out this bug report! 13 | type: markdown 14 | 15 | - attributes: 16 | label: "Describe the issue:" 17 | id: what-happened 18 | type: textarea 19 | validations: 20 | required: true 21 | 22 | - attributes: 23 | label: "Code example to reproduce the issue:" 24 | description: "It can be a GitHub repository/gist or a simple code snippet." 25 | placeholder: "```ts\nasync function main() {}\n```" 26 | id: reproduce 27 | type: textarea 28 | validations: 29 | required: true 30 | 31 | - attributes: 32 | label: "Version:" 33 | description: | 34 | What version of Hardhat are you running? 35 | Run `npx hardhat --version`. 36 | id: version 37 | type: textarea 38 | validations: 39 | required: true 40 | 41 | - attributes: 42 | label: "Relevant log output:" 43 | description: | 44 | Please copy and paste any relevant log output. This will be automatically formatted into code, so no need for backticks. 45 | render: Shell 46 | id: logs 47 | type: textarea 48 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/feature_request.yml: -------------------------------------------------------------------------------- 1 | name: "Feature Request" 2 | description: "Suggest an idea for Hardhat project template." 3 | title: "[Feature-Request]: " 4 | labels: 5 | - enhancement 6 | assignees: 7 | - pcaversaccio 8 | body: 9 | - attributes: 10 | value: | 11 | Please check the [issues tab](https://github.com/pcaversaccio/hardhat-project-template-ts/issues) to avoid duplicates. 12 | Thanks for taking the time to provide feedback on my Hardhat project template! 13 | type: markdown 14 | 15 | - attributes: 16 | label: "Describe the desired feature:" 17 | description: Explain what the feature solves/improves. 18 | id: feature-request 19 | type: textarea 20 | validations: 21 | required: true 22 | 23 | - attributes: 24 | label: "Code example that solves the feature:" 25 | description: "It can be a GitHub repository/gist or a simple code snippet." 26 | placeholder: "```ts\nasync function main() {}\n```" 27 | id: reproduce 28 | type: textarea 29 | -------------------------------------------------------------------------------- /.github/dependabot.yml: -------------------------------------------------------------------------------- 1 | version: 2 2 | updates: 3 | - package-ecosystem: "npm" 4 | directory: "/" 5 | schedule: 6 | interval: "weekly" 7 | day: "monday" 8 | target-branch: "main" 9 | labels: 10 | - "dependencies" 11 | assignees: 12 | - "pcaversaccio" 13 | -------------------------------------------------------------------------------- /.github/pull_request_template.md: -------------------------------------------------------------------------------- 1 | 11 | 12 | #### ✅ PR Checklist 13 | 14 | - [ ] Because this PR includes a **bug fix**, relevant tests have been included. 15 | - [ ] Because this PR includes a **new feature**, the change was previously discussed in an [issue](https://github.com/pcaversaccio/hardhat-project-template-ts/issues) or in the [discussions](https://github.com/pcaversaccio/hardhat-project-template-ts/discussions) section. 16 | - [x] I didn't do anything of this. 17 | 18 | ### 🕓 Changelog 19 | 20 | 21 | 22 | #### 🐶 Cute Animal Picture 23 | 24 | ![Put a link to a cute animal picture inside the parenthesis-->]() 25 | -------------------------------------------------------------------------------- /.github/workflows/checks.yml: -------------------------------------------------------------------------------- 1 | name: 👮‍♂️ Sanity checks 2 | 3 | on: [push, pull_request, workflow_dispatch] 4 | 5 | concurrency: 6 | group: ${{ github.workflow }}-${{ github.ref }} 7 | cancel-in-progress: true 8 | 9 | jobs: 10 | prettify-n-lint: 11 | runs-on: ${{ matrix.os }} 12 | strategy: 13 | matrix: 14 | os: 15 | - ubuntu-latest 16 | node_version: 17 | - 24 18 | 19 | steps: 20 | - name: Checkout 21 | uses: actions/checkout@v5 22 | 23 | - name: Install pnpm 24 | uses: pnpm/action-setup@v4 25 | with: 26 | run_install: false 27 | 28 | - name: Get pnpm cache directory path 29 | id: pnpm-cache-dir-path 30 | run: echo "dir=$(pnpm store path --silent)" >> $GITHUB_OUTPUT 31 | 32 | - name: Restore pnpm cache 33 | uses: actions/cache@v4 34 | id: pnpm-cache 35 | with: 36 | path: ${{ steps.pnpm-cache-dir-path.outputs.dir }} 37 | key: ${{ runner.os }}-pnpm-store-${{ hashFiles('**/pnpm-lock.yaml') }} 38 | restore-keys: | 39 | ${{ runner.os }}-pnpm-store- 40 | 41 | - name: Use Node.js ${{ matrix.node_version }} 42 | uses: actions/setup-node@v5 43 | with: 44 | node-version: ${{ matrix.node_version }} 45 | 46 | - name: Install pnpm project with a clean slate 47 | run: pnpm install --prefer-offline --frozen-lockfile 48 | 49 | - name: Prettier and lint 50 | run: pnpm lint:check 51 | 52 | codespell: 53 | runs-on: ${{ matrix.os }} 54 | strategy: 55 | matrix: 56 | os: 57 | - ubuntu-latest 58 | 59 | steps: 60 | - name: Checkout 61 | uses: actions/checkout@v5 62 | 63 | - name: Run codespell 64 | uses: codespell-project/actions-codespell@v2 65 | with: 66 | check_filenames: true 67 | skip: ./.git,pnpm-lock.yaml 68 | ignore_words_list: superseed,slippy 69 | 70 | validate-links: 71 | runs-on: ${{ matrix.os }} 72 | strategy: 73 | matrix: 74 | os: 75 | - ubuntu-latest 76 | ruby_version: 77 | - 3.4 78 | 79 | steps: 80 | - name: Checkout 81 | uses: actions/checkout@v5 82 | 83 | - name: Set up Ruby 84 | uses: ruby/setup-ruby@v1 85 | with: 86 | ruby-version: ${{ matrix.ruby_version }} 87 | bundler-cache: true 88 | 89 | - name: Install awesome_bot 90 | run: gem install awesome_bot 91 | 92 | - name: Validate URLs 93 | run: awesome_bot ./*.md contracts/src/*.sol contracts/test/*.sol --request-delay 0.4 --white-list http://localhost:24012,https://etherscan.io,https://snowtrace.io 94 | -------------------------------------------------------------------------------- /.github/workflows/codeql.yml: -------------------------------------------------------------------------------- 1 | name: 🔍️ CodeQL 2 | 3 | on: [push, pull_request, workflow_dispatch] 4 | 5 | concurrency: 6 | group: ${{ github.workflow }}-${{ github.ref }} 7 | cancel-in-progress: true 8 | 9 | jobs: 10 | analyse: 11 | runs-on: ${{ matrix.os }} 12 | permissions: 13 | # The permissions set for `actions` and `contents` are only 14 | # required for workflows in private repositories. 15 | actions: read 16 | contents: read 17 | security-events: write 18 | strategy: 19 | matrix: 20 | os: 21 | - ubuntu-latest 22 | language: 23 | - javascript-typescript 24 | 25 | steps: 26 | - name: Checkout 27 | uses: actions/checkout@v5 28 | 29 | - name: Initialise CodeQL 30 | uses: github/codeql-action/init@v3 31 | with: 32 | languages: ${{ matrix.language }} 33 | queries: +security-and-quality 34 | 35 | - name: Autobuild 36 | uses: github/codeql-action/autobuild@v3 37 | 38 | - name: Perform CodeQL analysis 39 | uses: github/codeql-action/analyze@v3 40 | with: 41 | category: "/language:${{ matrix.language }}" 42 | -------------------------------------------------------------------------------- /.github/workflows/test-contracts.yml: -------------------------------------------------------------------------------- 1 | name: 🕵️‍♂️ Test smart contracts 2 | 3 | on: [push, pull_request, workflow_dispatch] 4 | 5 | concurrency: 6 | group: ${{ github.workflow }}-${{ github.ref }} 7 | cancel-in-progress: true 8 | 9 | jobs: 10 | tests: 11 | runs-on: ${{ matrix.os }} 12 | permissions: 13 | contents: read 14 | security-events: write 15 | strategy: 16 | matrix: 17 | os: 18 | - ubuntu-latest 19 | node_version: 20 | - 24 21 | 22 | steps: 23 | - name: Checkout 24 | uses: actions/checkout@v5 25 | with: 26 | submodules: recursive 27 | 28 | - name: Install pnpm 29 | uses: pnpm/action-setup@v4 30 | with: 31 | run_install: false 32 | 33 | - name: Get pnpm cache directory path 34 | id: pnpm-cache-dir-path 35 | run: echo "dir=$(pnpm store path --silent)" >> $GITHUB_OUTPUT 36 | 37 | - name: Restore pnpm cache 38 | uses: actions/cache@v4 39 | id: pnpm-cache 40 | with: 41 | path: ${{ steps.pnpm-cache-dir-path.outputs.dir }} 42 | key: ${{ runner.os }}-pnpm-store-${{ hashFiles('**/pnpm-lock.yaml') }} 43 | restore-keys: | 44 | ${{ runner.os }}-pnpm-store- 45 | 46 | - name: Use Node.js ${{ matrix.node_version }} 47 | uses: actions/setup-node@v5 48 | with: 49 | node-version: ${{ matrix.node_version }} 50 | 51 | - name: Install pnpm project with a clean slate 52 | run: pnpm install --prefer-offline --frozen-lockfile 53 | 54 | - name: Install Foundry 55 | uses: foundry-rs/foundry-toolchain@v1 56 | with: 57 | version: nightly 58 | 59 | - name: Hardhat tests 60 | run: pnpm test:hh 61 | 62 | - name: Show the Foundry CI config 63 | run: forge config 64 | env: 65 | FOUNDRY_PROFILE: ci 66 | FOUNDRY_DISABLE_NIGHTLY_WARNING: "1" 67 | 68 | - name: Foundry tests 69 | run: pnpm test:forge 70 | env: 71 | FOUNDRY_PROFILE: ci 72 | FOUNDRY_DISABLE_NIGHTLY_WARNING: "1" 73 | 74 | - name: Slither static analyser 75 | uses: crytic/slither-action@v0.4.1 76 | id: slither 77 | with: 78 | node-version: ${{ matrix.node_version }} 79 | fail-on: config 80 | sarif: results.sarif 81 | 82 | - name: Upload SARIF file 83 | uses: github/codeql-action/upload-sarif@v3 84 | with: 85 | sarif_file: ${{ steps.slither.outputs.sarif }} 86 | 87 | coverage: 88 | runs-on: ${{ matrix.os }} 89 | permissions: 90 | pull-requests: write 91 | strategy: 92 | matrix: 93 | os: 94 | - ubuntu-latest 95 | node_version: 96 | - 24 97 | 98 | steps: 99 | - name: Checkout 100 | uses: actions/checkout@v5 101 | with: 102 | submodules: recursive 103 | 104 | - name: Install pnpm 105 | uses: pnpm/action-setup@v4 106 | with: 107 | run_install: false 108 | 109 | - name: Get pnpm cache directory path 110 | id: pnpm-cache-dir-path 111 | run: echo "dir=$(pnpm store path --silent)" >> $GITHUB_OUTPUT 112 | 113 | - name: Restore pnpm cache 114 | uses: actions/cache@v4 115 | id: pnpm-cache 116 | with: 117 | path: ${{ steps.pnpm-cache-dir-path.outputs.dir }} 118 | key: ${{ runner.os }}-pnpm-store-${{ hashFiles('**/pnpm-lock.yaml') }} 119 | restore-keys: | 120 | ${{ runner.os }}-pnpm-store- 121 | 122 | - name: Use Node.js ${{ matrix.node_version }} 123 | uses: actions/setup-node@v5 124 | with: 125 | node-version: ${{ matrix.node_version }} 126 | 127 | - name: Install pnpm project with a clean slate 128 | run: pnpm install --prefer-offline --frozen-lockfile 129 | 130 | - name: Install Foundry 131 | uses: foundry-rs/foundry-toolchain@v1 132 | with: 133 | version: nightly 134 | 135 | - name: Set up LCOV 136 | uses: hrishikesh-kadam/setup-lcov@v1 137 | with: 138 | ref: v2.3.1 139 | 140 | - name: Run coverage 141 | run: | 142 | echo '```' >> $GITHUB_STEP_SUMMARY 143 | NO_COLOR=1 forge coverage --report summary --report lcov --lcov-version 2.3.1 >> $GITHUB_STEP_SUMMARY 144 | echo '```' >> $GITHUB_STEP_SUMMARY 145 | env: 146 | FOUNDRY_PROFILE: default 147 | FOUNDRY_DISABLE_NIGHTLY_WARNING: "1" 148 | 149 | # See https://github.com/ScopeLift/foundry-template/blob/fd3875d2e99a65dec19431723d6516b4ed76746e/.github/workflows/ci.yml#L49-L78. 150 | - name: Remove unnecessary directories 151 | run: lcov --branch-coverage --remove lcov.info 'test/*' 'script/*' 'node_modules/*' --output-file lcov.info --ignore-errors unused,unused 152 | 153 | - name: Post coverage report 154 | if: ${{ (github.event.pull_request.head.repo.full_name == github.repository && github.event_name == 'pull_request') }} 155 | uses: romeovs/lcov-reporter-action@v0.4.0 156 | with: 157 | title: "Test Coverage Report" 158 | delete-old-comments: true 159 | lcov-file: ./lcov.info 160 | github-token: ${{ secrets.GITHUB_TOKEN }} 161 | 162 | # The following steps act as a temporary workaround, as LCOV `2.3.1` is not yet supported 163 | # in `zgosalvez/github-actions-report-lcov@v5`: https://github.com/zgosalvez/github-actions-report-lcov/issues/168. 164 | - name: Set up LCOV `1.16` 165 | run: | 166 | wget https://github.com/linux-test-project/lcov/releases/download/v1.16/lcov-1.16.tar.gz 167 | tar -xzf lcov-1.16.tar.gz 168 | cd lcov-1.16 169 | sudo make install 170 | lcov --version 171 | sudo rm -rf lcov-1.16.tar.gz lcov-1.16 172 | 173 | - name: Run coverage using LCOV `1.16` 174 | run: forge coverage --report lcov --lcov-version 1.16 175 | env: 176 | FOUNDRY_PROFILE: default 177 | FOUNDRY_DISABLE_NIGHTLY_WARNING: "1" 178 | 179 | # See https://github.com/ScopeLift/foundry-template/blob/fd3875d2e99a65dec19431723d6516b4ed76746e/.github/workflows/ci.yml#L49-L78. 180 | - name: Remove unnecessary `test` directory 181 | run: lcov --remove lcov.info 'test/*' 'script/*' 'node_modules/*' --output-file lcov.info --rc lcov_branch_coverage=1 182 | 183 | - name: Verify minimum coverage 184 | uses: zgosalvez/github-actions-report-lcov@v5 185 | with: 186 | coverage-files: ./lcov.info 187 | # Please specify here the minimum coverage threshold below which any PR will fail. 188 | minimum-coverage: 100 189 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Ignore all Visual Studio Code settings 2 | .vscode/* 3 | !.vscode/settings.json 4 | !.vscode/tasks.json 5 | !.vscode/launch.json 6 | !.vscode/extensions.json 7 | !.vscode/*.code-snippets 8 | 9 | # Local history for Visual Studio Code 10 | .history 11 | 12 | # Built Visual Studio Code extensions 13 | *.vsix 14 | 15 | # Dependency directory 16 | node_modules 17 | 18 | # dotenv environment variable files 19 | .env 20 | .env.development.local 21 | .env.test.local 22 | .env.production.local 23 | .env.local 24 | 25 | # Hardhat configuration file 26 | vars.json 27 | 28 | # Log files 29 | logs 30 | *.log 31 | npm-debug.log* 32 | yarn-debug.log* 33 | yarn-error.log* 34 | .pnpm-debug.log* 35 | 36 | # Yarn integrity file 37 | .yarn-integrity 38 | 39 | # Optional npm cache directory 40 | .npm 41 | 42 | # Modern Yarn files 43 | .pnp.* 44 | .yarn/* 45 | !.yarn/cache 46 | !.yarn/patches 47 | !.yarn/plugins 48 | !.yarn/releases 49 | !.yarn/sdks 50 | !.yarn/versions 51 | 52 | # Hardhat files 53 | cache 54 | cache_hardhat 55 | artifacts 56 | .deps 57 | 58 | # TypeScript bindings output directory 59 | typechain-types 60 | 61 | # solidity-coverage directory and output file 62 | coverage 63 | coverage.json 64 | 65 | # forge-coverage lcov.info file 66 | lcov.info 67 | 68 | # xdeployer output directory 69 | deployments 70 | 71 | # Foundry output directory 72 | forge-artifacts 73 | 74 | # Ignore flattened files 75 | flattened.sol 76 | 77 | # Tenderly fork deployment directory 78 | deployments_tenderly 79 | 80 | # ZKsync files 81 | cache-zk 82 | cache_hardhat-zk 83 | artifacts-zk 84 | deployments-zk 85 | 86 | # Miscellaneous files 87 | bin 88 | out 89 | -------------------------------------------------------------------------------- /.gitmodules: -------------------------------------------------------------------------------- 1 | [submodule "contracts/lib/forge-std"] 2 | path = contracts/lib/forge-std 3 | url = https://github.com/foundry-rs/forge-std.git 4 | -------------------------------------------------------------------------------- /.prettierignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | pnpm-lock.yaml 3 | lib 4 | cache 5 | cache_hardhat 6 | cache_hardhat-zk 7 | artifacts 8 | artifacts-zk 9 | typechain-types 10 | coverage 11 | deployments 12 | deployments-zk 13 | deployments_tenderly 14 | forge-artifacts 15 | bin 16 | out 17 | -------------------------------------------------------------------------------- /.prettierrc.yml: -------------------------------------------------------------------------------- 1 | plugins: 2 | - "prettier-plugin-solidity" 3 | -------------------------------------------------------------------------------- /.solcover.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | skipFiles: ["mocks/", "lib/", "test/", "Create2DeployerLocal.sol"], 3 | }; 4 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | # dependencies 2 | update :; forge update 3 | 4 | # install latest stable solc version 5 | solc :; sudo add-apt-repository ppa:ethereum/ethereum && sudo apt-get update && sudo apt-get install solc 6 | 7 | # build & test 8 | build :; forge build 9 | build-optimised :; forge build --optimize 10 | test-forge :; forge test 11 | test-gasreport :; forge test --gas-report 12 | trace :; forge test -vvvvv 13 | clean :; forge clean 14 | snapshot :; forge snapshot 15 | 16 | # chmod scripts 17 | scripts :; chmod +x ./scripts/* 18 | 19 | # fork mainnet with Hardhat 20 | mainnet-fork :; npx hardhat node --fork ${ETH_MAINNET_RPC_URL} 21 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Fully-Fledged Hardhat Project Template Based on TypeScript 2 | 3 | [![🕵️‍♂️ Test smart contracts](https://github.com/pcaversaccio/hardhat-project-template-ts/actions/workflows/test-contracts.yml/badge.svg)](https://github.com/pcaversaccio/hardhat-project-template-ts/actions/workflows/test-contracts.yml) 4 | [![License: MIT](https://img.shields.io/badge/License-MIT-blue.svg)](https://opensource.org/license/mit) 5 | 6 | ## Installation 7 | 8 | It is recommended to install [`pnpm`](https://pnpm.io) through the `npm` package manager, which comes bundled with [Node.js](https://nodejs.org/en) when you install it on your system. It is recommended to use a Node.js version `>=24.2.0`. 9 | 10 | Once you have `npm` installed, you can run the following both to install and upgrade `pnpm`: 11 | 12 | ```console 13 | npm install -g pnpm 14 | ``` 15 | 16 | After having installed `pnpm`, simply run: 17 | 18 | ```console 19 | pnpm install 20 | ``` 21 | 22 | ## Running Deployments 23 | 24 | > [!NOTE] 25 | > The deployment script [`deploy.ts`](./scripts/deploy.ts) attempts to automatically verify the contract on the target chain after deployment. If you have not configured an API key, the verification will fail. 26 | 27 | **Example Sepolia:** 28 | 29 | ```console 30 | pnpm deploy:sepolia 31 | ``` 32 | 33 | > The deployment script [`deploy.ts`](./scripts/deploy.ts) includes the `tenderly` Hardhat Runtime Environment (HRE) extension with the `verify` method. Please consider uncommenting and configuring the Tenderly `project`, `username`, `forkNetwork`, `privateVerification`, and `deploymentsDir` attributes in the [`hardhat.config.ts`](./hardhat.config.ts) file before deploying or remove this call. Also, for this plugin to function you need to create a `config.yaml` file at `$HOME/.tenderly/config.yaml` or `%HOMEPATH%\.tenderly\config.yaml` and add an `access_key` field to it. For further information, see [here](https://github.com/Tenderly/hardhat-tenderly/tree/master/packages/hre-extender-v2#installing-tenderly-cli). 34 | 35 | > For the deployment on the [ZKsync Era](https://docs.zksync.io/) test network, you must add your to-be-deployed contract artifact to [`deploy-zksync.ts`](./deploy/deploy-zksync.ts), enable `zksync` in the [`hardhat.config.ts`](./hardhat.config.ts#L121) file, and then run `pnpm compile` (in case you face any compilation issues, disable all configurations associated with the [`@tenderly/hardhat-tenderly`](https://github.com/Tenderly/hardhat-tenderly) plugin, including the `import` statement itself; see also [here](https://github.com/matter-labs/hardhat-zksync/issues/998) and [here](https://github.com/matter-labs/hardhat-zksync/issues/1174)). Next, fund your deployer account on ZKsync Era Testnet, setup the ZKsync-related configuration variables accordingly, and simply run `pnpm deploy:zksynctestnet`. Eventually, to verify the contract you can invoke: `npx hardhat verify --network zkSyncTestnet --constructor-args arguments.js `. The same approach applies if you want to deploy on the production network, except that you need to run `pnpm deploy:zksyncmain` and use `--network zkSyncMain` for the contract verification. 36 | 37 | ## Running `CREATE2` Deployments 38 | 39 | ```console 40 | pnpm xdeploy 41 | ``` 42 | 43 | This template uses the [`xdeployer`](https://github.com/pcaversaccio/xdeployer) Hardhat plugin. Check out the documentation for more information on the specifics of the deployments. 44 | 45 | ## Configuration Variables 46 | 47 | Run `npx hardhat vars set PRIVATE_KEY` to set the private key of your wallet. This allows secure access to your wallet to use with both testnet and mainnet funds during Hardhat deployments. 48 | 49 | You can also run `npx hardhat vars setup` to see which other [configuration variables](https://v2.hardhat.org/hardhat-runner/docs/guides/configuration-variables) are available. 50 | 51 | ## Using a Ledger Hardware Wallet 52 | 53 | This template implements the [`hardhat-ledger`](https://v2.hardhat.org/hardhat-runner/plugins/nomicfoundation-hardhat-ledger) plugin. Run `npx hardhat set LEDGER_ACCOUNT` and enter the address of the Ledger account you want to use. 54 | 55 | ## Mainnet Forking 56 | 57 | You can start an instance of the Hardhat network that forks the mainnet. This means that it will simulate having the same state as the mainnet, but it will work as a local development network. That way you can interact with deployed protocols and test complex interactions locally. To use this feature, you need to connect to an archive node. 58 | 59 | This template is currently configured via the [`hardhat.config.ts`](./hardhat.config.ts) as follows: 60 | 61 | ```ts 62 | forking: { 63 | url: vars.get("ETH_MAINNET_URL", ethMainnetUrl), 64 | // The Hardhat network will by default fork from the latest mainnet block 65 | // To pin the block number, specify it below 66 | // You will need access to a node with archival data for this to work! 67 | // blockNumber: 14743877, 68 | // If you want to do some forking, set `enabled` to true 69 | enabled: false, 70 | }, 71 | ``` 72 | 73 | ## Contract Verification 74 | 75 | Change the contract address to your contract after the deployment has been successful. This works for both testnet and mainnet. You will need to get an API key from [etherscan](https://etherscan.io), [snowtrace](https://snowtrace.io) etc. 76 | 77 | **Example:** 78 | 79 | ```console 80 | npx hardhat verify --network ethMain --constructor-args arguments.js 81 | ``` 82 | 83 | ## Contract Interaction 84 | 85 | This template includes an [example script](./scripts/interact.ts) that shows how to interact programmatically with a deployed contract. You must customise it according to your contract's specifications. The script can be simply invoked via: 86 | 87 | ```console 88 | npx hardhat run scripts/interact.ts --network 89 | ``` 90 | 91 | ## Foundry 92 | 93 | This template repository also includes the [Foundry](https://github.com/foundry-rs/foundry) toolkit as well as the [`@nomicfoundation/hardhat-foundry`](https://v2.hardhat.org/hardhat-runner/docs/advanced/hardhat-and-foundry) plugin. 94 | 95 | > If you need help getting started with Foundry, I recommend reading the [📖 Foundry Book](https://getfoundry.sh). 96 | 97 | ### Dependencies 98 | 99 | ```console 100 | make update 101 | ``` 102 | 103 | or 104 | 105 | ```console 106 | forge update 107 | ``` 108 | 109 | ### Compilation 110 | 111 | ```console 112 | make build 113 | ``` 114 | 115 | or 116 | 117 | ```console 118 | forge build 119 | ``` 120 | 121 | ### Testing 122 | 123 | To run only TypeScript tests: 124 | 125 | ```console 126 | pnpm test:hh 127 | ``` 128 | 129 | To run only Solidity tests: 130 | 131 | ```console 132 | pnpm test:forge 133 | ``` 134 | 135 | or 136 | 137 | ```console 138 | make test-forge 139 | ``` 140 | 141 | To additionally display the gas report, you can run: 142 | 143 | ```console 144 | make test-gasreport 145 | ``` 146 | 147 | ### Deployment and Etherscan Verification 148 | 149 | Inside the [`scripts/`](./scripts) folder are a few preconfigured scripts that can be used to deploy and verify contracts via Foundry. These scripts are required to be _executable_ meaning they must be made executable by running: 150 | 151 | ```console 152 | make scripts 153 | ``` 154 | -------------------------------------------------------------------------------- /SECURITY.md: -------------------------------------------------------------------------------- 1 | # 🛡️ Security Policy 2 | 3 | ## 📬 Reporting a Vulnerability 4 | 5 | Please report any security issues you find to [email@address.com](mailto:email@address.com). 6 | -------------------------------------------------------------------------------- /abis/contracts/src/Create2DeployerLocal.sol/Create2DeployerLocal.json: -------------------------------------------------------------------------------- 1 | [ 2 | "error FailedContractCreation(address)", 3 | "error FailedContractInitialisation(address,bytes)", 4 | "error FailedEtherTransfer(address,bytes)", 5 | "error InvalidNonceValue(address)", 6 | "error InvalidSalt(address)", 7 | "event ContractCreation(address indexed,bytes32 indexed)", 8 | "event ContractCreation(address indexed)", 9 | "event Create3ProxyContractCreation(address indexed,bytes32 indexed)", 10 | "function computeCreate2Address(bytes32,bytes32) view returns (address)", 11 | "function computeCreate2Address(bytes32,bytes32,address) pure returns (address)", 12 | "function computeCreate3Address(bytes32,address) pure returns (address)", 13 | "function computeCreate3Address(bytes32) view returns (address)", 14 | "function computeCreateAddress(uint256) view returns (address)", 15 | "function computeCreateAddress(address,uint256) view returns (address)", 16 | "function deployCreate(bytes) payable returns (address)", 17 | "function deployCreate2(bytes32,bytes) payable returns (address)", 18 | "function deployCreate2(bytes) payable returns (address)", 19 | "function deployCreate2AndInit(bytes32,bytes,bytes,tuple(uint256,uint256),address) payable returns (address)", 20 | "function deployCreate2AndInit(bytes,bytes,tuple(uint256,uint256)) payable returns (address)", 21 | "function deployCreate2AndInit(bytes,bytes,tuple(uint256,uint256),address) payable returns (address)", 22 | "function deployCreate2AndInit(bytes32,bytes,bytes,tuple(uint256,uint256)) payable returns (address)", 23 | "function deployCreate2Clone(bytes32,address,bytes) payable returns (address)", 24 | "function deployCreate2Clone(address,bytes) payable returns (address)", 25 | "function deployCreate3(bytes) payable returns (address)", 26 | "function deployCreate3(bytes32,bytes) payable returns (address)", 27 | "function deployCreate3AndInit(bytes32,bytes,bytes,tuple(uint256,uint256)) payable returns (address)", 28 | "function deployCreate3AndInit(bytes,bytes,tuple(uint256,uint256)) payable returns (address)", 29 | "function deployCreate3AndInit(bytes32,bytes,bytes,tuple(uint256,uint256),address) payable returns (address)", 30 | "function deployCreate3AndInit(bytes,bytes,tuple(uint256,uint256),address) payable returns (address)", 31 | "function deployCreateAndInit(bytes,bytes,tuple(uint256,uint256)) payable returns (address)", 32 | "function deployCreateAndInit(bytes,bytes,tuple(uint256,uint256),address) payable returns (address)", 33 | "function deployCreateClone(address,bytes) payable returns (address)" 34 | ] 35 | -------------------------------------------------------------------------------- /abis/contracts/src/Greeter.sol/Greeter.json: -------------------------------------------------------------------------------- 1 | [ 2 | "constructor(string)", 3 | "function greet() view returns (string)", 4 | "function setGreeting(string)" 5 | ] 6 | -------------------------------------------------------------------------------- /abis/xdeployer/src/contracts/CreateX.sol/CreateX.json: -------------------------------------------------------------------------------- 1 | [ 2 | "error FailedContractCreation(address)", 3 | "error FailedContractInitialisation(address,bytes)", 4 | "error FailedEtherTransfer(address,bytes)", 5 | "error InvalidNonceValue(address)", 6 | "error InvalidSalt(address)", 7 | "event ContractCreation(address indexed,bytes32 indexed)", 8 | "event ContractCreation(address indexed)", 9 | "event Create3ProxyContractCreation(address indexed,bytes32 indexed)", 10 | "function computeCreate2Address(bytes32,bytes32) view returns (address)", 11 | "function computeCreate2Address(bytes32,bytes32,address) pure returns (address)", 12 | "function computeCreate3Address(bytes32,address) pure returns (address)", 13 | "function computeCreate3Address(bytes32) view returns (address)", 14 | "function computeCreateAddress(uint256) view returns (address)", 15 | "function computeCreateAddress(address,uint256) view returns (address)", 16 | "function deployCreate(bytes) payable returns (address)", 17 | "function deployCreate2(bytes32,bytes) payable returns (address)", 18 | "function deployCreate2(bytes) payable returns (address)", 19 | "function deployCreate2AndInit(bytes32,bytes,bytes,tuple(uint256,uint256),address) payable returns (address)", 20 | "function deployCreate2AndInit(bytes,bytes,tuple(uint256,uint256)) payable returns (address)", 21 | "function deployCreate2AndInit(bytes,bytes,tuple(uint256,uint256),address) payable returns (address)", 22 | "function deployCreate2AndInit(bytes32,bytes,bytes,tuple(uint256,uint256)) payable returns (address)", 23 | "function deployCreate2Clone(bytes32,address,bytes) payable returns (address)", 24 | "function deployCreate2Clone(address,bytes) payable returns (address)", 25 | "function deployCreate3(bytes) payable returns (address)", 26 | "function deployCreate3(bytes32,bytes) payable returns (address)", 27 | "function deployCreate3AndInit(bytes32,bytes,bytes,tuple(uint256,uint256)) payable returns (address)", 28 | "function deployCreate3AndInit(bytes,bytes,tuple(uint256,uint256)) payable returns (address)", 29 | "function deployCreate3AndInit(bytes32,bytes,bytes,tuple(uint256,uint256),address) payable returns (address)", 30 | "function deployCreate3AndInit(bytes,bytes,tuple(uint256,uint256),address) payable returns (address)", 31 | "function deployCreateAndInit(bytes,bytes,tuple(uint256,uint256)) payable returns (address)", 32 | "function deployCreateAndInit(bytes,bytes,tuple(uint256,uint256),address) payable returns (address)", 33 | "function deployCreateClone(address,bytes) payable returns (address)" 34 | ] 35 | -------------------------------------------------------------------------------- /arguments.js: -------------------------------------------------------------------------------- 1 | // JavaScript module that exports the constructor as an argument list 2 | // Required by the Hardhat plugin `hardhat-etherscan` 3 | // See also here: https://hardhat.org/plugins/nomiclabs-hardhat-etherscan.html#complex-arguments 4 | 5 | module.exports = [ 6 | "Hello, Hardhat!", // The example Greeter.sol file needs a string 7 | ]; 8 | -------------------------------------------------------------------------------- /contracts/src/Create2DeployerLocal.sol: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: MIT 2 | pragma solidity ^0.8.23; 3 | 4 | import {CreateX} from "xdeployer/src/contracts/CreateX.sol"; 5 | 6 | contract Create2DeployerLocal is CreateX {} 7 | -------------------------------------------------------------------------------- /contracts/src/Greeter.sol: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: Unlicense 2 | pragma solidity ^0.8.30; 3 | 4 | contract Greeter { 5 | string private greeting; 6 | 7 | constructor(string memory greeting_) { 8 | greeting = greeting_; 9 | } 10 | 11 | function greet() public view returns (string memory) { 12 | return greeting; 13 | } 14 | 15 | function setGreeting(string memory newGreeting) public { 16 | greeting = newGreeting; 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /contracts/test/Greeter.t.sol: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: Unlicense 2 | pragma solidity ^0.8.30; 3 | 4 | import {Test} from "forge-std/Test.sol"; 5 | import {Greeter} from "../src/Greeter.sol"; 6 | 7 | contract GreeterTest is Test { 8 | Greeter public greeter; 9 | 10 | function setUp() public { 11 | greeter = new Greeter("Hello, Hardhat!"); 12 | } 13 | 14 | function testCreateGreeter() public { 15 | assertEq(greeter.greet(), "Hello, Hardhat!"); 16 | greeter.setGreeting("Hola, mundo!"); 17 | assertEq(greeter.greet(), "Hola, mundo!"); 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /deploy-args.ts: -------------------------------------------------------------------------------- 1 | // Input the arguments for the constructor 2 | const data = [ 3 | "Hello, Hardhat!", // The example Greeter.sol file needs a string 4 | ]; 5 | // Export the arguments to be picked up by the `hardhat.config.ts` deployment script 6 | export { data }; 7 | -------------------------------------------------------------------------------- /deploy/deploy-zksync.ts: -------------------------------------------------------------------------------- 1 | // Note that the deployment scripts must be placed in the `deploy` folder for `hardhat deploy-zksync` 2 | import { HardhatRuntimeEnvironment } from "hardhat/types"; 3 | import { Wallet } from "zksync-ethers"; 4 | import { Deployer } from "@matterlabs/hardhat-zksync-deploy"; 5 | 6 | // Colour codes for terminal prints 7 | const RESET = "\x1b[0m"; 8 | const GREEN = "\x1b[32m"; 9 | 10 | function delay(ms: number) { 11 | return new Promise((resolve) => setTimeout(resolve, ms)); 12 | } 13 | 14 | export default async function main(hre: HardhatRuntimeEnvironment) { 15 | // Get the private key from the configured network 16 | // This assumes that a private key is configured for the selected network 17 | const accounts = hre.network.config.accounts; 18 | if (!Array.isArray(accounts)) { 19 | throw new Error( 20 | `No private key configured for network ${hre.network.name}`, 21 | ); 22 | } 23 | const PRIVATE_KEY = accounts[0]; 24 | if (typeof PRIVATE_KEY !== "string") { 25 | throw new Error( 26 | `No private key configured for network ${hre.network.name}`, 27 | ); 28 | } 29 | 30 | const wallet = new Wallet(PRIVATE_KEY); 31 | const deployer = new Deployer(hre, wallet); 32 | 33 | const constructorArgs = ["Hello, Hardhat!"]; 34 | const artifact = await deployer.loadArtifact("Greeter"); 35 | const contract = await deployer.deploy(artifact, constructorArgs); 36 | 37 | await contract.waitForDeployment(); 38 | const contractAddress = await contract.getAddress(); 39 | 40 | console.log("Greeter deployed to: " + `${GREEN}${contractAddress}${RESET}\n`); 41 | 42 | console.log( 43 | "Waiting 30 seconds before beginning the contract verification to allow the block explorer to index the contract...\n", 44 | ); 45 | await delay(30000); // Wait for 30 seconds before verifying the contract 46 | 47 | await hre.run("verify:verify", { 48 | address: contractAddress, 49 | constructorArguments: constructorArgs, 50 | }); 51 | } 52 | -------------------------------------------------------------------------------- /eslint.config.js: -------------------------------------------------------------------------------- 1 | /* eslint-disable @typescript-eslint/no-require-imports */ 2 | const eslint = require("@eslint/js"); 3 | const tseslint = require("typescript-eslint"); 4 | const eslintConfigPrettier = require("eslint-config-prettier"); 5 | /* eslint-enable @typescript-eslint/no-require-imports */ 6 | 7 | /** @type {import('typescript-eslint').TSESLint.FlatConfig.ConfigArray} */ 8 | module.exports = tseslint.config( 9 | { 10 | files: ["**/*.{js,ts}"], 11 | extends: [ 12 | eslint.configs.recommended, 13 | ...tseslint.configs.recommended, 14 | ...tseslint.configs.stylistic, 15 | eslintConfigPrettier, 16 | ], 17 | plugins: { 18 | "@typescript-eslint": tseslint.plugin, 19 | }, 20 | languageOptions: { 21 | ecmaVersion: "latest", 22 | parser: tseslint.parser, 23 | parserOptions: { 24 | project: true, 25 | tsconfigRootDir: __dirname, 26 | }, 27 | }, 28 | }, 29 | { 30 | ignores: [ 31 | "node_modules/**", 32 | "pnpm-lock.yaml", 33 | "lib/**", 34 | "cache/**", 35 | "cache_hardhat/**", 36 | "cache_hardhat-zk/**", 37 | "artifacts/**", 38 | "artifacts-zk/**", 39 | "typechain-types/**", 40 | "coverage/**", 41 | "deployments/**", 42 | "deployments-zk/**", 43 | "deployments_tenderly/**", 44 | "forge-artifacts/**", 45 | "bin/**", 46 | "out/**", 47 | ], 48 | }, 49 | ); 50 | -------------------------------------------------------------------------------- /foundry.toml: -------------------------------------------------------------------------------- 1 | # Defaults for all profiles. 2 | [profile.default] 3 | src = "contracts/src" # Set the source directory. 4 | test = "contracts/test" # Set the test directory. 5 | out = "forge-artifacts" # Set the output directory for the artifacts. 6 | libs = ["contracts/lib"] # Configure an array of library directories. 7 | cache = true # Enable caching. 8 | cache_path = "cache" # Set the path to the cache. 9 | force = false # Do not ignore the cache. 10 | solc_version = "0.8.30" # Set the Solidity compiler version. 11 | evm_version = "paris" # Set the EVM target version. 12 | optimizer = true # Enable the Solidity compiler optimiser. 13 | optimizer_runs = 999_999 # Configure the number of optimiser runs. 14 | via_ir = false # Prevent the compilation pipeline from running through the Yul intermediate representation. 15 | verbosity = 3 # Set the verbosity level for the tests. 16 | ffi = false # Enable the foreign function interface (ffi) cheatcode. 17 | fs_permissions = [{ access = "read-write", path = "./" }] # Configure read-write access to the project root. 18 | fuzz = { runs = 256, max_test_rejects = 65_536 } # Configure the number of fuzz runs and maximum number of combined inputs that may be rejected for the tests. 19 | invariant = { runs = 256, depth = 15 } # Configure the number of runs and calls (executed in one run) for each invariant test group. 20 | 21 | # Default overrides for the CI runs. 22 | [profile.ci] 23 | force = true # Perform always a clean build. 24 | verbosity = 4 # Increase the verbosity level for the tests. 25 | fuzz = { runs = 10_000, max_test_rejects = 150_000 } # Increase the number of fuzz runs and maximum number of combined inputs that may be rejected for the tests. 26 | invariant = { runs = 375, depth = 500 } # Increase the number of runs (while preserving the default depth) for each invariant test group. 27 | -------------------------------------------------------------------------------- /hardhat.config.ts: -------------------------------------------------------------------------------- 1 | import { HardhatUserConfig, task, vars } from "hardhat/config"; 2 | 3 | import "@nomicfoundation/hardhat-ethers"; 4 | import "@nomicfoundation/hardhat-verify"; 5 | import "@nomicfoundation/hardhat-ledger"; 6 | import "@nomicfoundation/hardhat-foundry"; 7 | import "@nomicfoundation/hardhat-chai-matchers"; 8 | import "@nomicfoundation/hardhat-ignition-ethers"; 9 | import "@typechain/hardhat"; 10 | 11 | import "xdeployer"; 12 | import "@matterlabs/hardhat-zksync-solc"; 13 | import "@matterlabs/hardhat-zksync-deploy"; 14 | import "@matterlabs/hardhat-zksync-verify"; 15 | import "@matterlabs/hardhat-zksync-ethers"; 16 | import "hardhat-gas-reporter"; 17 | import "hardhat-abi-exporter"; 18 | import "solidity-coverage"; 19 | import "hardhat-contract-sizer"; 20 | // Uncomment if you want to use the Hardhat Tenderly module 21 | // You must also uncomment the subsequent `tenderly` configuration in this file accordingly 22 | // import "@tenderly/hardhat-tenderly"; 23 | 24 | const ethMainnetUrl = vars.get("ETH_MAINNET_URL", "https://rpc.ankr.com/eth"); 25 | const accounts = [ 26 | vars.get( 27 | "PRIVATE_KEY", 28 | // `keccak256("DEFAULT_VALUE")` 29 | "0x0d1706281056b7de64efd2088195fa8224c39103f578c9b84f951721df3fa71c", 30 | ), 31 | ]; 32 | const ledgerAccounts = [ 33 | vars.get( 34 | "LEDGER_ACCOUNT", 35 | // `bytes20(uint160(uint256(keccak256("DEFAULT_VALUE"))))` 36 | "0x8195fa8224c39103f578c9b84f951721df3fa71c", 37 | ), 38 | ]; 39 | 40 | task("accounts", "Prints the list of accounts", async (_, hre) => { 41 | const accounts = await hre.ethers.getSigners(); 42 | 43 | for (const account of accounts) { 44 | console.log(account.address); 45 | } 46 | }); 47 | 48 | task("evm", "Prints the configured EVM version", async (_, hre) => { 49 | console.log(hre.config.solidity.compilers[0].settings.evmVersion); 50 | }); 51 | 52 | task( 53 | "balances", 54 | "Prints the list of accounts and their balances", 55 | async (_, hre) => { 56 | const accounts = await hre.ethers.getSigners(); 57 | 58 | for (const account of accounts) { 59 | console.log( 60 | account.address + 61 | " " + 62 | (await hre.ethers.provider.getBalance(account.address)), 63 | ); 64 | } 65 | }, 66 | ); 67 | 68 | const config: HardhatUserConfig = { 69 | paths: { 70 | sources: "./contracts/src", 71 | }, 72 | solidity: { 73 | // Only use Solidity default versions `>=0.8.25` for EVM networks that support the new `cancun` opcodes: 74 | // https://github.com/ethereum/execution-specs/blob/master/network-upgrades/mainnet-upgrades/cancun.md 75 | // Only use Solidity default versions `>=0.8.20` for EVM networks that support the opcode `PUSH0` 76 | // Otherwise, use the versions `<=0.8.19` 77 | version: "0.8.30", 78 | settings: { 79 | optimizer: { 80 | enabled: true, 81 | runs: 999_999, 82 | }, 83 | evmVersion: "paris", // Prevent using the `PUSH0` and `cancun` opcodes 84 | }, 85 | }, 86 | zksolc: { 87 | version: "1.5.15", 88 | compilerSource: "binary", 89 | settings: { 90 | enableEraVMExtensions: false, 91 | forceEVMLA: false, 92 | optimizer: { 93 | enabled: true, 94 | mode: "3", 95 | fallback_to_optimizing_for_size: false, 96 | }, 97 | }, 98 | }, 99 | networks: { 100 | hardhat: { 101 | initialBaseFeePerGas: 0, 102 | chainId: 31337, 103 | hardfork: "cancun", 104 | forking: { 105 | url: vars.get("ETH_MAINNET_URL", ethMainnetUrl), 106 | // The Hardhat network will by default fork from the latest mainnet block 107 | // To pin the block number, specify it below 108 | // You will need access to a node with archival data for this to work! 109 | // blockNumber: 14743877, 110 | // If you want to do some forking, set `enabled` to true 111 | enabled: false, 112 | }, 113 | ledgerAccounts, 114 | // zksync: true, // Enable ZKsync in the Hardhat local network 115 | }, 116 | localhost: { 117 | url: "http://127.0.0.1:8545", 118 | ledgerAccounts, 119 | }, 120 | tenderly: { 121 | // Add your own Tenderly fork ID 122 | url: `https://rpc.tenderly.co/fork/${vars.get("TENDERLY_FORK_ID", "")}`, 123 | ledgerAccounts, 124 | }, 125 | devnet: { 126 | // Add your own Tenderly DevNet ID 127 | url: `https://rpc.vnet.tenderly.co/devnet/${vars.get( 128 | "TENDERLY_DEVNET_ID", 129 | "", 130 | )}`, 131 | accounts, 132 | ledgerAccounts, 133 | }, 134 | sepolia: { 135 | chainId: 11155111, 136 | url: vars.get("ETH_SEPOLIA_TESTNET_URL", "https://rpc.sepolia.org"), 137 | accounts, 138 | ledgerAccounts, 139 | }, 140 | holesky: { 141 | chainId: 17000, 142 | url: vars.get( 143 | "ETH_HOLESKY_TESTNET_URL", 144 | "https://holesky.rpc.thirdweb.com", 145 | ), 146 | accounts, 147 | ledgerAccounts, 148 | }, 149 | hoodi: { 150 | chainId: 560048, 151 | url: vars.get( 152 | "ETH_HOODI_TESTNET_URL", 153 | "https://rpc.hoodi.ethpandaops.io", 154 | ), 155 | accounts, 156 | ledgerAccounts, 157 | }, 158 | ethMain: { 159 | chainId: 1, 160 | url: ethMainnetUrl, 161 | accounts, 162 | ledgerAccounts, 163 | }, 164 | bscTestnet: { 165 | chainId: 97, 166 | url: vars.get( 167 | "BSC_TESTNET_URL", 168 | "https://data-seed-prebsc-1-s1.binance.org:8545", 169 | ), 170 | accounts, 171 | ledgerAccounts, 172 | }, 173 | bscMain: { 174 | chainId: 56, 175 | url: vars.get("BSC_MAINNET_URL", "https://bsc-dataseed1.binance.org"), 176 | accounts, 177 | ledgerAccounts, 178 | }, 179 | optimismTestnet: { 180 | chainId: 420, 181 | url: vars.get("OPTIMISM_TESTNET_URL", "https://goerli.optimism.io"), 182 | accounts, 183 | ledgerAccounts, 184 | }, 185 | optimismSepolia: { 186 | chainId: 11155420, 187 | url: vars.get("OPTIMISM_SEPOLIA_URL", "https://sepolia.optimism.io"), 188 | accounts, 189 | ledgerAccounts, 190 | }, 191 | optimismMain: { 192 | chainId: 10, 193 | url: vars.get("OPTIMISM_MAINNET_URL", "https://mainnet.optimism.io"), 194 | accounts, 195 | ledgerAccounts, 196 | }, 197 | arbitrumSepolia: { 198 | chainId: 421614, 199 | url: vars.get( 200 | "ARBITRUM_SEPOLIA_URL", 201 | "https://sepolia-rollup.arbitrum.io/rpc", 202 | ), 203 | accounts, 204 | ledgerAccounts, 205 | }, 206 | arbitrumMain: { 207 | chainId: 42161, 208 | url: vars.get("ARBITRUM_MAINNET_URL", "https://arb1.arbitrum.io/rpc"), 209 | accounts, 210 | ledgerAccounts, 211 | }, 212 | arbitrumNova: { 213 | chainId: 42170, 214 | url: vars.get("ARBITRUM_NOVA_URL", "https://nova.arbitrum.io/rpc"), 215 | accounts, 216 | ledgerAccounts, 217 | }, 218 | amoy: { 219 | chainId: 80002, 220 | url: vars.get( 221 | "POLYGON_TESTNET_URL", 222 | "https://rpc-amoy.polygon.technology", 223 | ), 224 | accounts, 225 | ledgerAccounts, 226 | }, 227 | polygonZkEVMTestnet: { 228 | chainId: 2442, 229 | url: vars.get( 230 | "POLYGON_ZKEVM_TESTNET_URL", 231 | "https://rpc.cardona.zkevm-rpc.com", 232 | ), 233 | accounts, 234 | ledgerAccounts, 235 | }, 236 | polygon: { 237 | chainId: 137, 238 | url: vars.get("POLYGON_MAINNET_URL", "https://polygon-rpc.com"), 239 | accounts, 240 | ledgerAccounts, 241 | }, 242 | polygonZkEVMMain: { 243 | chainId: 1101, 244 | url: vars.get("POLYGON_ZKEVM_MAINNET_URL", "https://zkevm-rpc.com"), 245 | accounts, 246 | ledgerAccounts, 247 | }, 248 | hecoMain: { 249 | chainId: 128, 250 | url: vars.get("HECO_MAINNET_URL", "https://http-mainnet.hecochain.com"), 251 | accounts, 252 | ledgerAccounts, 253 | }, 254 | fantomTestnet: { 255 | chainId: 4002, 256 | url: vars.get("FANTOM_TESTNET_URL", "https://rpc.testnet.fantom.network"), 257 | accounts, 258 | ledgerAccounts, 259 | }, 260 | fantomMain: { 261 | chainId: 250, 262 | url: vars.get("FANTOM_MAINNET_URL", "https://rpc.ankr.com/fantom"), 263 | accounts, 264 | ledgerAccounts, 265 | }, 266 | fuji: { 267 | chainId: 43113, 268 | url: vars.get( 269 | "AVALANCHE_TESTNET_URL", 270 | "https://api.avax-test.network/ext/bc/C/rpc", 271 | ), 272 | accounts, 273 | ledgerAccounts, 274 | }, 275 | avalanche: { 276 | chainId: 43114, 277 | url: vars.get( 278 | "AVALANCHE_MAINNET_URL", 279 | "https://api.avax.network/ext/bc/C/rpc", 280 | ), 281 | accounts, 282 | ledgerAccounts, 283 | }, 284 | chiado: { 285 | chainId: 10200, 286 | url: vars.get("GNOSIS_TESTNET_URL", "https://rpc.chiadochain.net"), 287 | accounts, 288 | ledgerAccounts, 289 | }, 290 | gnosis: { 291 | chainId: 100, 292 | url: vars.get("GNOSIS_MAINNET_URL", "https://rpc.gnosischain.com"), 293 | accounts, 294 | ledgerAccounts, 295 | }, 296 | moonbaseAlpha: { 297 | chainId: 1287, 298 | url: vars.get( 299 | "MOONBEAM_TESTNET_URL", 300 | "https://rpc.api.moonbase.moonbeam.network", 301 | ), 302 | accounts, 303 | ledgerAccounts, 304 | }, 305 | moonriver: { 306 | chainId: 1285, 307 | url: vars.get( 308 | "MOONRIVER_MAINNET_URL", 309 | "https://moonriver.public.blastapi.io", 310 | ), 311 | accounts, 312 | ledgerAccounts, 313 | }, 314 | moonbeam: { 315 | chainId: 1284, 316 | url: vars.get( 317 | "MOONBEAM_MAINNET_URL", 318 | "https://moonbeam.public.blastapi.io", 319 | ), 320 | accounts, 321 | ledgerAccounts, 322 | }, 323 | alfajores: { 324 | chainId: 44787, 325 | url: vars.get( 326 | "CELO_TESTNET_URL", 327 | "https://alfajores-forno.celo-testnet.org", 328 | ), 329 | accounts, 330 | ledgerAccounts, 331 | }, 332 | celo: { 333 | chainId: 42220, 334 | url: vars.get("CELO_MAINNET_URL", "https://forno.celo.org"), 335 | accounts, 336 | ledgerAccounts, 337 | }, 338 | auroraTestnet: { 339 | chainId: 1313161555, 340 | url: vars.get("AURORA_TESTNET_URL", "https://testnet.aurora.dev"), 341 | accounts, 342 | ledgerAccounts, 343 | }, 344 | auroraMain: { 345 | chainId: 1313161554, 346 | url: vars.get("AURORA_MAINNET_URL", "https://mainnet.aurora.dev"), 347 | accounts, 348 | ledgerAccounts, 349 | }, 350 | harmonyTestnet: { 351 | chainId: 1666700000, 352 | url: vars.get("HARMONY_TESTNET_URL", "https://api.s0.b.hmny.io"), 353 | accounts, 354 | ledgerAccounts, 355 | }, 356 | harmonyMain: { 357 | chainId: 1666600000, 358 | url: vars.get("HARMONY_MAINNET_URL", "https://api.harmony.one"), 359 | accounts, 360 | ledgerAccounts, 361 | }, 362 | spark: { 363 | chainId: 123, 364 | url: vars.get("FUSE_TESTNET_URL", "https://rpc.fusespark.io"), 365 | accounts, 366 | ledgerAccounts, 367 | }, 368 | fuse: { 369 | chainId: 122, 370 | url: vars.get("FUSE_MAINNET_URL", "https://rpc.fuse.io"), 371 | accounts, 372 | ledgerAccounts, 373 | }, 374 | cronosTestnet: { 375 | chainId: 338, 376 | url: vars.get("CRONOS_TESTNET_URL", "https://evm-t3.cronos.org"), 377 | accounts, 378 | ledgerAccounts, 379 | }, 380 | cronosMain: { 381 | chainId: 25, 382 | url: vars.get("CRONOS_MAINNET_URL", "https://evm.cronos.org"), 383 | accounts, 384 | ledgerAccounts, 385 | }, 386 | evmosTestnet: { 387 | chainId: 9000, 388 | url: vars.get("EVMOS_TESTNET_URL", "https://evmos-testnet.lava.build"), 389 | accounts, 390 | ledgerAccounts, 391 | }, 392 | evmosMain: { 393 | chainId: 9001, 394 | url: vars.get("EVMOS_MAINNET_URL", "https://evmos.lava.build"), 395 | accounts, 396 | ledgerAccounts, 397 | }, 398 | bobaTestnet: { 399 | chainId: 2888, 400 | url: vars.get("BOBA_TESTNET_URL", "https://goerli.boba.network"), 401 | accounts, 402 | ledgerAccounts, 403 | }, 404 | bobaMain: { 405 | chainId: 288, 406 | url: vars.get("BOBA_MAINNET_URL", "https://replica.boba.network"), 407 | accounts, 408 | ledgerAccounts, 409 | }, 410 | cantoTestnet: { 411 | chainId: 7701, 412 | url: vars.get("CANTO_TESTNET_URL", "https://canto-testnet.plexnode.wtf"), 413 | accounts, 414 | ledgerAccounts, 415 | }, 416 | cantoMain: { 417 | chainId: 7700, 418 | url: vars.get("CANTO_MAINNET_URL", "https://canto.slingshot.finance"), 419 | accounts, 420 | ledgerAccounts, 421 | }, 422 | baseTestnet: { 423 | chainId: 84531, 424 | url: vars.get("BASE_TESTNET_URL", "https://goerli.base.org"), 425 | accounts, 426 | ledgerAccounts, 427 | }, 428 | baseSepolia: { 429 | chainId: 84532, 430 | url: vars.get("BASE_SEPOLIA_URL", "https://sepolia.base.org"), 431 | accounts, 432 | ledgerAccounts, 433 | }, 434 | baseMain: { 435 | chainId: 8453, 436 | url: vars.get("BASE_MAINNET_URL", "https://mainnet.base.org"), 437 | accounts, 438 | ledgerAccounts, 439 | }, 440 | zkSyncTestnet: { 441 | chainId: 300, 442 | url: vars.get("ZKSYNC_TESTNET_URL", "https://sepolia.era.zksync.dev"), 443 | ethNetwork: "sepolia", 444 | zksync: true, 445 | verifyURL: 446 | "https://explorer.sepolia.era.zksync.dev/contract_verification", 447 | browserVerifyURL: "https://sepolia.explorer.zksync.io", 448 | enableVerifyURL: true, 449 | accounts, 450 | ledgerAccounts, 451 | }, 452 | zkSyncMain: { 453 | chainId: 324, 454 | url: vars.get("ZKSYNC_MAINNET_URL", "https://mainnet.era.zksync.io"), 455 | ethNetwork: "mainnet", 456 | zksync: true, 457 | verifyURL: 458 | "https://zksync2-mainnet-explorer.zksync.io/contract_verification", 459 | browserVerifyURL: "https://explorer.zksync.io", 460 | enableVerifyURL: true, 461 | accounts, 462 | ledgerAccounts, 463 | }, 464 | mantleTestnet: { 465 | chainId: 5003, 466 | url: vars.get("MANTLE_TESTNET_URL", "https://rpc.sepolia.mantle.xyz"), 467 | accounts, 468 | ledgerAccounts, 469 | }, 470 | mantleMain: { 471 | chainId: 5000, 472 | url: vars.get("MANTLE_MAINNET_URL", "https://rpc.mantle.xyz"), 473 | accounts, 474 | ledgerAccounts, 475 | }, 476 | filecoinTestnet: { 477 | chainId: 314159, 478 | url: vars.get( 479 | "FILECOIN_TESTNET_URL", 480 | "https://rpc.ankr.com/filecoin_testnet", 481 | ), 482 | accounts, 483 | ledgerAccounts, 484 | }, 485 | filecoinMain: { 486 | chainId: 314, 487 | url: vars.get("FILECOIN_MAINNET_URL", "https://rpc.ankr.com/filecoin"), 488 | accounts, 489 | ledgerAccounts, 490 | }, 491 | scrollTestnet: { 492 | chainId: 534351, 493 | url: vars.get("SCROLL_TESTNET_URL", "https://sepolia-rpc.scroll.io"), 494 | accounts, 495 | ledgerAccounts, 496 | }, 497 | scrollMain: { 498 | chainId: 534352, 499 | url: vars.get("SCROLL_MAINNET_URL", "https://rpc.scroll.io"), 500 | accounts, 501 | ledgerAccounts, 502 | }, 503 | lineaTestnet: { 504 | chainId: 59141, 505 | url: vars.get("LINEA_TESTNET_URL", "https://rpc.sepolia.linea.build"), 506 | accounts, 507 | ledgerAccounts, 508 | }, 509 | lineaMain: { 510 | chainId: 59144, 511 | url: vars.get("LINEA_MAINNET_URL", "https://rpc.linea.build"), 512 | accounts, 513 | ledgerAccounts, 514 | }, 515 | shimmerEVMTestnet: { 516 | chainId: 1071, 517 | url: vars.get( 518 | "SHIMMEREVM_TESTNET_URL", 519 | "https://json-rpc.evm.testnet.shimmer.network", 520 | ), 521 | accounts, 522 | ledgerAccounts, 523 | }, 524 | zoraTestnet: { 525 | chainId: 999999999, 526 | url: vars.get("ZORA_TESTNET_URL", "https://sepolia.rpc.zora.energy"), 527 | accounts, 528 | ledgerAccounts, 529 | }, 530 | zoraMain: { 531 | chainId: 7777777, 532 | url: vars.get("ZORA_MAINNET_URL", "https://rpc.zora.energy"), 533 | accounts, 534 | ledgerAccounts, 535 | }, 536 | luksoTestnet: { 537 | chainId: 4201, 538 | url: vars.get("LUKSO_TESTNET_URL", "https://rpc.testnet.lukso.network"), 539 | accounts, 540 | ledgerAccounts, 541 | }, 542 | luksoMain: { 543 | chainId: 42, 544 | url: vars.get("LUKSO_MAINNET_URL", "https://rpc.lukso.gateway.fm"), 545 | accounts, 546 | ledgerAccounts, 547 | }, 548 | mantaTestnet: { 549 | chainId: 3441006, 550 | url: vars.get( 551 | "MANTA_TESTNET_URL", 552 | "https://pacific-rpc.sepolia-testnet.manta.network/http", 553 | ), 554 | accounts, 555 | ledgerAccounts, 556 | }, 557 | mantaMain: { 558 | chainId: 169, 559 | url: vars.get( 560 | "MANTA_MAINNET_URL", 561 | "https://pacific-rpc.manta.network/http", 562 | ), 563 | accounts, 564 | ledgerAccounts, 565 | }, 566 | shardeumTestnet: { 567 | chainId: 8081, 568 | url: vars.get("SHARDEUM_TESTNET_URL", "https://dapps.shardeum.org"), 569 | accounts, 570 | ledgerAccounts, 571 | }, 572 | artheraTestnet: { 573 | chainId: 10243, 574 | url: vars.get("ARTHERA_TESTNET_URL", "https://rpc-test.arthera.net"), 575 | accounts, 576 | ledgerAccounts, 577 | }, 578 | frameTestnet: { 579 | chainId: 68840142, 580 | url: vars.get("FRAME_TESTNET_URL", "https://rpc.testnet.frame.xyz/http"), 581 | accounts, 582 | ledgerAccounts, 583 | }, 584 | enduranceTestnet: { 585 | chainId: 6480, 586 | url: vars.get( 587 | "ENDURANCE_TESTNET_URL", 588 | "https://myrpctestnet.fusionist.io", 589 | ), 590 | accounts, 591 | ledgerAccounts, 592 | }, 593 | openduranceTestnet: { 594 | chainId: 6480001001, 595 | url: vars.get( 596 | "OPENDURANCE_TESTNET_URL", 597 | "https://rpc-l2-testnet.fusionist.io", 598 | ), 599 | accounts, 600 | ledgerAccounts, 601 | }, 602 | enduranceMain: { 603 | chainId: 648, 604 | url: vars.get( 605 | "ENDURANCE_MAINNET_URL", 606 | "https://rpc-endurance.fusionist.io", 607 | ), 608 | accounts, 609 | ledgerAccounts, 610 | }, 611 | blastTestnet: { 612 | chainId: 168587773, 613 | url: vars.get("BLAST_TESTNET_URL", "https://sepolia.blast.io"), 614 | accounts, 615 | ledgerAccounts, 616 | }, 617 | blastMain: { 618 | chainId: 81457, 619 | url: vars.get("BLAST_MAINNET_URL", "https://rpc.blast.io"), 620 | accounts, 621 | ledgerAccounts, 622 | }, 623 | kromaTestnet: { 624 | chainId: 2358, 625 | url: vars.get("KROMA_TESTNET_URL", "https://api.sepolia.kroma.network"), 626 | accounts, 627 | ledgerAccounts, 628 | }, 629 | kromaMain: { 630 | chainId: 255, 631 | url: vars.get("KROMA_MAINNET_URL", "https://api.kroma.network"), 632 | accounts, 633 | ledgerAccounts, 634 | }, 635 | dosTestnet: { 636 | chainId: 3939, 637 | url: vars.get("DOS_TESTNET_URL", "https://test.doschain.com"), 638 | accounts, 639 | ledgerAccounts, 640 | }, 641 | dosMain: { 642 | chainId: 7979, 643 | url: vars.get("DOS_MAINNET_URL", "https://main.doschain.com"), 644 | accounts, 645 | ledgerAccounts, 646 | }, 647 | fraxtalTestnet: { 648 | chainId: 2522, 649 | url: vars.get("FRAXTAL_TESTNET_URL", "https://rpc.testnet.frax.com"), 650 | accounts, 651 | ledgerAccounts, 652 | }, 653 | fraxtalMain: { 654 | chainId: 252, 655 | url: vars.get("FRAXTAL_MAINNET_URL", "https://rpc.frax.com"), 656 | accounts, 657 | ledgerAccounts, 658 | }, 659 | kavaMain: { 660 | chainId: 2222, 661 | url: vars.get("KAVA_MAINNET_URL", "https://evm.kava-rpc.com"), 662 | accounts, 663 | ledgerAccounts, 664 | }, 665 | metisTestnet: { 666 | chainId: 59902, 667 | url: vars.get("METIS_TESTNET_URL", "https://sepolia.metisdevops.link"), 668 | accounts, 669 | ledgerAccounts, 670 | }, 671 | metisMain: { 672 | chainId: 1088, 673 | url: vars.get( 674 | "METIS_MAINNET_URL", 675 | "https://andromeda.metis.io/?owner=1088", 676 | ), 677 | accounts, 678 | ledgerAccounts, 679 | }, 680 | modeTestnet: { 681 | chainId: 919, 682 | url: vars.get("MODE_TESTNET_URL", "https://sepolia.mode.network"), 683 | accounts, 684 | ledgerAccounts, 685 | }, 686 | modeMain: { 687 | chainId: 34443, 688 | url: vars.get("MODE_MAINNET_URL", "https://mainnet.mode.network"), 689 | accounts, 690 | ledgerAccounts, 691 | }, 692 | seiDevnet: { 693 | chainId: 713715, 694 | url: vars.get("SEI_DEVNET_URL", "https://evm-rpc-arctic-1.sei-apis.com"), 695 | accounts, 696 | ledgerAccounts, 697 | }, 698 | seiTestnet: { 699 | chainId: 1328, 700 | url: vars.get("SEI_TESTNET_URL", "https://evm-rpc-testnet.sei-apis.com"), 701 | accounts, 702 | ledgerAccounts, 703 | }, 704 | seiMain: { 705 | chainId: 1329, 706 | url: vars.get("SEI_MAINNET_URL", "https://evm-rpc.sei-apis.com"), 707 | accounts, 708 | ledgerAccounts, 709 | }, 710 | xlayerTestnet: { 711 | chainId: 195, 712 | url: vars.get("XLAYER_TESTNET_URL", "https://testrpc.xlayer.tech"), 713 | accounts, 714 | ledgerAccounts, 715 | }, 716 | xlayerMain: { 717 | chainId: 196, 718 | url: vars.get("XLAYER_MAINNET_URL", "https://rpc.xlayer.tech"), 719 | accounts, 720 | ledgerAccounts, 721 | }, 722 | bobTestnet: { 723 | chainId: 111, 724 | url: vars.get("BOB_TESTNET_URL", "https://testnet.rpc.gobob.xyz"), 725 | accounts, 726 | ledgerAccounts, 727 | }, 728 | bobMain: { 729 | chainId: 60808, 730 | url: vars.get("BOB_MAINNET_URL", "https://rpc.gobob.xyz"), 731 | accounts, 732 | ledgerAccounts, 733 | }, 734 | coreTestnet: { 735 | chainId: 1115, 736 | url: vars.get("CORE_TESTNET_URL", "https://rpc.test.btcs.network"), 737 | accounts, 738 | ledgerAccounts, 739 | }, 740 | coreMain: { 741 | chainId: 1116, 742 | url: vars.get("CORE_MAINNET_URL", "https://rpc.coredao.org"), 743 | accounts, 744 | ledgerAccounts, 745 | }, 746 | telosTestnet: { 747 | chainId: 41, 748 | url: vars.get("TELOS_TESTNET_URL", "https://testnet.telos.net/evm"), 749 | accounts, 750 | ledgerAccounts, 751 | }, 752 | telosMain: { 753 | chainId: 40, 754 | url: vars.get("TELOS_MAINNET_URL", "https://mainnet.telos.net/evm"), 755 | accounts, 756 | ledgerAccounts, 757 | }, 758 | rootstockTestnet: { 759 | chainId: 31, 760 | url: vars.get( 761 | "ROOTSTOCK_TESTNET_URL", 762 | "https://public-node.testnet.rsk.co", 763 | ), 764 | accounts, 765 | ledgerAccounts, 766 | }, 767 | rootstockMain: { 768 | chainId: 30, 769 | url: vars.get("ROOTSTOCK_MAINNET_URL", "https://public-node.rsk.co"), 770 | accounts, 771 | ledgerAccounts, 772 | }, 773 | chilizTestnet: { 774 | chainId: 88882, 775 | url: vars.get("CHILIZ_TESTNET_URL", "https://spicy-rpc.chiliz.com"), 776 | accounts, 777 | ledgerAccounts, 778 | }, 779 | chilizMain: { 780 | chainId: 88888, 781 | url: vars.get("CHILIZ_MAINNET_URL", "https://rpc.ankr.com/chiliz"), 782 | accounts, 783 | ledgerAccounts, 784 | }, 785 | taraxaTestnet: { 786 | chainId: 842, 787 | url: vars.get("TARAXA_TESTNET_URL", "https://rpc.testnet.taraxa.io"), 788 | accounts, 789 | ledgerAccounts, 790 | }, 791 | taraxaMain: { 792 | chainId: 841, 793 | url: vars.get("TARAXA_MAINNET_URL", "https://rpc.mainnet.taraxa.io"), 794 | accounts, 795 | ledgerAccounts, 796 | }, 797 | gravityAlphaTestnet: { 798 | chainId: 13505, 799 | url: vars.get( 800 | "GRAVITY_ALPHA_TESTNET_URL", 801 | "https://rpc-sepolia.gravity.xyz", 802 | ), 803 | accounts, 804 | ledgerAccounts, 805 | }, 806 | gravityAlphaMain: { 807 | chainId: 1625, 808 | url: vars.get("GRAVITY_ALPHA_MAINNET_URL", "https://rpc.gravity.xyz"), 809 | accounts, 810 | ledgerAccounts, 811 | }, 812 | taikoTestnet: { 813 | chainId: 167009, 814 | url: vars.get("TAIKO_TESTNET_URL", "https://rpc.hekla.taiko.xyz"), 815 | accounts, 816 | ledgerAccounts, 817 | }, 818 | taikoMain: { 819 | chainId: 167000, 820 | url: vars.get("TAIKO_MAINNET_URL", "https://rpc.taiko.xyz"), 821 | accounts, 822 | ledgerAccounts, 823 | }, 824 | zetaChainTestnet: { 825 | chainId: 7001, 826 | url: vars.get("ZETA_CHAIN_TESTNET_URL", "https://7001.rpc.thirdweb.com"), 827 | accounts, 828 | ledgerAccounts, 829 | }, 830 | zetaChainMain: { 831 | chainId: 7000, 832 | url: vars.get("ZETA_CHAIN_MAINNET_URL", "https://7000.rpc.thirdweb.com"), 833 | accounts, 834 | ledgerAccounts, 835 | }, 836 | "5ireChainTestnet": { 837 | chainId: 997, 838 | url: vars.get( 839 | "5IRE_CHAIN_TESTNET_URL", 840 | "https://rpc.testnet.5ire.network", 841 | ), 842 | accounts, 843 | ledgerAccounts, 844 | }, 845 | "5ireChainMain": { 846 | chainId: 995, 847 | url: vars.get("5IRE_CHAIN_MAINNET_URL", "https://rpc.5ire.network"), 848 | accounts, 849 | ledgerAccounts, 850 | }, 851 | sapphireTestnet: { 852 | chainId: 23295, 853 | url: vars.get( 854 | "SAPPHIRE_TESTNET_URL", 855 | "https://testnet.sapphire.oasis.io", 856 | ), 857 | accounts, 858 | ledgerAccounts, 859 | }, 860 | sapphireMain: { 861 | chainId: 23294, 862 | url: vars.get("SAPPHIRE_MAINNET_URL", "https://sapphire.oasis.io"), 863 | accounts, 864 | ledgerAccounts, 865 | }, 866 | worldChainTestnet: { 867 | chainId: 4801, 868 | url: vars.get( 869 | "WORLD_CHAIN_TESTNET_URL", 870 | "https://worldchain-sepolia.g.alchemy.com/public", 871 | ), 872 | accounts, 873 | ledgerAccounts, 874 | }, 875 | worldChainMain: { 876 | chainId: 480, 877 | url: vars.get( 878 | "WORLD_CHAIN_MAINNET_URL", 879 | "https://worldchain-mainnet.g.alchemy.com/public", 880 | ), 881 | accounts, 882 | ledgerAccounts, 883 | }, 884 | plumeTestnet: { 885 | chainId: 98867, 886 | url: vars.get("PLUME_TESTNET_URL", "https://testnet-rpc.plume.org"), 887 | accounts, 888 | ledgerAccounts, 889 | }, 890 | plumeMain: { 891 | chainId: 98866, 892 | url: vars.get("PLUME_MAINNET_URL", "https://rpc.plume.org"), 893 | accounts, 894 | ledgerAccounts, 895 | }, 896 | unichainTestnet: { 897 | chainId: 1301, 898 | url: vars.get("UNICHAIN_TESTNET_URL", "https://sepolia.unichain.org"), 899 | accounts, 900 | ledgerAccounts, 901 | }, 902 | unichainMain: { 903 | chainId: 130, 904 | url: vars.get("UNICHAIN_MAINNET_URL", "https://mainnet.unichain.org"), 905 | accounts, 906 | ledgerAccounts, 907 | }, 908 | xdcTestnet: { 909 | chainId: 51, 910 | url: vars.get("XDC_TESTNET_URL", "https://erpc.apothem.network"), 911 | accounts, 912 | ledgerAccounts, 913 | }, 914 | xdcMain: { 915 | chainId: 50, 916 | url: vars.get("XDC_MAINNET_URL", "https://rpc.xinfin.network"), 917 | accounts, 918 | ledgerAccounts, 919 | }, 920 | sxTestnet: { 921 | chainId: 79479957, 922 | url: vars.get( 923 | "SX_TESTNET_URL", 924 | "https://rpc.sx-rollup-testnet.t.raas.gelato.cloud", 925 | ), 926 | accounts, 927 | ledgerAccounts, 928 | }, 929 | sxMain: { 930 | chainId: 4162, 931 | url: vars.get("SX_MAINNET_URL", "https://rpc.sx-rollup.gelato.digital"), 932 | accounts, 933 | ledgerAccounts, 934 | }, 935 | liskTestnet: { 936 | chainId: 4202, 937 | url: vars.get("LISK_TESTNET_URL", "https://rpc.sepolia-api.lisk.com"), 938 | accounts, 939 | ledgerAccounts, 940 | }, 941 | liskMain: { 942 | chainId: 1135, 943 | url: vars.get("LISK_MAINNET_URL", "https://rpc.api.lisk.com"), 944 | accounts, 945 | ledgerAccounts, 946 | }, 947 | metalL2Testnet: { 948 | chainId: 1740, 949 | url: vars.get("METALL2_TESTNET_URL", "https://testnet.rpc.metall2.com"), 950 | accounts, 951 | ledgerAccounts, 952 | }, 953 | metalL2Main: { 954 | chainId: 1750, 955 | url: vars.get("METALL2_MAINNET_URL", "https://rpc.metall2.com"), 956 | accounts, 957 | ledgerAccounts, 958 | }, 959 | superseedTestnet: { 960 | chainId: 53302, 961 | url: vars.get("SUPERSEED_TESTNET_URL", "https://sepolia.superseed.xyz"), 962 | accounts, 963 | ledgerAccounts, 964 | }, 965 | superseedMain: { 966 | chainId: 5330, 967 | url: vars.get("SUPERSEED_MAINNET_URL", "https://mainnet.superseed.xyz"), 968 | accounts, 969 | ledgerAccounts, 970 | }, 971 | storyTestnet: { 972 | chainId: 1315, 973 | url: vars.get("STORY_TESTNET_URL", "https://aeneid.storyrpc.io"), 974 | accounts, 975 | ledgerAccounts, 976 | }, 977 | sonicTestnet: { 978 | chainId: 57054, 979 | url: vars.get("SONIC_TESTNET_URL", "https://rpc.blaze.soniclabs.com"), 980 | accounts, 981 | ledgerAccounts, 982 | }, 983 | sonicMain: { 984 | chainId: 146, 985 | url: vars.get("SONIC_MAINNET_URL", "https://rpc.soniclabs.com"), 986 | accounts, 987 | ledgerAccounts, 988 | }, 989 | flowTestnet: { 990 | chainId: 545, 991 | url: vars.get("FLOW_TESTNET_URL", "https://testnet.evm.nodes.onflow.org"), 992 | accounts, 993 | ledgerAccounts, 994 | }, 995 | flowMain: { 996 | chainId: 747, 997 | url: vars.get("FLOW_MAINNET_URL", "https://mainnet.evm.nodes.onflow.org"), 998 | accounts, 999 | ledgerAccounts, 1000 | }, 1001 | inkTestnet: { 1002 | chainId: 763373, 1003 | url: vars.get( 1004 | "INK_TESTNET_URL", 1005 | "https://rpc-gel-sepolia.inkonchain.com", 1006 | ), 1007 | accounts, 1008 | ledgerAccounts, 1009 | }, 1010 | inkMain: { 1011 | chainId: 57073, 1012 | url: vars.get("INK_MAINNET_URL", "https://rpc-gel.inkonchain.com"), 1013 | accounts, 1014 | ledgerAccounts, 1015 | }, 1016 | morphTestnet: { 1017 | chainId: 2810, 1018 | url: vars.get( 1019 | "MORPH_TESTNET_URL", 1020 | "https://rpc-quicknode-holesky.morphl2.io", 1021 | ), 1022 | accounts, 1023 | ledgerAccounts, 1024 | }, 1025 | morphMain: { 1026 | chainId: 2818, 1027 | url: vars.get("MORPH_MAINNET_URL", "https://rpc-quicknode.morphl2.io"), 1028 | accounts, 1029 | ledgerAccounts, 1030 | }, 1031 | shapeTestnet: { 1032 | chainId: 11011, 1033 | url: vars.get("SHAPE_TESTNET_URL", "https://sepolia.shape.network"), 1034 | accounts, 1035 | ledgerAccounts, 1036 | }, 1037 | shapeMain: { 1038 | chainId: 360, 1039 | url: vars.get("SHAPE_MAINNET_URL", "https://mainnet.shape.network"), 1040 | accounts, 1041 | ledgerAccounts, 1042 | }, 1043 | etherlinkTestnet: { 1044 | chainId: 128123, 1045 | url: vars.get( 1046 | "ETHERLINK_TESTNET_URL", 1047 | "https://node.ghostnet.etherlink.com", 1048 | ), 1049 | accounts, 1050 | ledgerAccounts, 1051 | }, 1052 | etherlinkMain: { 1053 | chainId: 42793, 1054 | url: vars.get( 1055 | "ETHERLINK_MAINNET_URL", 1056 | "https://node.mainnet.etherlink.com", 1057 | ), 1058 | accounts, 1059 | ledgerAccounts, 1060 | }, 1061 | soneiumTestnet: { 1062 | chainId: 1946, 1063 | url: vars.get("SONEIUM_TESTNET_URL", "https://rpc.minato.soneium.org"), 1064 | accounts, 1065 | ledgerAccounts, 1066 | }, 1067 | soneiumMain: { 1068 | chainId: 1868, 1069 | url: vars.get("SONEIUM_MAINNET_URL", "https://rpc.soneium.org"), 1070 | accounts, 1071 | ledgerAccounts, 1072 | }, 1073 | swellTestnet: { 1074 | chainId: 1924, 1075 | url: vars.get( 1076 | "SWELL_TESTNET_URL", 1077 | "https://swell-testnet.alt.technology", 1078 | ), 1079 | accounts, 1080 | ledgerAccounts, 1081 | }, 1082 | swellMain: { 1083 | chainId: 1923, 1084 | url: vars.get( 1085 | "SWELL_MAINNET_URL", 1086 | "https://swell-mainnet.alt.technology", 1087 | ), 1088 | accounts, 1089 | ledgerAccounts, 1090 | }, 1091 | hemiTestnet: { 1092 | chainId: 743111, 1093 | url: vars.get("HEMI_TESTNET_URL", "https://testnet.rpc.hemi.network/rpc"), 1094 | accounts, 1095 | ledgerAccounts, 1096 | }, 1097 | hemiMain: { 1098 | chainId: 43111, 1099 | url: vars.get("HEMI_MAINNET_URL", "https://rpc.hemi.network/rpc"), 1100 | accounts, 1101 | ledgerAccounts, 1102 | }, 1103 | berachainTestnet: { 1104 | chainId: 80084, 1105 | url: vars.get("BERACHAIN_TESTNET_URL", "https://bartio.drpc.org"), 1106 | accounts, 1107 | ledgerAccounts, 1108 | }, 1109 | berachainMain: { 1110 | chainId: 80094, 1111 | url: vars.get("BERACHAIN_MAINNET_URL", "https://rpc.berachain.com"), 1112 | accounts, 1113 | ledgerAccounts, 1114 | }, 1115 | monadTestnet: { 1116 | chainId: 10143, 1117 | url: vars.get("MONAD_TESTNET_URL", "https://testnet-rpc.monad.xyz"), 1118 | accounts, 1119 | ledgerAccounts, 1120 | }, 1121 | cornTestnet: { 1122 | chainId: 21000001, 1123 | url: vars.get("CORN_TESTNET_URL", "https://testnet.corn-rpc.com"), 1124 | accounts, 1125 | ledgerAccounts, 1126 | }, 1127 | cornMain: { 1128 | chainId: 21000000, 1129 | url: vars.get("CORN_MAINNET_URL", "https://mainnet.corn-rpc.com"), 1130 | accounts, 1131 | ledgerAccounts, 1132 | }, 1133 | arenazTestnet: { 1134 | chainId: 9897, 1135 | url: vars.get( 1136 | "ARENAZ_TESTNET_URL", 1137 | "https://rpc.arena-z.t.raas.gelato.cloud", 1138 | ), 1139 | accounts, 1140 | ledgerAccounts, 1141 | }, 1142 | arenazMain: { 1143 | chainId: 7897, 1144 | url: vars.get("ARENAZ_MAINNET_URL", "https://rpc.arena-z.gg"), 1145 | accounts, 1146 | ledgerAccounts, 1147 | }, 1148 | iotexTestnet: { 1149 | chainId: 4690, 1150 | url: vars.get("IOTEX_TESTNET_URL", "https://babel-api.testnet.iotex.io"), 1151 | accounts, 1152 | ledgerAccounts, 1153 | }, 1154 | iotexMain: { 1155 | chainId: 4689, 1156 | url: vars.get("IOTEX_MAINNET_URL", "https://babel-api.mainnet.iotex.io"), 1157 | accounts, 1158 | ledgerAccounts, 1159 | }, 1160 | hychainTestnet: { 1161 | chainId: 29112, 1162 | url: vars.get( 1163 | "HYCHAIN_TESTNET_URL", 1164 | "https://testnet-rpc.hychain.com/http", 1165 | ), 1166 | accounts, 1167 | ledgerAccounts, 1168 | }, 1169 | hychainMain: { 1170 | chainId: 2911, 1171 | url: vars.get("HYCHAIN_MAINNET_URL", "https://rpc.hychain.com/http"), 1172 | accounts, 1173 | ledgerAccounts, 1174 | }, 1175 | zircuitTestnet: { 1176 | chainId: 48898, 1177 | url: vars.get( 1178 | "ZIRCUIT_TESTNET_URL", 1179 | "https://garfield-testnet.zircuit.com", 1180 | ), 1181 | accounts, 1182 | ledgerAccounts, 1183 | }, 1184 | zircuitMain: { 1185 | chainId: 48900, 1186 | url: vars.get("ZIRCUIT_MAINNET_URL", "https://zircuit-mainnet.drpc.org"), 1187 | accounts, 1188 | ledgerAccounts, 1189 | }, 1190 | megaETHTestnet: { 1191 | chainId: 6342, 1192 | url: vars.get("MEGAETH_TESTNET_URL", "https://carrot.megaeth.com/rpc"), 1193 | accounts, 1194 | ledgerAccounts, 1195 | }, 1196 | bitlayerTestnet: { 1197 | chainId: 200810, 1198 | url: vars.get("BITLAYER_TESTNET_URL", "https://testnet-rpc.bitlayer.org"), 1199 | accounts, 1200 | ledgerAccounts, 1201 | }, 1202 | bitlayerMain: { 1203 | chainId: 200901, 1204 | url: vars.get("BITLAYER_MAINNET_URL", "https://rpc.bitlayer.org"), 1205 | accounts, 1206 | ledgerAccounts, 1207 | }, 1208 | roninTestnet: { 1209 | chainId: 2021, 1210 | url: vars.get( 1211 | "RONIN_TESTNET_URL", 1212 | "https://saigon-testnet.roninchain.com/rpc", 1213 | ), 1214 | accounts, 1215 | ledgerAccounts, 1216 | }, 1217 | roninMain: { 1218 | chainId: 2020, 1219 | url: vars.get("RONIN_MAINNET_URL", "https://api.roninchain.com/rpc"), 1220 | accounts, 1221 | ledgerAccounts, 1222 | }, 1223 | immutableZkEVMTestnet: { 1224 | chainId: 13473, 1225 | url: vars.get( 1226 | "IMMUTABLEZKEVM_TESTNET_URL", 1227 | "https://rpc.testnet.immutable.com", 1228 | ), 1229 | accounts, 1230 | ledgerAccounts, 1231 | }, 1232 | immutableZkEVMMain: { 1233 | chainId: 13371, 1234 | url: vars.get("IMMUTABLEZKEVM_MAINNET_URL", "https://rpc.immutable.com"), 1235 | accounts, 1236 | ledgerAccounts, 1237 | }, 1238 | abstractTestnet: { 1239 | chainId: 11124, 1240 | url: vars.get("ABSTRACT_TESTNET_URL", "https://api.testnet.abs.xyz"), 1241 | accounts, 1242 | ledgerAccounts, 1243 | }, 1244 | abstractMain: { 1245 | chainId: 2741, 1246 | url: vars.get("ABSTRACT_MAINNET_URL", "https://api.mainnet.abs.xyz"), 1247 | accounts, 1248 | ledgerAccounts, 1249 | }, 1250 | hyperevmTestnet: { 1251 | chainId: 998, 1252 | url: vars.get( 1253 | "HYPEREVM_TESTNET_URL", 1254 | "https://rpc.hyperliquid-testnet.xyz/evm", 1255 | ), 1256 | accounts, 1257 | ledgerAccounts, 1258 | }, 1259 | hyperevmMain: { 1260 | chainId: 999, 1261 | url: vars.get("HYPEREVM_MAINNET_URL", "https://rpc.hyperliquid.xyz/evm"), 1262 | accounts, 1263 | ledgerAccounts, 1264 | }, 1265 | kaiaMain: { 1266 | chainId: 8217, 1267 | url: vars.get("KAIA_MAINNET_URL", "https://rpc.ankr.com/kaia"), 1268 | accounts, 1269 | ledgerAccounts, 1270 | }, 1271 | apeChainTestnet: { 1272 | chainId: 33111, 1273 | url: vars.get( 1274 | "APECHAIN_TESTNET_URL", 1275 | "https://curtis.rpc.caldera.xyz/http", 1276 | ), 1277 | accounts, 1278 | ledgerAccounts, 1279 | }, 1280 | apeChainMain: { 1281 | chainId: 33139, 1282 | url: vars.get( 1283 | "APECHAIN_MAINNET_URL", 1284 | "https://apechain.calderachain.xyz/http", 1285 | ), 1286 | accounts, 1287 | ledgerAccounts, 1288 | }, 1289 | }, 1290 | xdeploy: { 1291 | // Change this name to the name of your main contract 1292 | // Does not necessarily have to match the contract file name 1293 | contract: "Greeter", 1294 | 1295 | // Change to `undefined` if your constructor does not have any input arguments 1296 | constructorArgsPath: "./deploy-args.ts", 1297 | 1298 | // The salt must be the same for each EVM chain for which you want to have a single contract address 1299 | // Change the salt if you are doing a re-deployment with the same codebase 1300 | salt: vars.get( 1301 | "SALT", 1302 | // `keccak256("SALT")` 1303 | "0x087ee6a43229fddc3e140062b42bcff0c6d1c5a3bba8123976a59688e7024c25", 1304 | ), 1305 | 1306 | // This is your wallet's private key 1307 | signer: accounts[0], 1308 | 1309 | // Use the network names specified here: https://github.com/pcaversaccio/xdeployer#configuration 1310 | // Use `localhost` or `hardhat` for local testing 1311 | networks: ["hardhat", "sepolia", "optimismSepolia"], 1312 | 1313 | // Use the matching env URL with your chosen RPC in the `.env` file 1314 | rpcUrls: [ 1315 | "hardhat", 1316 | vars.get("ETH_SEPOLIA_TESTNET_URL", "https://rpc.sepolia.org"), 1317 | vars.get("OPTIMISM_SEPOLIA_URL", "https://sepolia.optimism.io"), 1318 | ], 1319 | 1320 | // Maximum limit is 15 * 10 ** 6 or 15,000,000. If the deployments are failing, try increasing this number 1321 | // However, keep in mind that this costs money in a production environment! 1322 | gasLimit: 1.2 * 10 ** 6, 1323 | }, 1324 | contractSizer: { 1325 | alphaSort: true, 1326 | runOnCompile: true, 1327 | disambiguatePaths: false, 1328 | strict: true, 1329 | only: [], 1330 | except: ["CreateX", "Create2DeployerLocal"], 1331 | }, 1332 | gasReporter: { 1333 | enabled: vars.has("REPORT_GAS") ? true : false, 1334 | currency: "USD", 1335 | }, 1336 | abiExporter: { 1337 | path: "./abis", 1338 | runOnCompile: true, 1339 | clear: true, 1340 | flat: false, 1341 | only: [], 1342 | spacing: 2, 1343 | pretty: true, 1344 | }, 1345 | sourcify: { 1346 | // Enable Sourcify verification by default 1347 | enabled: true, 1348 | apiUrl: "https://sourcify.dev/server", 1349 | browserUrl: "https://repo.sourcify.dev", 1350 | }, 1351 | blockscout: { 1352 | // Disable Blockscout verification by default 1353 | // You can use the `customChains` property as in the `etherscan` configuration to add further chains if desired 1354 | enabled: false, 1355 | }, 1356 | etherscan: { 1357 | // Add your own API key by getting an account at etherscan (https://etherscan.io), snowtrace (https://snowtrace.io) etc. 1358 | // This is used for verification purposes when you want to `npx hardhat verify` your contract using Hardhat 1359 | // The same API key works usually for both testnet and mainnet 1360 | apiKey: { 1361 | // For Ethereum testnets & mainnet 1362 | mainnet: vars.get("ETHERSCAN_API_KEY", ""), 1363 | sepolia: vars.get("ETHERSCAN_API_KEY", ""), 1364 | holesky: vars.get("ETHERSCAN_API_KEY", ""), 1365 | hoodi: vars.get("ETHERSCAN_API_KEY", ""), 1366 | // For BSC testnet & mainnet 1367 | bsc: vars.get("BSC_API_KEY", ""), 1368 | bscTestnet: vars.get("BSC_API_KEY", ""), 1369 | // For Heco mainnet 1370 | heco: vars.get("HECO_API_KEY", ""), 1371 | // For Fantom testnet & mainnet 1372 | opera: vars.get("FANTOM_API_KEY", ""), 1373 | ftmTestnet: vars.get("FANTOM_API_KEY", ""), 1374 | // For Optimism testnets & mainnet 1375 | optimisticEthereum: vars.get("OPTIMISM_API_KEY", ""), 1376 | optimisticGoerli: vars.get("OPTIMISM_API_KEY", ""), 1377 | optimisticSepolia: vars.get("OPTIMISM_API_KEY", ""), 1378 | // For Polygon testnets & mainnets 1379 | polygon: vars.get("POLYGON_API_KEY", ""), 1380 | polygonZkEVM: vars.get("POLYGON_ZKEVM_API_KEY", ""), 1381 | polygonAmoy: vars.get("POLYGON_API_KEY", ""), 1382 | polygonZkEVMTestnet: vars.get("POLYGON_ZKEVM_API_KEY", ""), 1383 | // For Arbitrum testnet & mainnets 1384 | arbitrumOne: vars.get("ARBITRUM_API_KEY", ""), 1385 | arbitrumNova: vars.get("ARBITRUM_API_KEY", ""), 1386 | arbitrumSepolia: vars.get("ARBITRUM_API_KEY", ""), 1387 | // For Avalanche testnet & mainnet 1388 | avalanche: vars.get("AVALANCHE_API_KEY", ""), 1389 | avalancheFujiTestnet: vars.get("AVALANCHE_API_KEY", ""), 1390 | // For Moonbeam testnet & mainnets 1391 | moonbeam: vars.get("MOONBEAM_API_KEY", ""), 1392 | moonriver: vars.get("MOONBEAM_API_KEY", ""), 1393 | moonbaseAlpha: vars.get("MOONBEAM_API_KEY", ""), 1394 | // For Celo testnet & mainnet 1395 | celo: vars.get("CELO_API_KEY", ""), 1396 | alfajores: vars.get("CELO_API_KEY", ""), 1397 | // For Harmony testnet & mainnet 1398 | harmony: vars.get("HARMONY_API_KEY", ""), 1399 | harmonyTestnet: vars.get("HARMONY_API_KEY", ""), 1400 | // For Aurora testnet & mainnet 1401 | aurora: vars.get("AURORA_API_KEY", ""), 1402 | auroraTestnet: vars.get("AURORA_API_KEY", ""), 1403 | // For Cronos testnet & mainnet 1404 | cronos: vars.get("CRONOS_API_KEY", ""), 1405 | cronosTestnet: vars.get("CRONOS_API_KEY", ""), 1406 | // For Gnosis/xDai testnet & mainnets 1407 | gnosis: vars.get("GNOSIS_API_KEY", ""), 1408 | xdai: vars.get("GNOSIS_API_KEY", ""), 1409 | chiado: vars.get("GNOSIS_API_KEY", ""), 1410 | // For Fuse testnet & mainnet 1411 | fuse: vars.get("FUSE_API_KEY", ""), 1412 | spark: vars.get("FUSE_API_KEY", ""), 1413 | // For Evmos testnet & mainnet 1414 | evmos: vars.get("EVMOS_API_KEY", ""), 1415 | evmosTestnet: vars.get("EVMOS_API_KEY", ""), 1416 | // For Boba network testnet & mainnet 1417 | boba: vars.get("BOBA_API_KEY", ""), 1418 | bobaTestnet: vars.get("BOBA_API_KEY", ""), 1419 | // For Canto testnet & mainnet 1420 | canto: vars.get("CANTO_API_KEY", ""), 1421 | cantoTestnet: vars.get("CANTO_API_KEY", ""), 1422 | // For Base testnets & mainnet 1423 | base: vars.get("BASE_API_KEY", ""), 1424 | baseTestnet: vars.get("BASE_API_KEY", ""), 1425 | baseSepolia: vars.get("BASE_API_KEY", ""), 1426 | // For Mantle testnet & mainnet 1427 | mantle: vars.get("MANTLE_API_KEY", ""), 1428 | mantleTestnet: vars.get("MANTLE_API_KEY", ""), 1429 | // For Filecoin testnet & mainnet 1430 | filecoin: vars.get("FILECOIN_API_KEY", ""), 1431 | filecoinTestnet: vars.get("FILECOIN_API_KEY", ""), 1432 | // For Scroll testnet & mainnet 1433 | scroll: vars.get("SCROLL_API_KEY", ""), 1434 | scrollTestnet: vars.get("SCROLL_API_KEY", ""), 1435 | // For Linea testnet & mainnet 1436 | linea: vars.get("LINEA_API_KEY", ""), 1437 | lineaTestnet: vars.get("LINEA_API_KEY", ""), 1438 | // For ShimmerEVM testnet 1439 | shimmerEVMTestnet: vars.get("SHIMMEREVM_API_KEY", ""), 1440 | // For Zora testnet & mainnet 1441 | zora: vars.get("ZORA_API_KEY", ""), 1442 | zoraTestnet: vars.get("ZORA_API_KEY", ""), 1443 | // For Lukso testnet & mainnet 1444 | lukso: vars.get("LUKSO_API_KEY", ""), 1445 | luksoTestnet: vars.get("LUKSO_API_KEY", ""), 1446 | // For Manta testnet & mainnet 1447 | manta: vars.get("MANTA_API_KEY", ""), 1448 | mantaTestnet: vars.get("MANTA_API_KEY", ""), 1449 | // For Arthera testnet 1450 | artheraTestnet: vars.get("ARTHERA_API_KEY", ""), 1451 | // For Endurance testnets & mainnet 1452 | endurance: vars.get("ENDURANCE_API_KEY", ""), 1453 | enduranceTestnet: vars.get("ENDURANCE_API_KEY", ""), 1454 | openduranceTestnet: vars.get("OPENDURANCE_API_KEY", ""), 1455 | // For Blast testnet & mainnet 1456 | blast: vars.get("BLAST_API_KEY", ""), 1457 | blastTestnet: vars.get("BLAST_API_KEY", ""), 1458 | // For Kroma testnet & mainnet 1459 | kroma: vars.get("KROMA_API_KEY", ""), 1460 | kromaTestnet: vars.get("KROMA_API_KEY", ""), 1461 | // For DOS Chain testnet & mainnet 1462 | dos: vars.get("DOS_API_KEY", ""), 1463 | dosTestnet: vars.get("DOS_API_KEY", ""), 1464 | // For Fraxtal testnet & mainnet 1465 | fraxtal: vars.get("FRAXTAL_API_KEY", ""), 1466 | fraxtalTestnet: vars.get("FRAXTAL_API_KEY", ""), 1467 | // For Kava mainnet 1468 | kava: vars.get("KAVA_API_KEY", ""), 1469 | // For Metis testnet & mainnet 1470 | metis: vars.get("METIS_API_KEY", ""), 1471 | metisTestnet: vars.get("METIS_API_KEY", ""), 1472 | // For Mode testnet & mainnet 1473 | mode: vars.get("MODE_API_KEY", ""), 1474 | modeTestnet: vars.get("MODE_API_KEY", ""), 1475 | // For X Layer testnet & mainnet 1476 | xlayer: vars.get("OKLINK_API_KEY", ""), 1477 | xlayerTestnet: vars.get("OKLINK_API_KEY", ""), 1478 | // For BOB testnet & mainnet 1479 | bob: vars.get("BOB_API_KEY", ""), 1480 | bobTestnet: vars.get("BOB_API_KEY", ""), 1481 | // For Core testnet & mainnet 1482 | core: vars.get("CORE_MAINNET_API_KEY", ""), 1483 | coreTestnet: vars.get("CORE_TESTNET_API_KEY", ""), 1484 | // For Telos testnet & mainnet 1485 | telos: vars.get("TELOS_API_KEY", ""), 1486 | telosTestnet: vars.get("TELOS_API_KEY", ""), 1487 | // For Rootstock testnet & mainnet 1488 | rootstock: vars.get("ROOTSTOCK_API_KEY", ""), 1489 | rootstockTestnet: vars.get("ROOTSTOCK_API_KEY", ""), 1490 | // For Chiliz testnet & mainnet 1491 | chiliz: vars.get("CHILIZ_API_KEY", ""), 1492 | chilizTestnet: vars.get("CHILIZ_API_KEY", ""), 1493 | // For Gravity Alpha testnet & mainnet 1494 | gravityAlpha: vars.get("GRAVITY_ALPHA_API_KEY", ""), 1495 | gravityAlphaTestnet: vars.get("GRAVITY_ALPHA_API_KEY", ""), 1496 | // For Taiko testnet & mainnet 1497 | taiko: vars.get("TAIKO_API_KEY", ""), 1498 | taikoTestnet: vars.get("TAIKO_API_KEY", ""), 1499 | // For ZetaChain testnet & mainnet 1500 | zetaChain: vars.get("ZETA_CHAIN_API_KEY", ""), 1501 | zetaChainTestnet: vars.get("ZETA_CHAIN_API_KEY", ""), 1502 | // For 5ireChain testnet & mainnet 1503 | "5ireChain": vars.get("5IRE_CHAIN_API_KEY", ""), 1504 | "5ireChainTestnet": vars.get("5IRE_CHAIN_API_KEY", ""), 1505 | // For Oasis Sapphire testnet & mainnet 1506 | sapphire: vars.get("SAPPHIRE_API_KEY", ""), 1507 | sapphireTestnet: vars.get("SAPPHIRE_API_KEY", ""), 1508 | // For World Chain testnet & mainnet 1509 | worldChain: vars.get("WORLD_CHAIN_API_KEY", ""), 1510 | worldChainTestnet: vars.get("WORLD_CHAIN_API_KEY", ""), 1511 | // For Plume testnet & mainnet 1512 | plume: vars.get("PLUME_API_KEY", ""), 1513 | plumeTestnet: vars.get("PLUME_API_KEY", ""), 1514 | // For Unichain testnet & mainnet 1515 | unichain: vars.get("UNICHAIN_API_KEY", ""), 1516 | unichainTestnet: vars.get("UNICHAIN_API_KEY", ""), 1517 | // For XDC testnet & mainnet 1518 | xdc: vars.get("XDC_API_KEY", ""), 1519 | xdcTestnet: vars.get("XDC_API_KEY", ""), 1520 | // For SX testnet & mainnet 1521 | sx: vars.get("SX_API_KEY", ""), 1522 | sxTestnet: vars.get("SX_API_KEY", ""), 1523 | // For ZKsync testnet & mainnet 1524 | zkSync: vars.get("ZKSYNC_API_KEY", ""), 1525 | zkSyncTestnet: vars.get("ZKSYNC_API_KEY", ""), 1526 | // For Lisk testnet & mainnet 1527 | lisk: vars.get("LISK_API_KEY", ""), 1528 | liskTestnet: vars.get("LISK_API_KEY", ""), 1529 | // For Metal L2 testnet & mainnet 1530 | metalL2: vars.get("METALL2_API_KEY", ""), 1531 | metalL2Testnet: vars.get("METALL2_API_KEY", ""), 1532 | // For Superseed testnet & mainnet 1533 | superseed: vars.get("SUPERSEED_API_KEY", ""), 1534 | superseedTestnet: vars.get("SUPERSEED_API_KEY", ""), 1535 | // For Story testnet 1536 | storyTestnet: vars.get("STORY_API_KEY", ""), 1537 | // For Sonic testnet & mainnet 1538 | sonic: vars.get("SONIC_API_KEY", ""), 1539 | sonicTestnet: vars.get("SONIC_API_KEY", ""), 1540 | // For EVM on Flow testnet & mainnet 1541 | flow: vars.get("FLOW_API_KEY", ""), 1542 | flowTestnet: vars.get("FLOW_API_KEY", ""), 1543 | // For Ink testnet & mainnet 1544 | ink: vars.get("INK_API_KEY", ""), 1545 | inkTestnet: vars.get("INK_API_KEY", ""), 1546 | // For Morph testnet & mainnet 1547 | morph: vars.get("MORPH_API_KEY", ""), 1548 | morphTestnet: vars.get("MORPH_API_KEY", ""), 1549 | // For Shape testnet & mainnet 1550 | shape: vars.get("SHAPE_API_KEY", ""), 1551 | shapeTestnet: vars.get("SHAPE_API_KEY", ""), 1552 | // For Etherlink testnet & mainnet 1553 | etherlink: vars.get("ETHERLINK_API_KEY", ""), 1554 | etherlinkTestnet: vars.get("ETHERLINK_API_KEY", ""), 1555 | // For Soneium testnet & mainnet 1556 | soneium: vars.get("SONEIUM_API_KEY", ""), 1557 | soneiumTestnet: vars.get("SONEIUM_API_KEY", ""), 1558 | // For Swellchain testnet & mainnet 1559 | swell: vars.get("SWELL_API_KEY", ""), 1560 | swellTestnet: vars.get("SWELL_API_KEY", ""), 1561 | // For Hemi testnet & mainnet 1562 | hemi: vars.get("HEMI_API_KEY", ""), 1563 | hemiTestnet: vars.get("HEMI_API_KEY", ""), 1564 | // For Berachain testnet & mainnet 1565 | berachain: vars.get("BERACHAIN_API_KEY", ""), 1566 | berachainTestnet: vars.get("BERACHAIN_API_KEY", ""), 1567 | // For Corn testnet & mainnet 1568 | corn: vars.get("CORN_API_KEY", ""), 1569 | cornTestnet: vars.get("CORN_API_KEY", ""), 1570 | // For Arena-Z testnet & mainnet 1571 | arenaz: vars.get("ARENAZ_API_KEY", ""), 1572 | arenazTestnet: vars.get("ARENAZ_API_KEY", ""), 1573 | // For IoTeX testnet & mainnet 1574 | iotex: vars.get("IOTEX_API_KEY", ""), 1575 | iotexTestnet: vars.get("IOTEX_API_KEY", ""), 1576 | // For HYCHAIN testnet & mainnet 1577 | hychain: vars.get("HYCHAIN_API_KEY", ""), 1578 | hychainTestnet: vars.get("HYCHAIN_API_KEY", ""), 1579 | // For Zircuit testnet & mainnet 1580 | zircuit: vars.get("ZIRCUIT_API_KEY", ""), 1581 | zircuitTestnet: vars.get("ZIRCUIT_API_KEY", ""), 1582 | // For Bitlayer testnet & mainnet 1583 | bitlayer: vars.get("BITLAYER_API_KEY", ""), 1584 | bitlayerTestnet: vars.get("BITLAYER_API_KEY", ""), 1585 | // For Immutable zkEVM testnet & mainnet 1586 | immutableZkEVM: vars.get("IMMUTABLEZKEVM_API_KEY", ""), 1587 | immutableZkEVMTestnet: vars.get("IMMUTABLEZKEVM_API_KEY", ""), 1588 | // For Abstract testnet & mainnet 1589 | abstract: vars.get("ABSTRACT_API_KEY", ""), 1590 | abstractTestnet: vars.get("ABSTRACT_API_KEY", ""), 1591 | // For Kaia mainnet 1592 | kaia: vars.get("OKLINK_API_KEY", ""), 1593 | // For ApeChain testnet & mainnet 1594 | apeChain: vars.get("APECHAIN_API_KEY", ""), 1595 | apeChainTestnet: vars.get("APECHAIN_API_KEY", ""), 1596 | }, 1597 | customChains: [ 1598 | { 1599 | network: "holesky", 1600 | chainId: 17000, 1601 | urls: { 1602 | apiURL: "https://api-holesky.etherscan.io/api", 1603 | browserURL: "https://holesky.etherscan.io", 1604 | }, 1605 | }, 1606 | { 1607 | network: "hoodi", 1608 | chainId: 560048, 1609 | urls: { 1610 | apiURL: "https://api-hoodi.etherscan.io/api", 1611 | browserURL: "https://hoodi.etherscan.io", 1612 | }, 1613 | }, 1614 | { 1615 | network: "optimisticSepolia", 1616 | chainId: 11155420, 1617 | urls: { 1618 | apiURL: "https://api-sepolia-optimistic.etherscan.io/api", 1619 | browserURL: "https://sepolia-optimism.etherscan.io", 1620 | }, 1621 | }, 1622 | { 1623 | network: "chiado", 1624 | chainId: 10200, 1625 | urls: { 1626 | apiURL: "https://gnosis-chiado.blockscout.com/api", 1627 | browserURL: "https://gnosis-chiado.blockscout.com", 1628 | }, 1629 | }, 1630 | { 1631 | network: "celo", 1632 | chainId: 42220, 1633 | urls: { 1634 | apiURL: "https://api.celoscan.io/api", 1635 | browserURL: "https://celoscan.io", 1636 | }, 1637 | }, 1638 | { 1639 | network: "alfajores", 1640 | chainId: 44787, 1641 | urls: { 1642 | apiURL: "https://api-alfajores.celoscan.io/api", 1643 | browserURL: "https://alfajores.celoscan.io", 1644 | }, 1645 | }, 1646 | { 1647 | network: "cronos", 1648 | chainId: 25, 1649 | urls: { 1650 | apiURL: "https://api.cronoscan.com/api", 1651 | browserURL: "https://cronoscan.com", 1652 | }, 1653 | }, 1654 | { 1655 | network: "cronosTestnet", 1656 | chainId: 338, 1657 | urls: { 1658 | apiURL: "https://cronos.org/explorer/testnet3/api", 1659 | browserURL: "https://cronos.org/explorer/testnet3", 1660 | }, 1661 | }, 1662 | { 1663 | network: "fuse", 1664 | chainId: 122, 1665 | urls: { 1666 | apiURL: "https://explorer.fuse.io/api", 1667 | browserURL: "https://explorer.fuse.io", 1668 | }, 1669 | }, 1670 | { 1671 | network: "spark", 1672 | chainId: 123, 1673 | urls: { 1674 | apiURL: "https://explorer.fusespark.io/api", 1675 | browserURL: "https://explorer.fusespark.io", 1676 | }, 1677 | }, 1678 | { 1679 | network: "evmos", 1680 | chainId: 9001, 1681 | urls: { 1682 | apiURL: "https://api.verify.mintscan.io/evm/api/0x2329", 1683 | browserURL: "https://www.mintscan.io/evmos", 1684 | }, 1685 | }, 1686 | { 1687 | network: "evmosTestnet", 1688 | chainId: 9000, 1689 | urls: { 1690 | apiURL: "https://api.verify.mintscan.io/evm/api/0x2328", 1691 | browserURL: "https://www.mintscan.io/evmos-testnet", 1692 | }, 1693 | }, 1694 | { 1695 | network: "boba", 1696 | chainId: 288, 1697 | urls: { 1698 | apiURL: 1699 | "https://api.routescan.io/v2/network/mainnet/evm/288/etherscan", 1700 | browserURL: "https://bobascan.com", 1701 | }, 1702 | }, 1703 | { 1704 | network: "bobaTestnet", 1705 | chainId: 2888, 1706 | urls: { 1707 | apiURL: 1708 | "https://api.routescan.io/v2/network/testnet/evm/2888/etherscan", 1709 | browserURL: "https://testnet.bobascan.com", 1710 | }, 1711 | }, 1712 | { 1713 | network: "arbitrumNova", 1714 | chainId: 42170, 1715 | urls: { 1716 | apiURL: "https://api-nova.arbiscan.io/api", 1717 | browserURL: "https://nova.arbiscan.io", 1718 | }, 1719 | }, 1720 | { 1721 | network: "arbitrumSepolia", 1722 | chainId: 421614, 1723 | urls: { 1724 | apiURL: "https://api-sepolia.arbiscan.io/api", 1725 | browserURL: "https://sepolia.arbiscan.io", 1726 | }, 1727 | }, 1728 | { 1729 | network: "canto", 1730 | chainId: 7700, 1731 | urls: { 1732 | apiURL: "https://tuber.build/api", 1733 | browserURL: "https://tuber.build", 1734 | }, 1735 | }, 1736 | { 1737 | network: "cantoTestnet", 1738 | chainId: 7701, 1739 | urls: { 1740 | apiURL: "https://testnet.tuber.build/api", 1741 | browserURL: "https://testnet.tuber.build", 1742 | }, 1743 | }, 1744 | { 1745 | network: "base", 1746 | chainId: 8453, 1747 | urls: { 1748 | apiURL: "https://api.basescan.org/api", 1749 | browserURL: "https://basescan.org", 1750 | }, 1751 | }, 1752 | { 1753 | network: "baseTestnet", 1754 | chainId: 84531, 1755 | urls: { 1756 | apiURL: "https://api-goerli.basescan.org/api", 1757 | browserURL: "https://goerli.basescan.org", 1758 | }, 1759 | }, 1760 | { 1761 | network: "baseSepolia", 1762 | chainId: 84532, 1763 | urls: { 1764 | apiURL: "https://api-sepolia.basescan.org/api", 1765 | browserURL: "https://sepolia.basescan.org", 1766 | }, 1767 | }, 1768 | { 1769 | network: "mantle", 1770 | chainId: 5000, 1771 | urls: { 1772 | apiURL: "https://api.mantlescan.xyz/api", 1773 | browserURL: "https://mantlescan.xyz", 1774 | }, 1775 | }, 1776 | { 1777 | network: "mantleTestnet", 1778 | chainId: 5003, 1779 | urls: { 1780 | apiURL: "https://api-sepolia.mantlescan.xyz/api", 1781 | browserURL: "https://sepolia.mantlescan.xyz", 1782 | }, 1783 | }, 1784 | { 1785 | network: "filecoin", 1786 | chainId: 314, 1787 | urls: { 1788 | apiURL: "https://filfox.info/api/v1/tools/verifyContract", 1789 | browserURL: "https://filfox.info/en", 1790 | }, 1791 | }, 1792 | { 1793 | network: "filecoinTestnet", 1794 | chainId: 314159, 1795 | urls: { 1796 | apiURL: "https://calibration.filfox.info/api/v1/tools/verifyContract", 1797 | browserURL: "https://calibration.filfox.info/en", 1798 | }, 1799 | }, 1800 | { 1801 | network: "scroll", 1802 | chainId: 534352, 1803 | urls: { 1804 | apiURL: "https://api.scrollscan.com/api", 1805 | browserURL: "https://scrollscan.com", 1806 | }, 1807 | }, 1808 | { 1809 | network: "scrollTestnet", 1810 | chainId: 534351, 1811 | urls: { 1812 | apiURL: "https://api-sepolia.scrollscan.com/api", 1813 | browserURL: "https://sepolia.scrollscan.com", 1814 | }, 1815 | }, 1816 | { 1817 | network: "polygonZkEVM", 1818 | chainId: 1101, 1819 | urls: { 1820 | apiURL: "https://api-zkevm.polygonscan.com/api", 1821 | browserURL: "https://zkevm.polygonscan.com", 1822 | }, 1823 | }, 1824 | { 1825 | network: "polygonAmoy", 1826 | chainId: 80002, 1827 | urls: { 1828 | apiURL: "https://api-amoy.polygonscan.com/api", 1829 | browserURL: "https://amoy.polygonscan.com", 1830 | }, 1831 | }, 1832 | { 1833 | network: "polygonZkEVMTestnet", 1834 | chainId: 2442, 1835 | urls: { 1836 | apiURL: "https://api-cardona-zkevm.polygonscan.com/api", 1837 | browserURL: "https://cardona-zkevm.polygonscan.com", 1838 | }, 1839 | }, 1840 | { 1841 | network: "linea", 1842 | chainId: 59144, 1843 | urls: { 1844 | apiURL: "https://api.lineascan.build/api", 1845 | browserURL: "https://lineascan.build", 1846 | }, 1847 | }, 1848 | { 1849 | network: "lineaTestnet", 1850 | chainId: 59141, 1851 | urls: { 1852 | apiURL: "https://api-sepolia.lineascan.build/api", 1853 | browserURL: "https://sepolia.lineascan.build", 1854 | }, 1855 | }, 1856 | { 1857 | network: "shimmerEVMTestnet", 1858 | chainId: 1071, 1859 | urls: { 1860 | apiURL: "https://explorer.evm.testnet.shimmer.network/api", 1861 | browserURL: "https://explorer.evm.testnet.shimmer.network", 1862 | }, 1863 | }, 1864 | { 1865 | network: "zora", 1866 | chainId: 7777777, 1867 | urls: { 1868 | apiURL: "https://explorer.zora.energy/api", 1869 | browserURL: "https://explorer.zora.energy", 1870 | }, 1871 | }, 1872 | { 1873 | network: "zoraTestnet", 1874 | chainId: 999999999, 1875 | urls: { 1876 | apiURL: "https://sepolia.explorer.zora.energy/api", 1877 | browserURL: "https://sepolia.explorer.zora.energy", 1878 | }, 1879 | }, 1880 | { 1881 | network: "lukso", 1882 | chainId: 42, 1883 | urls: { 1884 | apiURL: "https://explorer.execution.mainnet.lukso.network/api", 1885 | browserURL: "https://explorer.execution.mainnet.lukso.network", 1886 | }, 1887 | }, 1888 | { 1889 | network: "luksoTestnet", 1890 | chainId: 4201, 1891 | urls: { 1892 | apiURL: "https://explorer.execution.testnet.lukso.network/api", 1893 | browserURL: "https://explorer.execution.testnet.lukso.network", 1894 | }, 1895 | }, 1896 | { 1897 | network: "manta", 1898 | chainId: 169, 1899 | urls: { 1900 | apiURL: "https://pacific-explorer.manta.network/api", 1901 | browserURL: "https://pacific-explorer.manta.network", 1902 | }, 1903 | }, 1904 | { 1905 | network: "mantaTestnet", 1906 | chainId: 3441006, 1907 | urls: { 1908 | apiURL: "https://pacific-explorer.sepolia-testnet.manta.network/api", 1909 | browserURL: "https://pacific-explorer.sepolia-testnet.manta.network", 1910 | }, 1911 | }, 1912 | { 1913 | network: "artheraTestnet", 1914 | chainId: 10243, 1915 | urls: { 1916 | apiURL: "https://explorer-test.arthera.net/api", 1917 | browserURL: "https://explorer-test.arthera.net", 1918 | }, 1919 | }, 1920 | { 1921 | network: "endurance", 1922 | chainId: 648, 1923 | urls: { 1924 | apiURL: "https://explorer-endurance.fusionist.io/api", 1925 | browserURL: "https://explorer-endurance.fusionist.io", 1926 | }, 1927 | }, 1928 | { 1929 | network: "enduranceTestnet", 1930 | chainId: 6480, 1931 | urls: { 1932 | apiURL: "https://myexplorertestnet.fusionist.io/api", 1933 | browserURL: "https://myexplorertestnet.fusionist.io", 1934 | }, 1935 | }, 1936 | { 1937 | network: "openduranceTestnet", 1938 | chainId: 6480001001, 1939 | urls: { 1940 | apiURL: "https://explorer-l2-testnet.fusionist.io/api", 1941 | browserURL: "https://explorer-l2-testnet.fusionist.io", 1942 | }, 1943 | }, 1944 | { 1945 | network: "blast", 1946 | chainId: 81457, 1947 | urls: { 1948 | apiURL: "https://api.blastscan.io/api", 1949 | browserURL: "https://blastscan.io", 1950 | }, 1951 | }, 1952 | { 1953 | network: "blastTestnet", 1954 | chainId: 168587773, 1955 | urls: { 1956 | apiURL: "https://api-sepolia.blastscan.io/api", 1957 | browserURL: "https://sepolia.blastscan.io", 1958 | }, 1959 | }, 1960 | { 1961 | network: "kroma", 1962 | chainId: 255, 1963 | urls: { 1964 | apiURL: "https://api.kromascan.com/api", 1965 | browserURL: "https://kromascan.com", 1966 | }, 1967 | }, 1968 | { 1969 | network: "kromaTestnet", 1970 | chainId: 2358, 1971 | urls: { 1972 | apiURL: "https://api-sepolia.kromascan.com", 1973 | browserURL: "https://sepolia.kromascan.com", 1974 | }, 1975 | }, 1976 | { 1977 | network: "dos", 1978 | chainId: 7979, 1979 | urls: { 1980 | apiURL: "https://doscan.io/api", 1981 | browserURL: "https://doscan.io", 1982 | }, 1983 | }, 1984 | { 1985 | network: "dosTestnet", 1986 | chainId: 3939, 1987 | urls: { 1988 | apiURL: "https://test.doscan.io/api", 1989 | browserURL: "https://test.doscan.io", 1990 | }, 1991 | }, 1992 | { 1993 | network: "fraxtal", 1994 | chainId: 252, 1995 | urls: { 1996 | apiURL: "https://api.fraxscan.com/api", 1997 | browserURL: "https://fraxscan.com", 1998 | }, 1999 | }, 2000 | { 2001 | network: "fraxtalTestnet", 2002 | chainId: 2522, 2003 | urls: { 2004 | apiURL: "https://api-holesky.fraxscan.com/api", 2005 | browserURL: "https://holesky.fraxscan.com", 2006 | }, 2007 | }, 2008 | { 2009 | network: "kava", 2010 | chainId: 2222, 2011 | urls: { 2012 | apiURL: "https://kavascan.com/api", 2013 | browserURL: "https://kavascan.com", 2014 | }, 2015 | }, 2016 | { 2017 | network: "metis", 2018 | chainId: 1088, 2019 | urls: { 2020 | apiURL: "https://andromeda-explorer.metis.io/api", 2021 | browserURL: "https://andromeda-explorer.metis.io", 2022 | }, 2023 | }, 2024 | { 2025 | network: "metisTestnet", 2026 | chainId: 59902, 2027 | urls: { 2028 | apiURL: "https://sepolia-explorer.metisdevops.link/api", 2029 | browserURL: "https://sepolia-explorer.metisdevops.link", 2030 | }, 2031 | }, 2032 | { 2033 | network: "mode", 2034 | chainId: 34443, 2035 | urls: { 2036 | apiURL: "https://explorer.mode.network/api", 2037 | browserURL: "https://explorer.mode.network", 2038 | }, 2039 | }, 2040 | { 2041 | network: "modeTestnet", 2042 | chainId: 919, 2043 | urls: { 2044 | apiURL: "https://sepolia.explorer.mode.network/api", 2045 | browserURL: "https://sepolia.explorer.mode.network", 2046 | }, 2047 | }, 2048 | { 2049 | network: "xlayer", 2050 | chainId: 196, 2051 | urls: { 2052 | apiURL: 2053 | "https://www.oklink.com/api/v5/explorer/contract/verify-source-code-plugin/XLAYER", 2054 | browserURL: "https://www.oklink.com/x-layer", 2055 | }, 2056 | }, 2057 | { 2058 | network: "xlayerTestnet", 2059 | chainId: 195, 2060 | urls: { 2061 | apiURL: 2062 | "https://www.oklink.com/api/v5/explorer/contract/verify-source-code-plugin/XLAYER_TESTNET", 2063 | browserURL: "https://www.oklink.com/x-layer-testnet", 2064 | }, 2065 | }, 2066 | { 2067 | network: "bob", 2068 | chainId: 60808, 2069 | urls: { 2070 | apiURL: "https://explorer.gobob.xyz/api", 2071 | browserURL: "https://explorer.gobob.xyz", 2072 | }, 2073 | }, 2074 | { 2075 | network: "bobTestnet", 2076 | chainId: 111, 2077 | urls: { 2078 | apiURL: "https://testnet-explorer.gobob.xyz/api", 2079 | browserURL: "https://testnet-explorer.gobob.xyz", 2080 | }, 2081 | }, 2082 | { 2083 | network: "core", 2084 | chainId: 1116, 2085 | urls: { 2086 | apiURL: "https://openapi.coredao.org/api", 2087 | browserURL: "https://scan.coredao.org", 2088 | }, 2089 | }, 2090 | { 2091 | network: "coreTestnet", 2092 | chainId: 1115, 2093 | urls: { 2094 | apiURL: "https://api.test.btcs.network/api", 2095 | browserURL: "https://scan.test.btcs.network", 2096 | }, 2097 | }, 2098 | { 2099 | network: "telos", 2100 | chainId: 40, 2101 | urls: { 2102 | apiURL: "https://api.teloscan.io/api", 2103 | browserURL: "https://www.teloscan.io", 2104 | }, 2105 | }, 2106 | { 2107 | network: "telosTestnet", 2108 | chainId: 41, 2109 | urls: { 2110 | apiURL: "https://api.testnet.teloscan.io/api", 2111 | browserURL: "https://testnet.teloscan.io", 2112 | }, 2113 | }, 2114 | { 2115 | network: "rootstock", 2116 | chainId: 30, 2117 | urls: { 2118 | apiURL: "https://rootstock.blockscout.com/api", 2119 | browserURL: "https://rootstock.blockscout.com", 2120 | }, 2121 | }, 2122 | { 2123 | network: "rootstockTestnet", 2124 | chainId: 31, 2125 | urls: { 2126 | apiURL: "https://rootstock-testnet.blockscout.com/api", 2127 | browserURL: "https://rootstock-testnet.blockscout.com", 2128 | }, 2129 | }, 2130 | { 2131 | network: "chiliz", 2132 | chainId: 88888, 2133 | urls: { 2134 | apiURL: 2135 | "https://api.routescan.io/v2/network/mainnet/evm/88888/etherscan/api", 2136 | browserURL: "https://chiliscan.com", 2137 | }, 2138 | }, 2139 | { 2140 | network: "chilizTestnet", 2141 | chainId: 88882, 2142 | urls: { 2143 | apiURL: 2144 | "https://api.routescan.io/v2/network/testnet/evm/88882/etherscan/api", 2145 | browserURL: "https://testnet.chiliscan.com", 2146 | }, 2147 | }, 2148 | { 2149 | network: "harmony", 2150 | chainId: 1666600000, 2151 | urls: { 2152 | apiURL: "https://explorer.harmony.one/api", 2153 | browserURL: "https://explorer.harmony.one", 2154 | }, 2155 | }, 2156 | { 2157 | network: "harmonyTestnet", 2158 | chainId: 1666700000, 2159 | urls: { 2160 | apiURL: "https://explorer.testnet.harmony.one/api", 2161 | browserURL: "https://explorer.testnet.harmony.one", 2162 | }, 2163 | }, 2164 | { 2165 | network: "gravityAlpha", 2166 | chainId: 1625, 2167 | urls: { 2168 | apiURL: "https://explorer.gravity.xyz/api", 2169 | browserURL: "https://explorer.gravity.xyz", 2170 | }, 2171 | }, 2172 | { 2173 | network: "gravityAlphaTestnet", 2174 | chainId: 13505, 2175 | urls: { 2176 | apiURL: "https://explorer-sepolia.gravity.xyz/api", 2177 | browserURL: "https://explorer-sepolia.gravity.xyz", 2178 | }, 2179 | }, 2180 | { 2181 | network: "taiko", 2182 | chainId: 167000, 2183 | urls: { 2184 | apiURL: "https://api.taikoscan.io/api", 2185 | browserURL: "https://taikoscan.io", 2186 | }, 2187 | }, 2188 | { 2189 | network: "taikoTestnet", 2190 | chainId: 167009, 2191 | urls: { 2192 | apiURL: "https://api-hekla.taikoscan.io/api", 2193 | browserURL: "https://hekla.taikoscan.io", 2194 | }, 2195 | }, 2196 | { 2197 | network: "zetaChain", 2198 | chainId: 7000, 2199 | urls: { 2200 | apiURL: "https://zetachain.blockscout.com/api", 2201 | browserURL: "https://zetachain.blockscout.com", 2202 | }, 2203 | }, 2204 | { 2205 | network: "zetaChainTestnet", 2206 | chainId: 7001, 2207 | urls: { 2208 | apiURL: "https://zetachain-athens-3.blockscout.com/api", 2209 | browserURL: "https://zetachain-athens-3.blockscout.com", 2210 | }, 2211 | }, 2212 | { 2213 | network: "5ireChain", 2214 | chainId: 995, 2215 | urls: { 2216 | apiURL: "https://5irescan.io/api", 2217 | browserURL: "https://5irescan.io", 2218 | }, 2219 | }, 2220 | { 2221 | network: "5ireChainTestnet", 2222 | chainId: 997, 2223 | urls: { 2224 | apiURL: "https://testnet.5irescan.io/api", 2225 | browserURL: "https://testnet.5irescan.io", 2226 | }, 2227 | }, 2228 | { 2229 | network: "sapphire", 2230 | chainId: 23294, 2231 | urls: { 2232 | apiURL: "https://explorer.oasis.io/mainnet/sapphire/api", 2233 | browserURL: "https://explorer.oasis.io/mainnet/sapphire", 2234 | }, 2235 | }, 2236 | { 2237 | network: "sapphireTestnet", 2238 | chainId: 23295, 2239 | urls: { 2240 | apiURL: "https://explorer.oasis.io/testnet/sapphire/api", 2241 | browserURL: "https://explorer.oasis.io/testnet/sapphire", 2242 | }, 2243 | }, 2244 | { 2245 | network: "worldChain", 2246 | chainId: 480, 2247 | urls: { 2248 | apiURL: "https://worldchain-mainnet.explorer.alchemy.com/api", 2249 | browserURL: "https://worldchain-mainnet.explorer.alchemy.com", 2250 | }, 2251 | }, 2252 | { 2253 | network: "worldChainTestnet", 2254 | chainId: 4801, 2255 | urls: { 2256 | apiURL: "https://worldchain-sepolia.explorer.alchemy.com/api", 2257 | browserURL: "https://worldchain-sepolia.explorer.alchemy.com", 2258 | }, 2259 | }, 2260 | { 2261 | network: "plume", 2262 | chainId: 98866, 2263 | urls: { 2264 | apiURL: "https://explorer.plume.org/api", 2265 | browserURL: "https://explorer.plume.org", 2266 | }, 2267 | }, 2268 | { 2269 | network: "plumeTestnet", 2270 | chainId: 98867, 2271 | urls: { 2272 | apiURL: "https://testnet-explorer.plume.org/api", 2273 | browserURL: "https://testnet-explorer.plume.org", 2274 | }, 2275 | }, 2276 | { 2277 | network: "unichain", 2278 | chainId: 130, 2279 | urls: { 2280 | apiURL: "https://api.uniscan.xyz/api", 2281 | browserURL: "https://uniscan.xyz", 2282 | }, 2283 | }, 2284 | { 2285 | network: "unichainTestnet", 2286 | chainId: 1301, 2287 | urls: { 2288 | apiURL: "https://api-sepolia.uniscan.xyz/api", 2289 | browserURL: "https://sepolia.uniscan.xyz", 2290 | }, 2291 | }, 2292 | { 2293 | network: "xdc", 2294 | chainId: 50, 2295 | urls: { 2296 | apiURL: "https://api.xdcscan.com/api", 2297 | browserURL: "https://xdcscan.com", 2298 | }, 2299 | }, 2300 | { 2301 | network: "xdcTestnet", 2302 | chainId: 51, 2303 | urls: { 2304 | apiURL: "https://api-testnet.xdcscan.com/api", 2305 | browserURL: "https://testnet.xdcscan.com", 2306 | }, 2307 | }, 2308 | { 2309 | network: "sx", 2310 | chainId: 4162, 2311 | urls: { 2312 | apiURL: "https://explorerl2.sx.technology/api", 2313 | browserURL: "https://explorerl2.sx.technology", 2314 | }, 2315 | }, 2316 | { 2317 | network: "sxTestnet", 2318 | chainId: 79479957, 2319 | urls: { 2320 | apiURL: "https://explorerl2.toronto.sx.technology/api", 2321 | browserURL: "https://explorerl2.toronto.sx.technology", 2322 | }, 2323 | }, 2324 | { 2325 | network: "zkSync", 2326 | chainId: 324, 2327 | urls: { 2328 | apiURL: "https://api-era.zksync.network/api", 2329 | browserURL: "https://era.zksync.network", 2330 | }, 2331 | }, 2332 | { 2333 | network: "zkSyncTestnet", 2334 | chainId: 300, 2335 | urls: { 2336 | apiURL: "https://api-sepolia-era.zksync.network/api", 2337 | browserURL: "https://sepolia-era.zksync.network", 2338 | }, 2339 | }, 2340 | { 2341 | network: "lisk", 2342 | chainId: 1135, 2343 | urls: { 2344 | apiURL: "https://blockscout.lisk.com/api", 2345 | browserURL: "https://blockscout.lisk.com", 2346 | }, 2347 | }, 2348 | { 2349 | network: "liskTestnet", 2350 | chainId: 4202, 2351 | urls: { 2352 | apiURL: "https://sepolia-blockscout.lisk.com/api", 2353 | browserURL: "https://sepolia-blockscout.lisk.com", 2354 | }, 2355 | }, 2356 | { 2357 | network: "metalL2", 2358 | chainId: 1750, 2359 | urls: { 2360 | apiURL: "https://explorer.metall2.com/api", 2361 | browserURL: "https://explorer.metall2.com", 2362 | }, 2363 | }, 2364 | { 2365 | network: "metalL2Testnet", 2366 | chainId: 1740, 2367 | urls: { 2368 | apiURL: "https://testnet.explorer.metall2.com/api", 2369 | browserURL: "https://testnet.explorer.metall2.com", 2370 | }, 2371 | }, 2372 | { 2373 | network: "superseed", 2374 | chainId: 5330, 2375 | urls: { 2376 | apiURL: "https://explorer.superseed.xyz/api", 2377 | browserURL: "https://explorer.superseed.xyz", 2378 | }, 2379 | }, 2380 | { 2381 | network: "superseedTestnet", 2382 | chainId: 53302, 2383 | urls: { 2384 | apiURL: "https://sepolia-explorer.superseed.xyz/api", 2385 | browserURL: "https://sepolia-explorer.superseed.xyz", 2386 | }, 2387 | }, 2388 | { 2389 | network: "storyTestnet", 2390 | chainId: 1315, 2391 | urls: { 2392 | apiURL: "https://aeneid.storyscan.io/api", 2393 | browserURL: "https://aeneid.storyscan.io", 2394 | }, 2395 | }, 2396 | { 2397 | network: "sonic", 2398 | chainId: 146, 2399 | urls: { 2400 | apiURL: "https://api.sonicscan.org/api", 2401 | browserURL: "https://sonicscan.org", 2402 | }, 2403 | }, 2404 | { 2405 | network: "sonicTestnet", 2406 | chainId: 57054, 2407 | urls: { 2408 | apiURL: "https://api-testnet.sonicscan.org/api", 2409 | browserURL: "https://testnet.sonicscan.org", 2410 | }, 2411 | }, 2412 | { 2413 | network: "flow", 2414 | chainId: 747, 2415 | urls: { 2416 | apiURL: "https://evm.flowscan.io/api", 2417 | browserURL: "https://evm.flowscan.io", 2418 | }, 2419 | }, 2420 | { 2421 | network: "flowTestnet", 2422 | chainId: 545, 2423 | urls: { 2424 | apiURL: "https://evm-testnet.flowscan.io/api", 2425 | browserURL: "https://evm-testnet.flowscan.io", 2426 | }, 2427 | }, 2428 | { 2429 | network: "ink", 2430 | chainId: 57073, 2431 | urls: { 2432 | apiURL: "https://explorer.inkonchain.com/api", 2433 | browserURL: "https://explorer.inkonchain.com", 2434 | }, 2435 | }, 2436 | { 2437 | network: "inkTestnet", 2438 | chainId: 763373, 2439 | urls: { 2440 | apiURL: "https://explorer-sepolia.inkonchain.com/api", 2441 | browserURL: "https://explorer-sepolia.inkonchain.com", 2442 | }, 2443 | }, 2444 | { 2445 | network: "morph", 2446 | chainId: 2818, 2447 | urls: { 2448 | apiURL: "https://explorer.morphl2.io/api", 2449 | browserURL: "https://explorer.morphl2.io", 2450 | }, 2451 | }, 2452 | { 2453 | network: "morphTestnet", 2454 | chainId: 2810, 2455 | urls: { 2456 | apiURL: "https://explorer-holesky.morphl2.io/api", 2457 | browserURL: "https://explorer-holesky.morphl2.io", 2458 | }, 2459 | }, 2460 | { 2461 | network: "shape", 2462 | chainId: 360, 2463 | urls: { 2464 | apiURL: "https://shapescan.xyz/api", 2465 | browserURL: "https://shapescan.xyz", 2466 | }, 2467 | }, 2468 | { 2469 | network: "shapeTestnet", 2470 | chainId: 11011, 2471 | urls: { 2472 | apiURL: "https://sepolia.shapescan.xyz/api", 2473 | browserURL: "https://sepolia.shapescan.xyz", 2474 | }, 2475 | }, 2476 | { 2477 | network: "etherlink", 2478 | chainId: 42793, 2479 | urls: { 2480 | apiURL: "https://explorer.etherlink.com/api", 2481 | browserURL: "https://explorer.etherlink.com", 2482 | }, 2483 | }, 2484 | { 2485 | network: "etherlinkTestnet", 2486 | chainId: 128123, 2487 | urls: { 2488 | apiURL: "https://testnet.explorer.etherlink.com/api", 2489 | browserURL: "https://testnet.explorer.etherlink.com", 2490 | }, 2491 | }, 2492 | { 2493 | network: "soneium", 2494 | chainId: 1868, 2495 | urls: { 2496 | apiURL: "https://soneium.blockscout.com/api", 2497 | browserURL: "https://soneium.blockscout.com", 2498 | }, 2499 | }, 2500 | { 2501 | network: "soneiumTestnet", 2502 | chainId: 1946, 2503 | urls: { 2504 | apiURL: "https://soneium-minato.blockscout.com/api", 2505 | browserURL: "https://soneium-minato.blockscout.com", 2506 | }, 2507 | }, 2508 | { 2509 | network: "swell", 2510 | chainId: 1923, 2511 | urls: { 2512 | apiURL: "https://explorer.swellnetwork.io/api", 2513 | browserURL: "https://explorer.swellnetwork.io", 2514 | }, 2515 | }, 2516 | { 2517 | network: "swellTestnet", 2518 | chainId: 1924, 2519 | urls: { 2520 | apiURL: "https://swell-testnet-explorer.alt.technology/api", 2521 | browserURL: "https://swell-testnet-explorer.alt.technology", 2522 | }, 2523 | }, 2524 | { 2525 | network: "hemi", 2526 | chainId: 43111, 2527 | urls: { 2528 | apiURL: "https://explorer.hemi.xyz/api", 2529 | browserURL: "https://explorer.hemi.xyz", 2530 | }, 2531 | }, 2532 | { 2533 | network: "hemiTestnet", 2534 | chainId: 743111, 2535 | urls: { 2536 | apiURL: "https://testnet.explorer.hemi.xyz/api", 2537 | browserURL: "https://testnet.explorer.hemi.xyz", 2538 | }, 2539 | }, 2540 | { 2541 | network: "berachain", 2542 | chainId: 80094, 2543 | urls: { 2544 | apiURL: "https://api.berascan.com/api", 2545 | browserURL: "https://berascan.com", 2546 | }, 2547 | }, 2548 | { 2549 | network: "berachainTestnet", 2550 | chainId: 80084, 2551 | urls: { 2552 | apiURL: 2553 | "https://api.routescan.io/v2/network/testnet/evm/80084/etherscan", 2554 | browserURL: "https://bartio.beratrail.io", 2555 | }, 2556 | }, 2557 | { 2558 | network: "corn", 2559 | chainId: 21000000, 2560 | urls: { 2561 | apiURL: 2562 | "https://api.routescan.io/v2/network/mainnet/evm/21000000/etherscan", 2563 | browserURL: "https://cornscan.io", 2564 | }, 2565 | }, 2566 | { 2567 | network: "cornTestnet", 2568 | chainId: 21000001, 2569 | urls: { 2570 | apiURL: 2571 | "https://api.routescan.io/v2/network/testnet/evm/21000001/etherscan", 2572 | browserURL: "https://testnet.cornscan.io", 2573 | }, 2574 | }, 2575 | { 2576 | network: "arenaz", 2577 | chainId: 7897, 2578 | urls: { 2579 | apiURL: "https://explorer.arena-z.gg/api", 2580 | browserURL: "https://explorer.arena-z.gg", 2581 | }, 2582 | }, 2583 | { 2584 | network: "arenazTestnet", 2585 | chainId: 9897, 2586 | urls: { 2587 | apiURL: "https://arena-z.blockscout.com/api", 2588 | browserURL: "https://arena-z.blockscout.com", 2589 | }, 2590 | }, 2591 | { 2592 | network: "iotex", 2593 | chainId: 4689, 2594 | urls: { 2595 | apiURL: "https://iotexscout.io/api", 2596 | browserURL: "https://iotexscan.io", 2597 | }, 2598 | }, 2599 | { 2600 | network: "iotexTestnet", 2601 | chainId: 4690, 2602 | urls: { 2603 | apiURL: "https://testnet.iotexscan.io/api", 2604 | browserURL: "https://testnet.iotexscan.io", 2605 | }, 2606 | }, 2607 | { 2608 | network: "hychain", 2609 | chainId: 2911, 2610 | urls: { 2611 | apiURL: "https://explorer.hychain.com/api", 2612 | browserURL: "https://explorer.hychain.com", 2613 | }, 2614 | }, 2615 | { 2616 | network: "hychainTestnet", 2617 | chainId: 29112, 2618 | urls: { 2619 | apiURL: "https://testnet.explorer.hychain.com/api", 2620 | browserURL: "https://testnet.explorer.hychain.com", 2621 | }, 2622 | }, 2623 | { 2624 | network: "zircuit", 2625 | chainId: 48900, 2626 | urls: { 2627 | apiURL: "https://explorer.zircuit.com/api/contractVerifyHardhat", 2628 | browserURL: "https://explorer.zircuit.com", 2629 | }, 2630 | }, 2631 | { 2632 | network: "zircuitTestnet", 2633 | chainId: 48898, 2634 | urls: { 2635 | apiURL: 2636 | "https://explorer.garfield-testnet.zircuit.com/api/contractVerifyHardhat", 2637 | browserURL: "https://explorer.garfield-testnet.zircuit.com", 2638 | }, 2639 | }, 2640 | { 2641 | network: "bitlayer", 2642 | chainId: 200901, 2643 | urls: { 2644 | apiURL: "https://api.btrscan.com/scan/api", 2645 | browserURL: "https://www.btrscan.com", 2646 | }, 2647 | }, 2648 | { 2649 | network: "bitlayerTestnet", 2650 | chainId: 200810, 2651 | urls: { 2652 | apiURL: "https://api-testnet.btrscan.com/scan/api", 2653 | browserURL: "https://testnet.btrscan.com", 2654 | }, 2655 | }, 2656 | { 2657 | network: "immutableZkEVM", 2658 | chainId: 13371, 2659 | urls: { 2660 | apiURL: "https://explorer.immutable.com/api", 2661 | browserURL: "https://explorer.immutable.com", 2662 | }, 2663 | }, 2664 | { 2665 | network: "immutableZkEVMTestnet", 2666 | chainId: 13473, 2667 | urls: { 2668 | apiURL: "https://explorer.testnet.immutable.com/api", 2669 | browserURL: "https://explorer.testnet.immutable.com", 2670 | }, 2671 | }, 2672 | { 2673 | network: "abstract", 2674 | chainId: 2741, 2675 | urls: { 2676 | apiURL: "https://api.abscan.org/api", 2677 | browserURL: "https://abscan.org", 2678 | }, 2679 | }, 2680 | { 2681 | network: "abstractTestnet", 2682 | chainId: 11124, 2683 | urls: { 2684 | apiURL: "https://api-sepolia.abscan.org/api", 2685 | browserURL: "https://sepolia.abscan.org", 2686 | }, 2687 | }, 2688 | { 2689 | network: "kaia", 2690 | chainId: 8217, 2691 | urls: { 2692 | apiURL: 2693 | "https://www.oklink.com/api/v5/explorer/contract/verify-source-code-plugin/KAIA", 2694 | browserURL: "https://www.oklink.com/kaia", 2695 | }, 2696 | }, 2697 | { 2698 | network: "apeChain", 2699 | chainId: 33139, 2700 | urls: { 2701 | apiURL: "https://api.apescan.io/api", 2702 | browserURL: "https://apescan.io", 2703 | }, 2704 | }, 2705 | { 2706 | network: "apeChainTestnet", 2707 | chainId: 33111, 2708 | urls: { 2709 | apiURL: "https://api-curtis.apescan.io/api", 2710 | browserURL: "https://curtis.apescan.io", 2711 | }, 2712 | }, 2713 | ], 2714 | }, 2715 | // tenderly: { 2716 | // username: "MyAwesomeUsername", 2717 | // project: "super-awesome-project", 2718 | // forkNetwork: "", 2719 | // privateVerification: false, 2720 | // deploymentsDir: "deployments_tenderly", 2721 | // }, 2722 | }; 2723 | 2724 | export default config; 2725 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "hardhat-project-template-ts", 3 | "version": "1.0.0", 4 | "description": "A fully-fledged Hardhat project template based on TypeScript.", 5 | "keywords": [ 6 | "template", 7 | "typescript", 8 | "ethereum", 9 | "smart-contracts", 10 | "solidity", 11 | "foundry", 12 | "hardhat" 13 | ], 14 | "repository": { 15 | "type": "git", 16 | "url": "git+https://github.com/pcaversaccio/hardhat-project-template-ts.git" 17 | }, 18 | "homepage": "https://github.com/pcaversaccio/hardhat-project-template-ts#readme", 19 | "bugs": { 20 | "url": "https://github.com/pcaversaccio/hardhat-project-template-ts/issues" 21 | }, 22 | "author": "Pascal Marco Caversaccio ", 23 | "license": "MIT", 24 | "packageManager": "pnpm@10.18.1", 25 | "scripts": { 26 | "help": "npx hardhat help", 27 | "accounts": "npx hardhat accounts", 28 | "balances": "npx hardhat balances", 29 | "node:hh": "npx hardhat node", 30 | "clean": "npx hardhat clean && forge clean", 31 | "snapshot": "forge snapshot --out forge-artifacts", 32 | "coverage:hh": "npx hardhat coverage", 33 | "coverage:forge": "forge coverage --report summary --out forge-artifacts --lcov-version 2.3.1", 34 | "coverage:forge:report": "forge coverage --report lcov --out forge-artifacts --lcov-version 2.3.1 && lcov --branch-coverage --remove lcov.info \"test/*\" \"script/*\" \"node_modules/*\" --output-file lcov.info --ignore-errors unused,unused && genhtml lcov.info --branch-coverage --output-dir coverage", 35 | "test:hh": "npx hardhat test", 36 | "test:forge": "forge test -vvv --root . -C contracts/src --match-path \"contracts/test/*\" --out forge-artifacts", 37 | "compile": "npx hardhat compile && forge build --root . -C contracts/src --optimize --out forge-artifacts", 38 | "size": "npx hardhat size-contracts", 39 | "xdeploy": "npx hardhat xdeploy", 40 | "abi": "npx hardhat export-abi", 41 | "vars:path": "npx hardhat vars path", 42 | "evm": "npx hardhat evm", 43 | "deploy:hh": "npx hardhat run --network hardhat scripts/deploy.ts", 44 | "deploy:localhost": "npx hardhat run --network localhost scripts/deploy.ts", 45 | "deploy:tenderly": "npx hardhat run --network tenderly scripts/deploy.ts", 46 | "deploy:devnet": "npx hardhat run --network devnet scripts/deploy.ts", 47 | "deploy:sepolia": "npx hardhat run --network sepolia scripts/deploy.ts", 48 | "deploy:holesky": "npx hardhat run --network holesky scripts/deploy.ts", 49 | "deploy:hoodi": "npx hardhat run --network hoodi scripts/deploy.ts", 50 | "deploy:ethmain": "npx hardhat run --network ethMain scripts/deploy.ts", 51 | "deploy:bsctestnet": "npx hardhat run --network bscTestnet scripts/deploy.ts", 52 | "deploy:bscmain": "npx hardhat run --network bscMain scripts/deploy.ts", 53 | "deploy:optimismtestnet": "npx hardhat run --network optimismTestnet scripts/deploy.ts", 54 | "deploy:optimismsepolia": "npx hardhat run --network optimismSepolia scripts/deploy.ts", 55 | "deploy:optimismmain": "npx hardhat run --network optimismMain scripts/deploy.ts", 56 | "deploy:arbitrumsepolia": "npx hardhat run --network arbitrumSepolia scripts/deploy.ts", 57 | "deploy:arbitrummain": "npx hardhat run --network arbitrumMain scripts/deploy.ts", 58 | "deploy:arbitrumnova": "npx hardhat run --network arbitrumNova scripts/deploy.ts", 59 | "deploy:amoy": "npx hardhat run --network amoy scripts/deploy.ts", 60 | "deploy:polygonzkevmtestnet": "npx hardhat run --network polygonZkEVMTestnet scripts/deploy.ts", 61 | "deploy:polygon": "npx hardhat run --network polygon scripts/deploy.ts", 62 | "deploy:polygonzkevmmain": "npx hardhat run --network polygonZkEVMMain scripts/deploy.ts", 63 | "deploy:hecomain": "npx hardhat run --network hecoMain scripts/deploy.ts", 64 | "deploy:fantomtestnet": "npx hardhat run --network fantomTestnet scripts/deploy.ts", 65 | "deploy:fantommain": "npx hardhat run --network fantomMain scripts/deploy.ts", 66 | "deploy:fuji": "npx hardhat run --network fuji scripts/deploy.ts", 67 | "deploy:avalanche": "npx hardhat run --network avalanche scripts/deploy.ts", 68 | "deploy:chiado": "npx hardhat run --network chiado scripts/deploy.ts", 69 | "deploy:gnosis": "npx hardhat run --network gnosis scripts/deploy.ts", 70 | "deploy:moonbasealpha": "npx hardhat run --network moonbaseAlpha scripts/deploy.ts", 71 | "deploy:moonriver": "npx hardhat run --network moonriver scripts/deploy.ts", 72 | "deploy:moonbeam": "npx hardhat run --network moonbeam scripts/deploy.ts", 73 | "deploy:alfajores": "npx hardhat run --network alfajores scripts/deploy.ts", 74 | "deploy:celo": "npx hardhat run --network celo scripts/deploy.ts", 75 | "deploy:auroratestnet": "npx hardhat run --network auroraTestnet scripts/deploy.ts", 76 | "deploy:auroramain": "npx hardhat run --network auroraMain scripts/deploy.ts", 77 | "deploy:harmonytestnet": "npx hardhat run --network harmonyTestnet scripts/deploy.ts", 78 | "deploy:harmonymain": "npx hardhat run --network harmonyMain scripts/deploy.ts", 79 | "deploy:spark": "npx hardhat run --network spark scripts/deploy.ts", 80 | "deploy:fuse": "npx hardhat run --network fuse scripts/deploy.ts", 81 | "deploy:cronostestnet": "npx hardhat run --network cronosTestnet scripts/deploy.ts", 82 | "deploy:cronosmain": "npx hardhat run --network cronosMain scripts/deploy.ts", 83 | "deploy:evmostestnet": "npx hardhat run --network evmosTestnet scripts/deploy.ts", 84 | "deploy:evmosmain": "npx hardhat run --network evmosMain scripts/deploy.ts", 85 | "deploy:bobatestnet": "npx hardhat run --network bobaTestnet scripts/deploy.ts", 86 | "deploy:bobamain": "npx hardhat run --network bobaMain scripts/deploy.ts", 87 | "deploy:cantotestnet": "npx hardhat run --network cantoTestnet scripts/deploy.ts", 88 | "deploy:cantomain": "npx hardhat run --network cantoMain scripts/deploy.ts", 89 | "deploy:basetestnet": "npx hardhat run --network baseTestnet scripts/deploy.ts", 90 | "deploy:basesepolia": "npx hardhat run --network baseSepolia scripts/deploy.ts", 91 | "deploy:basemain": "npx hardhat run --network baseMain scripts/deploy.ts", 92 | "deploy:zksynctestnet": "npx hardhat deploy-zksync --network zkSyncTestnet --script deploy-zksync.ts", 93 | "deploy:zksyncmain": "npx hardhat deploy-zksync --network zkSyncMain --script deploy-zksync.ts", 94 | "deploy:mantletestnet": "npx hardhat run --network mantleTestnet scripts/deploy.ts", 95 | "deploy:mantlemain": "npx hardhat run --network mantleMain scripts/deploy.ts", 96 | "deploy:filecointestnet": "npx hardhat run --network filecoinTestnet scripts/deploy.ts", 97 | "deploy:filecoinmain": "npx hardhat run --network filecoinMain scripts/deploy.ts", 98 | "deploy:scrolltestnet": "npx hardhat run --network scrollTestnet scripts/deploy.ts", 99 | "deploy:scrollmain": "npx hardhat run --network scrollMain scripts/deploy.ts", 100 | "deploy:lineatestnet": "npx hardhat run --network lineaTestnet scripts/deploy.ts", 101 | "deploy:lineamain": "npx hardhat run --network lineaMain scripts/deploy.ts", 102 | "deploy:shimmerevmtestnet": "npx hardhat run --network shimmerEVMTestnet scripts/deploy.ts", 103 | "deploy:zoratestnet": "npx hardhat run --network zoraTestnet scripts/deploy.ts", 104 | "deploy:zoramain": "npx hardhat run --network zoraMain scripts/deploy.ts", 105 | "deploy:luksotestnet": "npx hardhat run --network luksoTestnet scripts/deploy.ts", 106 | "deploy:luksomain": "npx hardhat run --network luksoMain scripts/deploy.ts", 107 | "deploy:mantatestnet": "npx hardhat run --network mantaTestnet scripts/deploy.ts", 108 | "deploy:mantamain": "npx hardhat run --network mantaMain scripts/deploy.ts", 109 | "deploy:shardeumtestnet": "npx hardhat run --network shardeumTestnet scripts/deploy.ts", 110 | "deploy:artheratestnet": "npx hardhat run --network artheraTestnet scripts/deploy.ts", 111 | "deploy:frametestnet": "npx hardhat run --network frameTestnet scripts/deploy.ts", 112 | "deploy:endurancetestnet": "npx hardhat run --network enduranceTestnet scripts/deploy.ts", 113 | "deploy:opendurancetestnet": "npx hardhat run --network openduranceTestnet scripts/deploy.ts", 114 | "deploy:endurancemain": "npx hardhat run --network enduranceMain scripts/deploy.ts", 115 | "deploy:blasttestnet": "npx hardhat run --network blastTestnet scripts/deploy.ts", 116 | "deploy:blastmain": "npx hardhat run --network blastMain scripts/deploy.ts", 117 | "deploy:kromatestnet": "npx hardhat run --network kromaTestnet scripts/deploy.ts", 118 | "deploy:kromamain": "npx hardhat run --network kromaMain scripts/deploy.ts", 119 | "deploy:dostestnet": "npx hardhat run --network dosTestnet scripts/deploy.ts", 120 | "deploy:dosmain": "npx hardhat run --network dosMain scripts/deploy.ts", 121 | "deploy:fraxtaltestnet": "npx hardhat run --network fraxtalTestnet scripts/deploy.ts", 122 | "deploy:fraxtalmain": "npx hardhat run --network fraxtalMain scripts/deploy.ts", 123 | "deploy:kavamain": "npx hardhat run --network kavaMain scripts/deploy.ts", 124 | "deploy:metistestnet": "npx hardhat run --network metisTestnet scripts/deploy.ts", 125 | "deploy:metismain": "npx hardhat run --network metisMain scripts/deploy.ts", 126 | "deploy:modetestnet": "npx hardhat run --network modeTestnet scripts/deploy.ts", 127 | "deploy:modemain": "npx hardhat run --network modeMain scripts/deploy.ts", 128 | "deploy:seidevnet": "npx hardhat run --network seiDevnet scripts/deploy.ts", 129 | "deploy:seitestnet": "npx hardhat run --network seiTestnet scripts/deploy.ts", 130 | "deploy:seimain": "npx hardhat run --network seiMain scripts/deploy.ts", 131 | "deploy:xlayertestnet": "npx hardhat run --network xlayerTestnet scripts/deploy.ts", 132 | "deploy:xlayermain": "npx hardhat run --network xlayerMain scripts/deploy.ts", 133 | "deploy:bobtestnet": "npx hardhat run --network bobTestnet scripts/deploy.ts", 134 | "deploy:bobmain": "npx hardhat run --network bobMain scripts/deploy.ts", 135 | "deploy:coretestnet": "npx hardhat run --network coreTestnet scripts/deploy.ts", 136 | "deploy:coremain": "npx hardhat run --network coreMain scripts/deploy.ts", 137 | "deploy:telostestnet": "npx hardhat run --network telosTestnet scripts/deploy.ts", 138 | "deploy:telosmain": "npx hardhat run --network telosMain scripts/deploy.ts", 139 | "deploy:rootstocktestnet": "npx hardhat run --network rootstockTestnet scripts/deploy.ts", 140 | "deploy:rootstockmain": "npx hardhat run --network rootstockMain scripts/deploy.ts", 141 | "deploy:chiliztestnet": "npx hardhat run --network chilizTestnet scripts/deploy.ts", 142 | "deploy:chilizmain": "npx hardhat run --network chilizMain scripts/deploy.ts", 143 | "deploy:taraxatestnet": "npx hardhat run --network taraxaTestnet scripts/deploy.ts", 144 | "deploy:taraxamain": "npx hardhat run --network taraxaMain scripts/deploy.ts", 145 | "deploy:gravityalphatestnet": "npx hardhat run --network gravityAlphaTestnet scripts/deploy.ts", 146 | "deploy:gravityalphamain": "npx hardhat run --network gravityAlphaMain scripts/deploy.ts", 147 | "deploy:taikotestnet": "npx hardhat run --network taikoTestnet scripts/deploy.ts", 148 | "deploy:taikomain": "npx hardhat run --network taikoMain scripts/deploy.ts", 149 | "deploy:zetachaintestnet": "npx hardhat run --network zetaChainTestnet scripts/deploy.ts", 150 | "deploy:zetachainmain": "npx hardhat run --network zetaChainMain scripts/deploy.ts", 151 | "deploy:5irechaintestnet": "npx hardhat run --network 5ireChainTestnet scripts/deploy.ts", 152 | "deploy:5irechainmain": "npx hardhat run --network 5ireChainMain scripts/deploy.ts", 153 | "deploy:sapphiretestnet": "npx hardhat run --network sapphireTestnet scripts/deploy.ts", 154 | "deploy:sapphiremain": "npx hardhat run --network sapphireMain scripts/deploy.ts", 155 | "deploy:worldchaintestnet": "npx hardhat run --network worldChainTestnet scripts/deploy.ts", 156 | "deploy:worldchainmain": "npx hardhat run --network worldChainMain scripts/deploy.ts", 157 | "deploy:plumetestnet": "npx hardhat run --network plumeTestnet scripts/deploy.ts", 158 | "deploy:plumemain": "npx hardhat run --network plumeMain scripts/deploy.ts", 159 | "deploy:unichaintestnet": "npx hardhat run --network unichainTestnet scripts/deploy.ts", 160 | "deploy:unichainmain": "npx hardhat run --network unichainMain scripts/deploy.ts", 161 | "deploy:xdctestnet": "npx hardhat run --network xdcTestnet scripts/deploy.ts", 162 | "deploy:xdcmain": "npx hardhat run --network xdcMain scripts/deploy.ts", 163 | "deploy:sxtestnet": "npx hardhat run --network sxTestnet scripts/deploy.ts", 164 | "deploy:sxmain": "npx hardhat run --network sxMain scripts/deploy.ts", 165 | "deploy:lisktestnet": "npx hardhat run --network liskTestnet scripts/deploy.ts", 166 | "deploy:liskmain": "npx hardhat run --network liskMain scripts/deploy.ts", 167 | "deploy:metall2testnet": "npx hardhat run --network metalL2Testnet scripts/deploy.ts", 168 | "deploy:metall2main": "npx hardhat run --network metalL2Main scripts/deploy.ts", 169 | "deploy:superseedtestnet": "npx hardhat run --network superseedTestnet scripts/deploy.ts", 170 | "deploy:superseedmain": "npx hardhat run --network superseedMain scripts/deploy.ts", 171 | "deploy:storytestnet": "npx hardhat run --network storyTestnet scripts/deploy.ts", 172 | "deploy:sonictestnet": "npx hardhat run --network sonicTestnet scripts/deploy.ts", 173 | "deploy:sonicmain": "npx hardhat run --network sonicMain scripts/deploy.ts", 174 | "deploy:flowtestnet": "npx hardhat run --network flowTestnet scripts/deploy.ts", 175 | "deploy:flowmain": "npx hardhat run --network flowMain scripts/deploy.ts", 176 | "deploy:inktestnet": "npx hardhat run --network inkTestnet scripts/deploy.ts", 177 | "deploy:inkmain": "npx hardhat run --network inkMain scripts/deploy.ts", 178 | "deploy:morphtestnet": "npx hardhat run --network morphTestnet scripts/deploy.ts", 179 | "deploy:morphmain": "npx hardhat run --network morphMain scripts/deploy.ts", 180 | "deploy:shapetestnet": "npx hardhat run --network shapeTestnet scripts/deploy.ts", 181 | "deploy:shapemain": "npx hardhat run --network shapeMain scripts/deploy.ts", 182 | "deploy:etherlinktestnet": "npx hardhat run --network etherlinkTestnet scripts/deploy.ts", 183 | "deploy:etherlinkmain": "npx hardhat run --network etherlinkMain scripts/deploy.ts", 184 | "deploy:soneiumtestnet": "npx hardhat run --network soneiumTestnet scripts/deploy.ts", 185 | "deploy:soneiummain": "npx hardhat run --network soneiumMain scripts/deploy.ts", 186 | "deploy:swelltestnet": "npx hardhat run --network swellTestnet scripts/deploy.ts", 187 | "deploy:swellmain": "npx hardhat run --network swellMain scripts/deploy.ts", 188 | "deploy:hemitestnet": "npx hardhat run --network hemiTestnet scripts/deploy.ts", 189 | "deploy:hemimain": "npx hardhat run --network hemiMain scripts/deploy.ts", 190 | "deploy:berachaintestnet": "npx hardhat run --network berachainTestnet scripts/deploy.ts", 191 | "deploy:berachainmain": "npx hardhat run --network berachainMain scripts/deploy.ts", 192 | "deploy:monadtestnet": "npx hardhat run --network monadTestnet scripts/deploy.ts", 193 | "deploy:corntestnet": "npx hardhat run --network cornTestnet scripts/deploy.ts", 194 | "deploy:cornmain": "npx hardhat run --network cornMain scripts/deploy.ts", 195 | "deploy:arenaztestnet": "npx hardhat run --network arenazTestnet scripts/deploy.ts", 196 | "deploy:arenazmain": "npx hardhat run --network arenazMain scripts/deploy.ts", 197 | "deploy:iotextestnet": "npx hardhat run --network iotexTestnet scripts/deploy.ts", 198 | "deploy:iotexmain": "npx hardhat run --network iotexMain scripts/deploy.ts", 199 | "deploy:hychaintestnet": "npx hardhat run --network hychainTestnet scripts/deploy.ts", 200 | "deploy:hychainmain": "npx hardhat run --network hychainMain scripts/deploy.ts", 201 | "deploy:zircuittestnet": "npx hardhat run --network zircuitTestnet scripts/deploy.ts", 202 | "deploy:zircuitmain": "npx hardhat run --network zircuitMain scripts/deploy.ts", 203 | "deploy:megaethtestnet": "npx hardhat run --network megaETHTestnet scripts/deploy.ts", 204 | "deploy:bitlayertestnet": "npx hardhat run --network bitlayerTestnet scripts/deploy.ts", 205 | "deploy:bitlayermain": "npx hardhat run --network bitlayerMain scripts/deploy.ts", 206 | "deploy:ronintestnet": "npx hardhat run --network roninTestnet scripts/deploy.ts", 207 | "deploy:roninmain": "npx hardhat run --network roninMain scripts/deploy.ts", 208 | "deploy:immutablezkevmtestnet": "npx hardhat run --network immutableZkEVMTestnet scripts/deploy.ts", 209 | "deploy:immutablezkevmmain": "npx hardhat run --network immutableZkEVMMain scripts/deploy.ts", 210 | "deploy:abstracttestnet": "npx hardhat run --network abstractTestnet scripts/deploy.ts", 211 | "deploy:abstractmain": "npx hardhat run --network abstractMain scripts/deploy.ts", 212 | "deploy:hyperevmtestnet": "npx hardhat run --network hyperevmTestnet scripts/deploy.ts", 213 | "deploy:hyperevmmain": "npx hardhat run --network hyperevmMain scripts/deploy.ts", 214 | "deploy:kaiamain": "npx hardhat run --network kaiaMain scripts/deploy.ts", 215 | "deploy:apechaintestnet": "npx hardhat run --network apeChainTestnet scripts/deploy.ts", 216 | "deploy:apechainmain": "npx hardhat run --network apeChainMain scripts/deploy.ts", 217 | "prettier:check": "npx prettier -c \"**/*.{js,ts,md,sol,json,yml,yaml}\"", 218 | "prettier:fix": "npx prettier -w \"**/*.{js,ts,md,sol,json,yml,yaml}\"", 219 | "slippy:check": "npx slippy \"contracts/**/*.sol\"", 220 | "lint:check": "pnpm prettier:check && pnpm slippy:check && npx eslint .", 221 | "lint:fix": "pnpm prettier:fix && npx eslint . --fix" 222 | }, 223 | "devDependencies": { 224 | "@eslint/js": "^9.37.0", 225 | "@matterlabs/hardhat-zksync-deploy": "^1.8.0", 226 | "@matterlabs/hardhat-zksync-ethers": "^1.4.0", 227 | "@matterlabs/hardhat-zksync-solc": "^1.5.1", 228 | "@matterlabs/hardhat-zksync-verify": "^1.9.1", 229 | "@nomicfoundation/hardhat-chai-matchers": "^2.1.0", 230 | "@nomicfoundation/hardhat-ethers": "^3.1.0", 231 | "@nomicfoundation/hardhat-foundry": "^1.2.0", 232 | "@nomicfoundation/hardhat-ignition": "^0.15.13", 233 | "@nomicfoundation/hardhat-ignition-ethers": "^0.15.14", 234 | "@nomicfoundation/hardhat-ledger": "^1.2.0", 235 | "@nomicfoundation/hardhat-network-helpers": "^1.1.0", 236 | "@nomicfoundation/hardhat-verify": "^2.1.1", 237 | "@nomicfoundation/ignition-core": "^0.15.13", 238 | "@openzeppelin/contracts": "^5.4.0", 239 | "@slippy-lint/slippy": "^0.2.0", 240 | "@tenderly/hardhat-tenderly": "^2.5.2", 241 | "@typechain/ethers-v6": "^0.5.1", 242 | "@typechain/hardhat": "^9.1.0", 243 | "@types/chai": "^4.3.20", 244 | "@types/mocha": "^10.0.10", 245 | "@types/node": "^24.7.0", 246 | "chai": "^4.5.0", 247 | "eslint": "^9.37.0", 248 | "eslint-config-prettier": "^10.1.8", 249 | "ethers": "^6.15.0", 250 | "hardhat": "^2.26.3", 251 | "hardhat-abi-exporter": "^2.11.0", 252 | "hardhat-contract-sizer": "^2.10.1", 253 | "hardhat-gas-reporter": "^2.3.0", 254 | "prettier": "^3.6.2", 255 | "prettier-plugin-solidity": "^2.1.0", 256 | "solidity-coverage": "^0.8.16", 257 | "ts-node": "^10.9.2", 258 | "typechain": "^8.3.2", 259 | "typescript": "^5.9.3", 260 | "typescript-eslint": "^8.46.0", 261 | "xdeployer": "^3.1.17", 262 | "zksync-ethers": "^6.21.0" 263 | }, 264 | "pnpm": { 265 | "onlyBuiltDependencies": [ 266 | "bufferutil", 267 | "cpu-features", 268 | "keccak", 269 | "node-hid", 270 | "protobufjs", 271 | "secp256k1", 272 | "ssh2", 273 | "usb", 274 | "utf-8-validate" 275 | ] 276 | } 277 | } 278 | -------------------------------------------------------------------------------- /remappings.txt: -------------------------------------------------------------------------------- 1 | hardhat/=node_modules/hardhat/ 2 | xdeployer/=node_modules/xdeployer/ 3 | forge-std/=contracts/lib/forge-std/src/ 4 | @openzeppelin/=node_modules/@openzeppelin/ 5 | -------------------------------------------------------------------------------- /renovate.json: -------------------------------------------------------------------------------- 1 | { 2 | "baseBranches": ["main"], 3 | "labels": ["dependencies"], 4 | "assignees": ["pcaversaccio"], 5 | "separateMajorMinor": false, 6 | "extends": [ 7 | ":preserveSemverRanges", 8 | "group:all", 9 | "schedule:monthly", 10 | ":maintainLockFilesMonthly" 11 | ], 12 | "lockFileMaintenance": { 13 | "extends": ["group:all"], 14 | "commitMessageAction": "Update" 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /scripts/deploy.sh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | 3 | # Read the RPC URL 4 | echo Enter your RPC URL \(script uses silent mode\;\ i.e. not printed to the console\): 5 | echo Example: "https://eth-mainnet.alchemyapi.io/v2/XXXXXXXXXX" 6 | read -s rpc 7 | 8 | # Read the private key 9 | echo Enter your private key \(script uses silent mode\;\ i.e. not printed to the console\): 10 | echo Example: "0xabc123abc123abc123abc123abc123abc123abc123abc123abc123abc123abc1" 11 | read -s key 12 | 13 | # Read the contract name 14 | echo Which contract do you want to deploy \(e.g. Greeter\)? 15 | read contract 16 | 17 | # Read the constructor arguments 18 | echo Enter the constructor arguments separated by spaces \(e.g. hello 0xacc4de8d4ca96c3f0c91b58f1d6c0d80cf8cc146 1\): 19 | read -ra args 20 | 21 | if [ -z "$args" ]; then 22 | forge create -i ./contracts/src/${contract}.sol:${contract} --rpc-url $rpc --private-key $key 23 | else 24 | forge create -i ./contracts/src/${contract}.sol:${contract} --rpc-url $rpc --private-key $key --constructor-args ${args} 25 | fi 26 | -------------------------------------------------------------------------------- /scripts/deploy.ts: -------------------------------------------------------------------------------- 1 | import hre from "hardhat"; 2 | 3 | // Colour codes for terminal prints 4 | const RESET = "\x1b[0m"; 5 | const GREEN = "\x1b[32m"; 6 | 7 | function delay(ms: number) { 8 | return new Promise((resolve) => setTimeout(resolve, ms)); 9 | } 10 | 11 | async function main() { 12 | const constructorArgs = ["Hello, Hardhat!"]; 13 | const contract = await hre.ethers.deployContract("Greeter", constructorArgs); 14 | 15 | await contract.waitForDeployment(); 16 | const contractAddress = await contract.getAddress(); 17 | 18 | console.log("Greeter deployed to: " + `${GREEN}${contractAddress}${RESET}\n`); 19 | 20 | console.log( 21 | "Waiting 30 seconds before beginning the contract verification to allow the block explorer to index the contract...\n", 22 | ); 23 | await delay(30000); // Wait for 30 seconds before verifying the contract 24 | 25 | await hre.run("verify:verify", { 26 | address: contractAddress, 27 | constructorArguments: constructorArgs, 28 | }); 29 | 30 | // Uncomment if you want to enable the `tenderly` extension 31 | // await hre.tenderly.verify({ 32 | // name: "Greeter", 33 | // address: contractAddress, 34 | // }); 35 | } 36 | 37 | main().catch((error) => { 38 | console.error(error); 39 | process.exitCode = 1; 40 | }); 41 | -------------------------------------------------------------------------------- /scripts/deploy_local.sh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | 3 | # Read the RPC URL 4 | echo Enter your mainnet RPC URL to fork a local Hardhat node from \(script uses silent mode\;\ i.e. not printed to the console\): 5 | echo Example: "https://eth-mainnet.alchemyapi.io/v2/XXXXXXXXXX" 6 | read -s rpc 7 | 8 | ## Fork the mainnet 9 | echo Please wait 1 minute for Hardhat to fork the mainnet and run locally... 10 | echo If this command fails, try running "yarn" to install Hardhat dependencies... 11 | make -s mainnet-fork ETH_MAINNET_RPC_URL=$rpc & 12 | 13 | # Wait for Hardhat to fork the mainnet 14 | sleep 60 15 | 16 | # Read the contract name 17 | echo Which contract do you want to deploy \(e.g. Greeter\)? 18 | read contract 19 | 20 | # Read the constructor arguments 21 | echo Enter the constructor arguments separated by spaces \(e.g. hello 0xacc4de8d4ca96c3f0c91b58f1d6c0d80cf8cc146 1\): 22 | read -ra args 23 | 24 | if [ -z "$args" ]; then 25 | forge create -i ./contracts/src/${contract}.sol:${contract} --rpc-url "http://localhost:8545" 26 | else 27 | forge create -i ./contracts/src/${contract}.sol:${contract} --rpc-url "http://localhost:8545" --constructor-args ${args} 28 | fi 29 | -------------------------------------------------------------------------------- /scripts/flatten.sh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | 3 | # Read the contract name 4 | echo Which contract do you want to flatten \(e.g. Greeter\)? 5 | read contract 6 | 7 | # Remove an existing flattened contract 8 | rm -rf flattened.sol 9 | 10 | # Flatten the contract 11 | forge flatten ./contracts/src/${contract}.sol >flattened.sol 12 | -------------------------------------------------------------------------------- /scripts/interact.ts: -------------------------------------------------------------------------------- 1 | // An example script that shows how to interact programmatically with a deployed contract 2 | // You must customise it according to your contract's specifications 3 | import hre from "hardhat"; 4 | 5 | // Colour codes for terminal prints 6 | const RESET = "\x1b[0m"; 7 | const GREEN = "\x1b[32m"; 8 | 9 | async function main() { 10 | const address = "0xB8d2BDd1C99A33b831553DA64F6215983bf0475a"; // Specify here your contract address 11 | const contract = await hre.ethers.getContractAt("Greeter", address); // Specify here your contract name 12 | 13 | //////////////// 14 | // PAYLOAD // 15 | ////////////// 16 | 17 | const newGreeting = "Buongiorno!"; // Specify here the payload of the to-be-called function 18 | 19 | //////////////// 20 | // SENDING // 21 | ////////////// 22 | 23 | const tx = await contract.setGreeting(newGreeting); // Specify here the to-be-called function name 24 | console.log("The transaction hash is: " + `${GREEN}${tx.hash}${RESET}\n`); 25 | console.log("Waiting until the transaction is confirmed...\n"); 26 | const receipt = await tx.wait(); // Wait until the transaction is confirmed 27 | console.log( 28 | "The transaction returned the following transaction receipt:\n", 29 | receipt, 30 | ); 31 | } 32 | 33 | // To run it, invoke `npx hardhat run scripts/interact.ts --network ` 34 | main().catch((error) => { 35 | console.error(error); 36 | process.exitCode = 1; 37 | }); 38 | -------------------------------------------------------------------------------- /scripts/verify.sh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | 3 | echo Which compiler version did you use to build? 4 | read version 5 | echo Selected compiler version: $version 6 | 7 | echo Which contract do you want to verify \(e.g. Greeter\)? 8 | read contract 9 | echo Selected contract name: $contract 10 | 11 | echo What is the deployed address? 12 | read deployed 13 | echo Selected contract address: $deployed 14 | 15 | echo What is the chain ID of the deployed address? 16 | read id 17 | echo Selected chain ID: $id 18 | 19 | echo Enter the constructor abi \(e.g. constructor\(string\)\): 20 | read abi 21 | echo Selected constructor abi: $abi 22 | 23 | echo Enter the constructor arguments separated by spaces \(e.g. 1 2 3\): 24 | read -ra args 25 | echo Selected constructor arguments: $args 26 | 27 | encoded=$(cast abi-encode $abi $args) 28 | echo ABI-encoded constructor arguments: ${encoded:2} 29 | 30 | echo Enter your Etherscan API key: 31 | read -s etherscan 32 | 33 | if [ -z "$args" ]; then 34 | forge verify-contract --chain-id $id --compiler-version $version $deployed ./contracts/src/${contract}.sol:${contract} $etherscan 35 | else 36 | forge verify-contract --constructor-args ${encoded:2} --chain-id $id --compiler-version $version $deployed ./contracts/src/${contract}.sol:${contract} $etherscan 37 | fi 38 | -------------------------------------------------------------------------------- /slippy.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | ignores: ["contracts/lib/**/*"], 3 | rules: { 4 | "explicit-types": "error", 5 | "id-denylist": "error", 6 | "imports-on-top": "error", 7 | "max-state-vars": "error", 8 | "naming-convention": "error", 9 | "no-console": "error", 10 | "no-default-visibility": "error", 11 | "no-duplicate-imports": "error", 12 | "no-empty-blocks": "error", 13 | "no-global-imports": "error", 14 | "no-tx-origin": "error", 15 | "no-uninitialized-immutable-references": "error", 16 | "no-unused-vars": "error", 17 | "require-revert-reason": "error", 18 | "sort-imports": "error", 19 | "sort-modifiers": "error", 20 | }, 21 | }; 22 | -------------------------------------------------------------------------------- /slither.config.json: -------------------------------------------------------------------------------- 1 | { 2 | "compile_force_framework": "hardhat", 3 | "hardhat_ignore_compile": false, 4 | "detectors_to_exclude": "pragma,solc-version", 5 | "fail_on": "none", 6 | "exclude_informational": false, 7 | "exclude_low": false, 8 | "exclude_medium": false, 9 | "exclude_high": false, 10 | "filter_paths": "contracts/lib|contracts/test|contracts/src/Create2DeployerLocal.sol|@openzeppelin|hardhat/console.sol|xdeployer" 11 | } 12 | -------------------------------------------------------------------------------- /test/Greeter.test.ts: -------------------------------------------------------------------------------- 1 | import { expect, assert } from "chai"; 2 | import hre from "hardhat"; 3 | import { SignerWithAddress } from "@nomicfoundation/hardhat-ethers/signers"; 4 | import { mine, time } from "@nomicfoundation/hardhat-network-helpers"; 5 | import { Greeter } from "../typechain-types"; 6 | 7 | describe("Greeter", function () { 8 | let deployerAccount: SignerWithAddress; 9 | let greeter: Greeter; 10 | 11 | beforeEach(async function () { 12 | [deployerAccount] = await hre.ethers.getSigners(); 13 | greeter = await hre.ethers.deployContract( 14 | "Greeter", 15 | ["Hello, Hardhat!"], 16 | deployerAccount, 17 | ); 18 | await greeter.waitForDeployment(); 19 | }); 20 | 21 | it("Should return the new greeting once it's changed", async function () { 22 | expect(await greeter.greet()).to.equal("Hello, Hardhat!"); 23 | 24 | const setGreetingTx = await greeter.setGreeting("Hola, mundo!"); 25 | 26 | // Wait until the transaction is mined 27 | await setGreetingTx.wait(); 28 | 29 | expect(await greeter.greet()).to.equal("Hola, mundo!"); 30 | }); 31 | 32 | // Showcase test on how to use the Hardhat network helpers library 33 | it("Should mine the given number of blocks", async function () { 34 | const blockNumberBefore = await time.latestBlock(); 35 | 36 | await mine(100); 37 | 38 | assert.equal(await time.latestBlock(), blockNumberBefore + 100); 39 | }); 40 | }); 41 | -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "es2024", 4 | "module": "commonjs", 5 | "allowJs": true, 6 | "strict": true, 7 | "esModuleInterop": true, 8 | "outDir": "dist", 9 | "declaration": true, 10 | "forceConsistentCasingInFileNames": true, 11 | "skipLibCheck": true, 12 | "resolveJsonModule": true 13 | }, 14 | "include": [ 15 | "./scripts/**/*.js", 16 | "./scripts/**/*.ts", 17 | "./deploy/**/*.js", 18 | "./deploy/**/*.ts", 19 | "./test/**/*.js", 20 | "./test/**/*.ts", 21 | "./typechain-types/**/*.ts" 22 | ], 23 | "files": [ 24 | "hardhat.config.ts", 25 | "deploy-args.ts", 26 | "eslint.config.js", 27 | "arguments.js", 28 | ".solcover.js", 29 | "slippy.config.js" 30 | ] 31 | } 32 | --------------------------------------------------------------------------------