I am trying to call transfer of an ERC20 token from another "escrow" smart contract in remix JavaScript VM (London). I have 2 contracts like so:
MyToken.sol (an ERC20Votes.sol, but "votes" should not affect anything here?):
//SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
import "@openzeppelin/contracts/token/ERC20/extensions/ERC20Votes.sol";
contract MyToken is ERC20Votes {
uint256 public maxSupply = 555; // * 10**18;
constructor() ERC20("MyToken", "MT") ERC20Permit("MyToken") {
_mint(msg.sender, maxSupply);
}
// The functions below are overrides required by Solidity.
function _afterTokenTransfer(
address from,
address to,
uint256 amount
) internal override(ERC20Votes) {
super._afterTokenTransfer(from, to, amount);
}
function _mint(address to, uint256 amount) internal override(ERC20Votes) {
super._mint(to, amount);
}
function _burn(address account, uint256 amount)
internal
override(ERC20Votes)
{
super._burn(account, amount);
}
}
Escrow3.sol
//SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
import "@openzeppelin/contracts/token/ERC20/ERC20.sol";
import "hardhat/console.sol";
contract Escrow3 {
ERC20 token;
constructor(address _token) {
token = ERC20(_token);
}
function confirm(
address _recipient,
uint256 _amount
) external {
require(msg.sender != _recipient, "Caller cannot be recipient");
require(token.balanceOf(msg.sender) >= _amount, "Insufficient funds");
bool sent = token.transfer(_recipient, _amount);
require(sent, "transfer fail");
}
function getBalanceToken() external view returns(uint256) {
return token.balanceOf(msg.sender);
}
}
In remix, I first deploy MyToken.sol, then deploy Escrow3.sol with MyToken's address in its constructor. With the deployer's address, I then call getBalanceToken in remix and it returns 555 as expected. In remix, I then call (via deployer's address) confirm with _recipient = another address and _amount = 5. I get this error:
ERC20: transfer amount exceeds balance
This is strange because getBalanceToken clearly shows deployer's address with enough tokens in balance and the check for Insufficient funds did not revert in the confirm function.
I have tried everything and looked everywhere and I still do not understand how to solve this.
transferbut it will not work in your contract. See for an explanation here: https://ethereum.stackexchange.com/questions/46457/send-tokens-using-approve-and-transferfrom-vs-only-transfer. – Ismael Nov 06 '21 at 05:30I have also tried approve _ transferFrom, but I can get it to work in the same contract.
– user82768 Nov 06 '21 at 05:35