Nodejs
在 Hardhat 和 Ethers.js 中部署之前找到合約的地址
我有 2 個合約,它們將彼此的地址作為建構子參數。這是虛擬碼,
constructor A(address B) constructor B(address A)
我正在使用部署契約
const Contract = await ethers.getContractFactory(contractName) const contract = await Contract.deploy(...args) await contract.deployed() console.log(contract.address) // I want to find address before, not after deployment
部署前如何找到合約地址?
@ethersproject/address
提供getContractAddress()
查找未來部署地址的功能。const { ethers } = require('hardhat') const { getContractAddress } = require('@ethersproject/address') async function main() { const [owner] = await ethers.getSigners() const transactionCount = await owner.getTransactionCount() const futureAddress = getContractAddress({ from: owner.address, nonce: transactionCount }) }
合約地址是確定性的,需要部署者地址和隨機數來預先計算它。
您可以使用以下程式碼在部署前確定合約地址。
const rlp = require('rlp'); const keccak = require('keccak'); const web3 = require('web3') const encodedData = rlp.encode([ '0x6c4465dc4dc3466c5736142ce8e12917a1e22c4', // address from which contract is to be deployed web3.utils.toHex(4) // hex encoded nonce of address that will be used for contract deployment ]); const contractAddress = `0x${keccak('keccak256').update(encodedData).digest('hex').substring(24)}` console.log({contractAddress}
但我會建議在第二個合約中添加一個方法,稍後更新合約地址。確保該函式只能呼叫一次,這將是一種更可靠的方法。
範常式式碼:
pragma solidity 0.6.8; contract A { address b; function addSecondaryContract(address _b) public /* onlyOwner */ { require(b != address(0), "contract already added"); b = _b; } } contract B { address a; constructor(address _a) public{ a = _a; } }