Tokens – Resolving Token Approval Questions and Issues With ERC-20

decentralized-exchangeerc-20-approvetokens

I had a DEX approve 1000 USDT. I then traded 1000 USDT. The next day I want to trade another 1000 USDT from the same address, but the same DEX asks me for approval again! On Etherscan Token Approvals my address has 1000 USDT approved for this DEX (including version). Now the questions:

  1. Why does it ask for approval again (same address, same DEX version)?

  2. When 1000 USDT is approved, it means I can spend no more than 1000 USDT at a time for as many times as allowed by the balance of my account?

  3. Is there any point in approving less than the maximum amount? Because if the answer to the second question above is “yes”, then what prevents a thief’s bot from running the withdrawal transaction a few (dozen) times instead of just once?

  4. On the other hand, if an approval for an amount is only valid once, then why do DEXs say that you need to approve a token just once, why do well-respected people advise to revoke approvals and why does the Etherscan Token Approvals site menacingly states “$xxx at risk”, when all these approvals have long been used?

Thanks a lot in advance.

Best Answer

It asks for approval again because you used all the allowance on your first transfer.

There is a fundamental error in how you understand approval.

When you approve the DEX to spend 10 000 of your coins, you write on the erc20's contract that the dex address can spend 10000 of your coins. So when the DEX contacts the erc20's contract and ask to use 10000 of your tokens, the contract checks that allowance and reduces it by 10000 tokens.

Here's a look at the code from openzeppelin

    function _spendAllowance(address owner, address spender, uint256 amount) internal virtual {
        uint256 currentAllowance = allowance(owner, spender);
        if (currentAllowance != type(uint256).max) {
            require(currentAllowance >= amount, "ERC20: insufficient allowance");
            unchecked {
                _approve(owner, spender, currentAllowance - amount);
            }
        }
    }

You can see on the last line, the new allowance in 'currentAllowance - amount', which, in your case, would be 10 000 - 10 000 = 0.

So now, the DEX allowance over your tokens is 0 and if you want to allow the DEX to use more of your tokens you will have to do another approve().

That should have answered your point number 2. If approving 10 000 tokens meants that approved address could only spend 10 000 tokens per transaction, then anyone approved of 1 tokens could empty your total balance by just spamming the transferFrom function.

And for point number 3, it's usually bad practice to approve uint max value since that's a very very big number and doesn't allow a good control over the spending of the third party.

Hope this helps!

Related Topic