hardhat icon indicating copy to clipboard operation
hardhat copied to clipboard

--fork should support chainId

Open drortirosh opened this issue 2 years ago • 11 comments

when doing hardhat node --fork https://mainnet.infura.io/v3/ID the resulting chain uses the default chainId (31337), or whatever chain in the hardhat.config file.

For projects that require the real chain-id, it is far better to use the current chainId of the forked network please provide either --chainId (override the config file chainId from commandline) or --forkChainId (read chainId from the network we're forking)

drortirosh avatar Dec 16 '21 14:12 drortirosh

You can override via: the chainId property in the config.

I also add another parameter to the hre called forkName as an added failsafe

djh58 avatar Dec 17 '21 15:12 djh58

Hey @drortirosh, thanks a lot for suggesting this. As @djh58 said, the workaround for now is to set networks.hardhat.chainId in the config. There are also some shenanigans you can do with environment variables to be able to change the chain id from the command line (I can expand on this if you want).

We are planning to make a hardhat-network-cli binary to let users start a hardhat network instance outside of a hardhat project. That command will have several parameters like this. I wonder though how to call a "use the same id as the remote network" param. Since that's a somewhat unsafe thing to do (for replay reasons), we don't want to do it by default, nor to make it too easy to do. Maybe a verbose param like --unsafe-use-remote-chain-id could work.

fvictorio avatar Jan 07 '22 15:01 fvictorio

Thanks. I'm just curious how unsafe it is? It's a fork, so no transaction is actually sent.

drortirosh avatar Jan 09 '22 14:01 drortirosh

I don't think it's particularly unsafe, but I'm not a security guy so take it with a grain of salt.

The way I understand the problem is: if someone somehow has access to the transactions you are sending to Hardhat, and you are using a real account with funds (which you maybe shouldn't?), and the attacker somehow benefits from those txs (or just wants to troll you I guess), then they could take those txs and replay them in the real chain. Does that make sense?

fvictorio avatar Jan 12 '22 16:01 fvictorio

@fvictorio @drortirosh I think that's a valid risk. Here's what's in Ethers' docs:

If the chain ID is 0 will disable EIP-155 and the transaction will be valid on any network. This can be dangerous and care should be taken, since it allows transactions to be replayed on networks that were possibly not intended. Intentionally-replayable transactions are also disabled by default on recent versions of Geth and require configuration to enable.

If the chainId isn't specified it defaults to 31337 on Hardhat. Although even if you specify it to say 1, unless you're also configuring the gas price to be "market rate" that there's a good chance the transaction would fail on a live network.

Ultimately, it probably isn't a good idea to use a local fork with a real wallet with private keys, unless you're 100% sure your development environment is safe. Impersonating allows you to simulate sending actual transactions to a fork (or a regular hardhat network) and is a lot safer.

The only downside is you can't sign messages with it, so if that's something you're trying to mock out your best bet is to use a dummy account without any actual Ether

djh58 avatar Jan 12 '22 19:01 djh58

This issue was marked as stale because it didn't have any activity in the last 30 days. If you think it's still relevant, please leave a comment indicating so. Otherwise, it will be closed in 7 days.

github-actions[bot] avatar Jun 08 '22 08:06 github-actions[bot]

Not stale.

fvictorio avatar Jun 08 '22 14:06 fvictorio

Looking forward to this feature chainid impersonation will help a ton with testing flows

0xad1onchain avatar Jun 14 '22 19:06 0xad1onchain

what's the best way to set up value for hre.ethers.provider.getNetwork().name?

lebed2045 avatar Jul 04 '22 17:07 lebed2045

@fvictorio can you please expand on the way to set chainId from commandline? Also, is it possible to set a new chainId in the middle of a test suite? What is the recommended way to run test on multiple chainIds?

arr00 avatar Aug 08 '22 15:08 arr00

can you please expand on the way to set chainId from commandline?

Sure. In your Hardhat config you do something like this:

  chainId: Number(process.env.HARDHAT_CHAIN_ID)

And then you run your command like this: HARDHAT_CHAIN_ID=123 npx hardhat test

Also, is it possible to set a new chainId in the middle of a test suite?

Uhm, I don't think that's possible, at least not in an easy way.

What is the recommended way to run test on multiple chainIds?

I guess it depends on your use case. First thing that comes to mind (although far from ideal): have two separate directories in your tests and then do:

HARDHAT_CHAIN_ID=123 npx hardhat test test/a/**/*
HARDHAT_CHAIN_ID=456 npx hardhat test test/b/**/*

(I haven't tested this, but in theory it should work)

fvictorio avatar Aug 08 '22 18:08 fvictorio

what's the best way to set up value for hre.ethers.provider.getNetwork().name?

@lebed2045 have you found a way to setup a custom name? I'm also looking for a solution.

ccostel avatar Sep 23 '22 15:09 ccostel

@ccostel that seems off-topic for this issue, can you open a discussion about that? Please explain what exactly you are trying to do, because changing the name of the network on runtime seems super weird to me.

fvictorio avatar Sep 27 '22 10:09 fvictorio

Closing this in favor of https://github.com/NomicFoundation/hardhat/issues/2305, so we have only one issue dealing with this.

fvictorio avatar Dec 28 '22 16:12 fvictorio