简体   繁体   English

空投合约 - 合约无法发送代币 - ERC20 转账金额超过限额

[英]Airdrop contract - Contract can't send token - ERC20 transfer amount exceeds allowance

I am trying to create a contract which will be used as an airdrop contract.我正在尝试创建一个将用作空投合同的合同。 I will send tokens from a contract already deployed to it, and then any user can claim tokens to this airdrop contract.我将从已经部署到它的合约中发送代币,然后任何用户都可以向该空投合约索取代币。 However I got an error : ERC20 transfer amount exceeds allowance.但是我收到一个错误:ERC20 转账金额超出限额。 I am using transferFrom for this, I tried to increase allowance of the airdrop contract address, to approve .. like I saw in other posts, but still doesn't work.我为此使用了transferFrom,我试图增加空投合约地址的限额,以批准..就像我在其他帖子中看到的那样,但仍然不起作用。 With the function transfer, I got an other error : solidity safemath subtraction overflow.通过函数转移,我得到了另一个错误:solidity safemath 减法溢出。

Do you have any idea what I am doing wrong ?你知道我做错了什么吗?

airdrop.sol 

// SPDX-License-Identifier: GPL-3.0
pragma solidity ^0.8.0;

abstract contract Context {
    function _msgSender() internal view virtual returns (address) {
        return msg.sender;
    }

    function _msgData() internal view virtual returns (bytes calldata) {
        return msg.data;
    }
}
abstract contract Ownable is Context {
    address private _owner;

    event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);


    constructor() {
        _transferOwnership(_msgSender());
    }

   
    function owner() public view virtual returns (address) {
        return _owner;
    }

    
    modifier onlyOwner() {
        require(owner() == _msgSender(), "Ownable: caller is not the owner");
        _;
    }

   
    function renounceOwnership() public virtual onlyOwner {
        _transferOwnership(address(0));
    }

   
    function transferOwnership(address newOwner) public virtual onlyOwner {
        require(newOwner != address(0), "Ownable: new owner is the zero address");
        _transferOwnership(newOwner);
    }

   
    function _transferOwnership(address newOwner) internal virtual {
        address oldOwner = _owner;
        _owner = newOwner;
        emit OwnershipTransferred(oldOwner, newOwner);
    }

  
}

interface token{
     function transfer(address recipient, uint256 amount) external returns (bool);

     function transferFrom(address sender, address recipient, uint256 amount) external returns (bool);
}

contract airTortuga is Ownable{

      mapping (address=>bool)claimed;
      mapping (address=>bool) _blacklistedaddress;
      uint public amountToken=110000*10**9;
      uint public _airdropDelivered = 0;
      bool public airdropAlive = false;
      
      token _token;
      address[]  _blacklistedaddresses=[...];
      
      function setclaimtokenaddress(address add)public onlyOwner{
          _token=token(add);
      }
      function settokenamounttobeclaimed(uint amount)public onlyOwner{
          amountToken=amount*10**9;
      }
      function removeblackListAddress(address add)public onlyOwner{
           _blacklistedaddress[add]=false;
      }
      function resetairdropnumber()public onlyOwner{
          _airdropDelivered = 0;
      }
      function enableAirdropAlive()public onlyOwner{
          airdropAlive = true;
      }
      function disableAirdropAlive()public onlyOwner{
          airdropAlive = false;
      }
      
      function  blackListAddress()public onlyOwner{
          for (uint i; i<=_blacklistedaddresses.length-1; i++){
          _blacklistedaddress[_blacklistedaddresses[i]]=true;
          }
      }

      function claim()public{
          require(_blacklistedaddress[msg.sender]==false,'cant claim address blacklisted ');
          require(claimed[msg.sender]==false,'already claimed');
          require(airdropAlive==true,'no airdrop alive');
          
          _token.transferFrom(address(this), msg.sender, amountToken );
          _airdropDelivered = _airdropDelivered + 1;
          
          claimed[msg.sender]=true;
      }
    
}

Change the line换行

_token.transferFrom(address(this), msg.sender, amountToken );

to

_token.transfer( msg.sender, amountToken );

Since you are calling the function from the smart contract, the sender is implicity the contract itself.由于您是从智能合约中调用该函数,因此发送者是合约本身的隐含。

If you want to use .transferFrom() you have to first approve the transaction with .approve()如果你想使用.transferFrom()你必须先用.approve()批准交易

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM