How do exchanges interact with an ERC-20 contract? What functions do exchanges use?

Hello,

This is my first post on OpenZeppelin, but I've been following the forum for a while, and have gotten a lot of useful information from it, so thank you to all of the contributors reading this.

My question pertains to how exchanges interact with ERC-20 contracts - both centralized and decentralized exchanges. Though I've noted some circumstantial evidence that exchanges use the approve and transferFrom functions of a token, I'd like to gain an in-depth understanding of the process.

So, let's take the simplest token possible, one built using the openezeppelin ERC20 contract:

pragma solidity ^0.8.2;

import "@openzeppelin/contracts/token/ERC20/ERC20.sol";

contract MyToken is ERC20 {
    constructor() ERC20("MyToken", "MTK") {}
}

here are two scenarios:

Scenario A. Coinbase litsts MTK. Alice wants to buy some MTK from Coinbase. So Alice goes on Coinbase, and pays some fiat money for tokens. She then transfers the tokens into her personal wallet.

Scenario B. An MTK-ETH liquidity pool is set up on Uniswap. Bob acquires some MTK from that liquidity pool, and stores it in his wallet.

So how do Coinbase and Uniswap actually interact with the MTK contract? Do they somehow use the approve and transferFrom functions, or do they use the transfer function?

I am building a token with some unique features, and this info would help in my development process.

Feel free to ask for clarification if needed.

Thank you

Coinbase is a centralized custodial exchange/wallet. This means that while your token balance is on Coinbase they completely control it, in fact it's likely pooled together with the balances of many of the other users of the platform, and your own balance is an entry in their centralized database. When you transfer your balance from Coinbase to your own self-custody wallet, they use ERC20 transfer to move those funds on chain.

Uniswap and other decentralized exchanges do not work like this. They don't hold your assets (unless you're providing liquidity), so when you interact with the exchange you give it (ideally temporary) permission to transfer the asset on your behalf, under the rules established by the contract such as that after taking X tokens they will transfer Y of some other token to your account. The way to give this permission to transfer on your behalf is through approve which grants allowance to the Uniswap contract, and this allowance is then used by the contract through transferFrom.

Hope this clears things up for you!

That's great, really helpful. Thanks @frangio!

Hi, is there a solution from Openzeppelin to implement custodial wallets?

Custodial wallets are usually off-chain things. OpenZeppelin doesn't offer any sort of custodial solution.