receive() function fails in tests when using hardhat's console.log (and other weird behaviour)
Version of Hardhat
2.12.6
What happened?
I have receive() function in a dedicated contract presented below.
I'm testing it with Hardhat using forked mainnet and get two bugs:
- Uncommenting
console.logbreaks tests - Commenting
msg.sender == 0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2also breaks tests. While definitelyaddress(WETH) == 0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2
Errors happen when WETH contract sends ETH to my contract.
pragma solidity ^0.8.0;
import "./UsingGlobals.sol";
import "hardhat/console.sol";
// Receives eth from WETH contract when converting weth to eth
// Also receives eth from oldMEH when unwrapping blocks
contract Receiver is UsingGlobals {
receive() external payable {
// the console.log's here are meant to fix some hardhat bug
// turn them on for testing locally with mocks (no hardfork)
// console.log("....Receiver. msg.sender", msg.sender);
// console.log("....Receiver. address(WETH)", address(WETH));
require((
msg.sender == address(oldMeh) ||
// hardhat bug, uncomment the line below to fix flashloaner.js tests.
// address(WETH) returns same address, but in lower case - reason?
// safe to use real weth address in production
// but may be harmfull if using hardhat's mocked address
// TODO check before production deployment
msg.sender == 0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2 ||
msg.sender == address(WETH)
), "Receiver: Only receives from oldMEH or WETH");
// console.log("Flashloaner contract eth balance", address(this).balance);
}
}
When uncommenting `console.log' the error is:
Error: Transaction reverted and Hardhat couldn't infer the reason.
at FlashloanerAdapter._sendLogPayload (hardhat/console.sol:12)
at FlashloanerAdapter.log (hardhat/console.sol:217)
at FlashloanerAdapter.<receive> (contracts/Receiver.sol:15)
at <UnrecognizedContract>.<unknown> (0xc02aaa39b223fe8d0a0e5c4f27ead9083c756cc2)
at FlashloanerAdapter.receiveFlashLoan (contracts/Flashloaner.sol:50)
at <UnrecognizedContract>.<unknown> (0xba12222222228d8ba445958a75a0704d566bf2c8)
at FlashloanerAdapter._borrow (contracts/Flashloaner.sol:26)
at FlashloanerAdapter.borrowExt (contracts/test_adapters/Flashloaner.sol:10)
at HardhatNode._mineBlockWithPendingTxs (node_modules/hardhat/src/internal/hardhat-network/provider/node.ts:1815:23)
at HardhatNode.mineBlock (node_modules/hardhat/src/internal/hardhat-network/provider/node.ts:504:16)
at EthModule._sendTransactionAndReturnHash (node_modules/hardhat/src/internal/hardhat-network/provider/modules/eth.ts:1522:18)
at HardhatNetworkProvider.request (node_modules/hardhat/src/internal/hardhat-network/provider/provider.ts:118:18)
at EthersProviderWrapper.send (node_modules/@nomiclabs/hardhat-ethers/src/internal/ethers-provider-wrapper.ts:13:20)
When commenting address error is as follows. I already tried to investigate it before and found out that msg.sender and address(WETH) while same come in different letter cases (lower case and mixed). It only happened in this function.
Error: Transaction reverted without a reason string
at FlashloanerAdapter.<anonymous> (contracts/Receiver.sol:11)
at <UnrecognizedContract>.<unknown> (0xc02aaa39b223fe8d0a0e5c4f27ead9083c756cc2)
at FlashloanerAdapter.receiveFlashLoan (contracts/Flashloaner.sol:50)
at <UnrecognizedContract>.<unknown> (0xba12222222228d8ba445958a75a0704d566bf2c8)
at FlashloanerAdapter._borrow (contracts/Flashloaner.sol:26)
at FlashloanerAdapter.borrowExt (contracts/test_adapters/Flashloaner.sol:10)
at HardhatNode._mineBlockWithPendingTxs (node_modules/hardhat/src/internal/hardhat-network/provider/node.ts:1815:23)
at HardhatNode.mineBlock (node_modules/hardhat/src/internal/hardhat-network/provider/node.ts:504:16)
at EthModule._sendTransactionAndReturnHash (node_modules/hardhat/src/internal/hardhat-network/provider/modules/eth.ts:1522:18)
at HardhatNetworkProvider.request (node_modules/hardhat/src/internal/hardhat-network/provider/provider.ts:118:18)
at EthersProviderWrapper.send (node_modules/@nomiclabs/hardhat-ethers/src/internal/ethers-provider-wrapper.ts:13:20)
Minimal reproduction steps
This is hard to reproduce. I made a git checkpoint commit where it is easy to do. https://github.com/porobov/meh-resurrections/commit/562eb0d41c5e0a4ece6e6e8e0819a498ff5de089
Steps to reproduce:
- download git checkpoint from above
- run npx hardhat test test/flashloan.js --network hardhat. It should work fine.
- uncomment any of the console.log lines
- run the test again and see the error 1
- revert changes, comment the address line and see the error 2
Search terms
console.log breaks tests receive function fails
Hi @porobov , could you please check the commit link? I'm receiving a 404 error when trying to access it. I've checked your public repositories, but I couldn't find a repository named "meh-resurrections". Is it possible that it's a private repository? If so, could you please create a simple repository with the minimal steps to reproduce the error so that I can take a look? Thanks
Oops, apologies for that @ChristopherDedominici. Yes, it was private. Made it public.
Here's also a .env template if the code will require it (I noticed it was in .gitignore).
REPORT_GAS=false
GAS_PRICE_GWEI=30
ETH_USD_USD=1700
ETHERSCAN_API_KEY=""
# gateways
ALCHEMY_MAINNET_URL=""
ALCHEMY_GOERLI_URL=""
Thanks @porobov, I'll take a look
Updated many packages, including:
"hardhat": "^2.21.0",
"ethers": "^6.11.1",
"@nomicfoundation/hardhat-toolbox": "^4.0.0",
Latest node and npm. node v20.11.1 npm 10.5.0
Made another checkpoint https://github.com/porobov/meh-resurrections/commit/b24929dec9c88804f9fd5681eb09200ae698623a
Steps to reproduce (running it on localhost now):
- download git checkpoint from above
- run
npx hardhat test test/flashloan.js --network localhostornpx hardhat test test/MehERC721.js --network localhost. It should work fine. - uncomment
console.log("....Receiver. address(WETH)", address(WETH))to breakMehERC721.jstest - uncomment also
console.log("Flashloaner contract eth balance", address(this).balance);to breakflashloan.jstest
@ChristopherDedominici I don't think it's the only problem of console.log, I added simple line ++count; to track the number of receive function calls, however it fails. For now, I see only require lines are working as expected