Skip to content

Repository files navigation

PolkaVM Hardhat Template

A starter template for building and deploying Solidity contracts to both EVM and PolkaVM (Polkadot) from a single project, using Hardhat + resolc + Foundry.

Click "Use this template" on GitHub to create your own repository, drop your contracts into src/, and deploy to Anvil, a local PolkaVM node, or a testnet with one command.

The same Solidity compiles two ways:

  • EVM via solc: Anvil, Base Sepolia, Ethereum Sepolia, any EVM chain.
  • PolkaVM via resolc (@parity/hardhat-polkadot): a local revive dev node, Polkadot Hub testnet.

This template was produced under the ZK Email Kusama grant (Milestone 2) as the reusable project-structure / tooling outcome, stripped of the zkemail-specific verifier contracts and shipped with a plain Counter example so anyone can reuse it.

What's in here

Path Purpose
src/Counter.sol Example contract. Replace with your own.
hh-ignition/modules/Counter.ts Hardhat Ignition deployment module (primary deploy path).
test/Counter.t.sol Foundry test.
hardhat.config.ts solc + resolc build targets and EVM / PolkaVM networks.
foundry.toml Foundry build/test config.
bin/setup-dev-node.sh Downloads the local PolkaVM dev node + eth-rpc adapter.

Prerequisites

  • Node.js + Yarn
  • Foundry (forge, anvil, cast) for tests and the EVM local flow
  • macOS (arm64) or Linux (x86_64) for the bundled PolkaVM dev-node binaries

Install dependencies:

yarn

Environment

Copy .env.example to .env and fill in what you need:

Variable Required Description
PRIVATE_KEY For deploys EOA private key used to broadcast transactions (Hardhat accounts when set).
ETHERSCAN_API_KEY Verification only API key for an Etherscan-compatible explorer.

localEvm and localPvm use a fixed http://127.0.0.1:8545 URL; PRIVATE_KEY is only attached when set, so local PolkaVM dev defaults work even when you omit it.

Build

yarn build      # hardhat compile (solc + resolc)

Test

forge test

Local deploy

A) Local PolkaVM node

Terminal 1, fetch the dev-node binaries (once) and start the node:

yarn setup-pvm-node   # download dev-node + eth-rpc binaries (once)
yarn pvm-node         # start the local PolkaVM node + Eth-RPC adapter

This starts the revive dev node and an Eth-RPC adapter on 127.0.0.1:8545.

Terminal 2, build and deploy against the localPvm network:

yarn build
yarn deploy localPvm

B) Local EVM (Anvil)

Terminal 1:

anvil

Terminal 2, build and deploy against the localEvm network:

yarn build
yarn deploy localEvm

No PRIVATE_KEY needed: with none set, Hardhat uses Anvil's default unlocked account #0 (same as the localPvm flow). Set PRIVATE_KEY in .env only if you want to deploy from a specific account.

Testnet deploy

Create and fund a wallet

The deployer account needs testnet funds to deploy. Create a fresh keypair (Foundry's cast ships with this repo):

cast wallet new
# Successfully created new keypair.
# Address:     0xYourAddress...
# Private key: 0xYourPrivateKey...

Put the private key into .env (add RPC_URL to override the default RPC for the target network):

PRIVATE_KEY=<the private key from your cast wallet new output above>

Fund the address with testnet PAS, then confirm it arrived:

  • Faucet: https://faucet.polkadot.io/, select the Polkadot Hub TestNet (Paseo Asset Hub) and paste your address.
  • Explorer: https://blockscout-testnet.polkadot.io/address/<your address>

For the EVM testnets below, use that chain's own faucet (e.g. a Base Sepolia or Ethereum Sepolia faucet) to fund the same address.

Deploy

Pass a network keyed by chain ID from hardhat.config.ts:

yarn deploy 420420417   # Polkadot Hub testnet (PolkaVM)
yarn deploy 84532       # Base Sepolia (EVM)
yarn deploy 11155111    # Ethereum Sepolia (EVM)

Hardhat Ignition stores deployment artifacts under hh-ignition/deployments.

Verify

EVM

For EVM networks with a working Etherscan-compatible API (e.g. Base Sepolia):

yarn verify chain-84532

PolkaVM

Source-code verification is not currently possible for PolkaVM deployments. The contract is resolc-compiled to PolkaVM/RISC-V bytecode; the Blockscout explorer's verification API and @nomicfoundation/hardhat-verify both only support EVM solc/Vyper bytecode, and @parity/hardhat-polkadot does not yet provide a resolc-aware verify task. This is a PolkaVM tooling gap, not a deployment issue.

The contract is still fully visible on Blockscout (address, PolkaVM bytecode, transactions) and is exercisable via its read/write methods.

Adding your own contract

  1. Add your contract under src/ (remove Counter.sol if you don't need it).
  2. Update hh-ignition/modules/Counter.ts (or add a new module) to deploy it, passing any constructor args via m.contract("YourContract", [args]).
  3. Point the deploy script in package.json at your module.
  4. Update the Foundry test/ files to match.

Command reference

Command Description
yarn build Compile contracts with Hardhat (solc + resolc).
yarn deploy <network> Deploy with Hardhat Ignition to the given network.
yarn verify chain-<id> Verify an Ignition deployment.
yarn setup-pvm-node Download the local PolkaVM dev node + eth-rpc adapter.
yarn pvm-node Start the local PolkaVM node + Eth-RPC adapter.
forge test Run Foundry tests.

License

MIT

About

Starter template for building and deploying Solidity to both EVM and PolkaVM (Polkadot) with Hardhat, resolc, and Foundry.

Topics

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages