Перейти к основному контенту

Переводы и подтверждение токенов ERC-20 из умного контракта Solidity

Умные контракты
токенов
Solidity
erc-20
Intermediate
jdourlens
7 апреля 2020 г.
6 минута прочтения

В предыдущем руководстве мы изучили анатомию токена ERC-20 в Solidity в блокчейне Ethereum. В этой статье мы рассмотрим, как можно использовать умный контракт для взаимодействия с токеном с помощью языка Solidity.

Для этого умного контракта мы создадим настоящую учебную децентрализованную биржу, где пользователь сможет обменять эфир на наш недавно развернутый токен ERC-20.

Для этого руководства мы будем использовать в качестве основы код, который мы написали в предыдущем руководстве. Наш DEX будет создавать экземпляр контракта в своем конструкторе и выполнять следующие операции:

  • обмен токенов на эфир
  • обмен эфира на токены

Мы начнем писать код нашей децентрализованной биржи, добавив нашу простую кодовую базу ERC20:

Наш новый умный контракт DEX развернет ERC-20 и получит все созданные токены:

Итак, теперь у нас есть наш DEX, и у него в наличии весь резерв токенов. У контракта есть две функции:

  • buy: пользователь может отправить эфир и получить взамен токены
  • sell: пользователь может отправить токены, чтобы получить обратно эфир

Функция buy

Давайте напишем код для функции buy. Сначала нам нужно будет проверить количество эфира, которое содержит сообщение, и убедиться, что у контракта достаточно токенов и что в сообщении есть некоторое количество эфира. Если у контракта достаточно токенов, он отправит их пользователю и сгенерирует событие Bought.

Обратите внимание, что если мы вызовем функцию require в случае ошибки, отправленный эфир будет немедленно возвращен пользователю.

Для простоты мы обмениваем 1 токен на 1 wei.

function buy() payable public {
    uint256 amountTobuy = msg.value;
    uint256 dexBalance = token.balanceOf(address(this));
    require(amountTobuy > 0, "Нужно отправить немного эфира");
    require(amountTobuy <= dexBalance, "Недостаточно токенов в резерве");
    token.transfer(msg.sender, amountTobuy);
    emit Bought(amountTobuy);
}

В случае успешной покупки мы должны увидеть в транзакции два события: Transfer токена и Bought.

Два события в транзакции: Transfer и Bought

Функция sell

Функция, отвечающая за продажу, сначала потребует от пользователя предварительно подтвердить сумму, вызвав функцию approve. Подтверждение перевода требует, чтобы пользователь вызвал контракт токена ERC20Basic, экземпляр которого был создан DEX. Этого можно достичь, сначала вызвав функцию token() контракта DEX, чтобы получить адрес, по которому DEX развернул контракт ERC20Basic, названный token. Затем мы создаем экземпляр этого контракта в нашей сессии и вызываем его функцию approve. Затем мы можем вызвать функцию sell контракта DEX и обменять наши токены обратно на эфир. Например, вот как это выглядит в интерактивной сессии brownie:

Затем, когда вызывается функция sell, мы проверим, был ли успешным перевод с адреса вызывающего на адрес контракта, а затем отправим эфир обратно на адрес вызывающего.

function sell(uint256 amount) public {
    require(amount > 0, "Вы должны продать хотя бы несколько токенов");
    uint256 allowance = token.allowance(msg.sender, address(this));
    require(allowance >= amount, "Проверьте разрешенное количество токенов");
    token.transferFrom(msg.sender, address(this), amount);
    payable(msg.sender).transfer(amount);
    emit Sold(amount);
}

Если все сработает, вы должны увидеть в транзакции 2 события (Transfer и Sold), а также обновленные балансы токенов и эфира.

Два события в транзакции: Transfer и Sold

Из этого руководства мы узнали, как проверять баланс и разрешенное количество для токена ERC-20, а также как вызывать Transfer и TransferFrom смарт-контракта ERC20 с помощью интерфейса.

После того как вы совершите транзакцию, у нас есть руководство по JavaScript о том, как ожидать и получать сведения о транзакциях (opens in a new tab), которые были совершены с вашим контрактом, и руководство по декодированию событий, сгенерированных переводами токенов или любыми другими событиями (opens in a new tab), если у вас есть ABI.

Вот полный код для этого руководства:

Последнее обновление страницы: 3 марта 2026 г.

Было ли это руководство полезным?