Уважаемые пользователи Голос!
Сайт доступен в режиме «чтение» до сентября 2020 года. Операции с токенами Golos, Cyber можно проводить, используя альтернативные клиенты или через эксплорер Cyberway. Подробности здесь: https://golos.io/@goloscore/operacii-s-tokenami-golos-cyber-1594822432061
С уважением, команда “Голос”
GOLOS
RU
EN
UA
cryptminingnet
6 лет назад

Как создать собственный токен на базе ERC20 от Ethereum и запустить ICO за 20 минут

В последнее время я все чаще изучаю особенности блокчейна и децентрализованных приложений для собственного саморазвития. Для разнообразия процесса, я решил разработать свой собственный токен, основанный на Ethereum, и определить процесс запуска собственного ICO.

Путем наглядного примера по запуску собственного ICO, эта статья нацелена на объяснение основ функционирования смарт-контрактов (англ. smart-contract) в блокчейн-сети Ethereum.

Основы blockchain-сети Ethereum

Вот некоторые основные термины, которые нам понадобятся по мере создания токена. В случае, если большая часть терминов вам уже знакома, можете сразу переходить к следующему разделу.

Токены на основе ERC20 от Ethereum ERC20. В системе Ethereum, токены представляют собой любые товары, поддающиеся торговли, например, монеты, очки лояльности и т. д. На основе Ethereum вы можете создать собственные криптовалюты. Вдобавок, преимущество стандарта ERC20 заключается в совместимости всех токенов с любыми программными клиентами или цифровыми-кошельками, использующие одинаковые стандарты.

Смарт-контракты: Смарт-контракты — это самозапускающиеся программные блоки, которые функционируют на блокчейне Ethereum. Смарт-контракты способны обрабатывать не только кодовую часть, но также и информационную. Такие контракты способны принимать решения, взаимодействовать с другими контрактами, хранить данные и обмениваться Ether (единица криптовалюты в блокчейне Ethereum) между пользователями.

Solidity: Solidity — это язык для создания смарт-контрактов.MetaMask/Mist/Кошелек MEW: Все это является цифровой средой, которая хранит ваши Ether-средства и другие токены, на основе Ethereum.Шаг 1: Код

Откройте ваш любимый текстовый редактор и вставьте следующий код:

pragma solidity ^0.4.4;

contract Token {
/// @Возвращает общее количество токенов    function totalSupply() constant returns (uint256 supply) {}

/// @Параметры владельца. Адрес, с которого будут извлекаться токены.    /// @Возвращает текущий баланс.    function balanceOf(address _owner) constant returns (uint256 balance) {}

/// @Уведомляет об отправке `_value` токенов на адрес `_to` из `msg.sender`    /// @Параметр _to означает адрес получателя    /// @Параметр _value означает количество токенов, которые будут отправлены    /// @Возвращает информацию, была ли транзакция успешной или нет    function transfer(address _to, uint256 _value) returns (bool success) {}

/// @Уведомляет об отправке `_value` токенов на адрес `_to` из `_from` при условии, что подтверждено `_from`    /// @Параметр _from означает адрес отправителя    /// @Параметр _to означает адрес получателя    /// @Параметр _value означает количество токенов, которые будут отправлены    /// @Возвращает информацию, была ли транзакция успешной или нет    function transferFrom(address _from, address _to, uint256 _value) returns (bool success) {}

/// @Уведомляет `msg.sender` подтвердить `_addr` для отправки `_value` токенов    /// @Параметр _spender означает адрес счета, с которого можно отправлять токены    /// @Параметр _value означает количество токенов, которое разрешено отправить    /// @Возвращает информацию, была ли транзакция успешной или нет    function approve(address _spender, uint256 _value) returns (bool success) {}

 /// @Параметр _owner означает адрес владельца токенов    /// @Параметр _spender означает адрес счета, с которого можно отправлять токены    /// @Возвращает информацию об оставшемся количестве токенов, которое можно потратить    function allowance(address _owner, address _spender) constant returns (uint256 remaining) {}    event Transfer(address indexed _from, address indexed _to, uint256 _value);    event Approval(address indexed _owner, address indexed _spender, uint256 _value);}

contract StandardToken is Token {    function transfer(address _to, uint256 _value) returns (bool success) {         //По умолчанию предполагается, что totalSupply не может быть больше (2^256 - 1).        //Если токен не содержит totalSupply и можно неограниченно выпускать токены, необходимо следить за переконвертацией токена.        //Замените оператор if на this one.        //if (balances[msg.sender] >= _value && balances[_to] + _value > balances[_to]) {                 if (balances[msg.sender] >= _value && _value > 0) {            balances[msg.sender] -= _value;            balances[_to] += _value;            Transfer(msg.sender, _to, _value);            return true;        } else { return false; }    }

function transferFrom(address _from, address _to, uint256 _value) returns (bool success) {        //Как и указано свыше, замените эту строку ниженаписанной, если желаете защитить контракт от переконвертированных токенов.          //if (balances[_from] >= _value && allowed[_from][msg.sender] >= _value && balances[_to] + _value > balances[_to]) {        if (balances[_from] >= _value && allowed[_from][msg.sender] >= _value && _value > 0) {            balances[_to] += _value;            balances[_from] -= _value;            allowed[_from][msg.sender] -= _value;            Transfer(_from, _to, _value);            return true;        } else { return false; }    }

function balanceOf(address _owner) constant returns (uint256 balance) {        return balances[_owner];    }     function approve(address _spender, uint256 _value) returns (bool success) {        allowed[msg.sender][_spender] = _value;        Approval(msg.sender, _spender, _value);        return true;    }     function allowance(address _owner, address _spender) constant returns (uint256 remaining) {      return allowed[_owner][_spender];    }     mapping (address => uint256) balances;    mapping (address => mapping (address => uint256)) allowed;    uint256 public totalSupply;} contract HashnodeTestCoin is StandardToken { // ПОДЛЕЖИТ ИЗМЕНЕНИЮ. Обновить название контракта.     /* Публичные переменные токена */     /*    ВНИМАНИЕ:    Нижеизложенные переменные ОПЦИОНАЛЬНЫ. Нет строгой необходимости их включать.       Они позволяют кастомизировать контракт токена и не влияют на основные функции.    Некоторые цифровые-кошельки/интерфейсы могут не поддерживать эти функции.    */    string public name;                   // Название токена    uint8 public decimals;                // Как много показывать десятичных. По умолчание устанавливает значение, равное 18    string public symbol;                 // Идентификатор: например SBX, XPR и т.д...    string public version = 'H1.0';     uint256 public unitsOneEthCanBuy;     // Как много единиц вашего токена можно купить за 1 ETH?    uint256 public totalEthInWei;         // WEI равняется минимальному значению ETH (эквивалентно центу в USD или сатоши в BTC). Здесь мы будем хранить все привлеченные ETH через ICO    address public fundsWallet;           // Куда должны перенаправляться привлеченные ETH?     // Это конструктор-функция, ее имя должно соответствовать вышенаписанному названию    function HashnodeTestCoin() {        balances[msg.sender] = 1000000000000000000000;               // Предоставить создателю контракта все начальные токены. В нашем случае количество равно 1000. Если вы хотите, чтобы количество равнялось число X, а десятичные равнялись 5, установите следующее значение X * 100000. (ПОДЛЕЖИТ ИЗМЕНЕНИЮ)        totalSupply = 1000000000000000000000;                        // Обновить общий выпуск (1000 для примера) (ПОДЛЕЖИТ ИЗМЕНЕНИЮ)        name = "HashnodeTestCoin";                                   // Установить название токена для отображения на дисплее (ПОДЛЕЖИТ ИЗМЕНЕНИЮ)        decimals = 18;                                               // Количество десятичных знаков после запятой для отображения на дисплее (ПОДЛЕЖИТ ИЗМЕНЕНИЮ)        symbol = "HTCN";                                             // Идентификатор токена для отображения на дисплее (ПОДЛЕЖИТ ИЗМЕНЕНИЮ)        unitsOneEthCanBuy = 10;                                      // Установить цену за единицу вашего токена для ICO (ПОДЛЕЖИТ ИЗМЕНЕНИЮ)        fundsWallet = msg.sender;                                    // Владелец контракта получает ETH    }     function() payable{        totalEthInWei = totalEthInWei + msg.value;        uint256 amount = msg.value * unitsOneEthCanBuy;        require(balances[fundsWallet] >= amount);         balances[fundsWallet] = balances[fundsWallet] - amount;        balances[msg.sender] = balances[msg.sender] + amount;         Transfer(fundsWallet, msg.sender, amount); // Передать сообщение блокчейн-сети         //Отправить Ether в fundsWallet        fundsWallet.transfer(msg.value);                                   }     /* Верификация и затем вызов контракта */    function approveAndCall(address _spender, uint256 _value, bytes _extraData) returns (bool success) {        allowed[msg.sender][_spender] = _value;       Approval(msg.sender, _spender, _value);         //вызов функции receiveApproval в контракте, который вы хотите уведомить. Этот процесс по умолчанию создает подпись функции, но в нашем случае это не нужно включать в контракт.        //receiveApproval(address _from, uint256 _value, address _tokenContract, bytes _extraData)        //к этому моменту, вызов к функции должен пройти успешно.         if(!_spender.call(bytes4(bytes32(sha3("receiveApproval(address,uint256,address,bytes)"))), msg.sender, _value, this, _extraData)) { throw; }        return true;    }}

Вышеуказанный код для создания простого ERC20 токена написан на языке Solidity. Он хорошо прокомментирован и его можно легко понять. Вставив код в ваш текстовый редактор, найдите надпись «CHANGE THIS». Здесь вам необходимо данные, в зависимости от характеристик вашего токена. В моем случае, я назвал мой токен HashnodeTestCoin (HTCN). Общий объем выпуска ограничен и составляет 1000 токенов HTCN, однако минимально-возможное количество для хранения HTCN равняется 0.000000000000000001, поскольку в строке «decimal» установлено значение 18 — стандартное количество знаков после запятой.


Вдобавок, владелец контракта (тот, кто его исполняет), получает все начальные токены. Я установил ценовое соотношение для ICO по следующим образом:1 ETH = 10 HTCNЭто значит, что если кто-то отправит нашему смарт-контракту 1 ETH, то в обмен получит 10 HTCN.Шаг 2
Скачайте MetaMask — расширения для Chrome, чтобы сгенерировать цифровой-кошелек. Владелец этого кошелька является и владельцем смарт-контракта. В качестве альтернативы, можно использовать Mist или My Ether Wallet. Для простоты примера, в нашем проекте мы будем использовать расширение MetaMask.

Скачав и установив расширение, создайте аккаунт, защищенный паролем. Затем, в верхнем левом углу расширения выберите «Ropsten TestNet». Прежде чем запустить контракт в Main-сети Ethereum’а, мы протестируем наш контракт с помощью TestNet, чтобы убедиться, что все работает как было запланировано. Выглядит все это следующим образом:

Теперь перейдите к Remix IDE (онлайн-компилятор и отладчик Solidity) и вставьте код, который вы изменили под свои параметры. Не обращайте внимания на все возможные предупреждения. Затем перейдите в настройки и уберите флажок «Enable optimization», если он установлен.

Дальше перейдите во вкладку «Run» и нажмите на кнопку «Create», которая расположена под надписью вашего токена. Нажав на кнопку, MetaMask предложить приобрести несколько единиц Ether для теста и отправит транзакцию. Выглядит примерно так:

Убедитесь, что вы используете сеть Ropsten TestNet, а не MainNet и нажмите «Submit». Вас перенаправит на сервис Etherscan, где можно отследить текущую транзакцию. Для верификации транзакции может потребоваться примерно 30 секунд. Как только произойдет подтверждение, выглядеть все будет следующим образом:

Поздравляю! Вы только что запустили собственный смарт-контракт. Заметьте, что адрес, указанный на изображении свыше — это адрес вашего смарт-контракта.

Теперь пора проверить, работает ли все на самом деле.

Шаг 3

Если ранее все было выполнено в соответствии с инструкцией, вам должны прийти все начальные токены (в моем случае — 1000 HTCN), как только вы добавить их в свой кошелек. Поэтому скопируйте адрес контракта, перейдите в MetaMask - > Add Token и вставьте скопированный адрес. Выглядит все это дело так:

Нажмите на кнопку «Add» и перезагрузите MetaMask. Теперь вы должны увидеть всю начальную поставку (в моем случае — это все те же 1000 HTCN).

Шаг 4

Теперь, при условии, что все работает должным образом, нам нужно верифицировать наш смарт-контракт, что все участники блокчейн-сети смогли воспользоваться им. Верификация — важная составляющая, поскольку она помогает установить доверие.Теперь перейдите в Etherscan на адрес ваше смарт-контракта и нажмите вкладку «Contract Code».

Нажмите на ссылку «verify and publish». Перейдя на новую страницу, заполните все детали, начиная с версии компилятора и возможностью оптимизации. Также не забудьте вставить исходный код нашего контракта, который мы скомпилировали в первом шаге.

Поздравляю! Теперь любой может посетить страницу вашего контракта и прочитать исходный код.

Шаг 5

Чтобы окончательно запустить контракт, остается только переключить с TestNet на MainNet в расширении MetaMask (в верхнем левом углу расширения) и повторить шаги со 2 по 4. Обратите внимание, что для запуска контракта на MainNet понадобится потратить настоящий Ether. Поэтому не запускайте контракт до тех пор, пока не будете уверены на 100% (Смарт-контракты невозможно изменить и нельзя обновить после запуска). В нашем уроке, мы продолжим использовать TestNet. 


Покупка токенов за Ether
В вашем ICO, пользователи будут покупать ваши токены за ETH. Помните, что мы установили цену в 1 ETH = 10 HTCN, пока разрабатывали контракт? Так вот, если пользователь захочет на вашем ICO купить 10 HTCN, ему придется заплатить 1 ETH. Давайте проверим это на практике.Перейдите в MetaMask, создайте новый аккаунт и заполните его для теста несколькими Ether. Как только на аккаунте будут средства, нажмите «Send» и в поле адреса, вставьте адрес вашего смарт-контракта. В поле для количества токенов, введите 2 (ETH).

Отправьте 2 ETH и дождитесь подтверждения транзакции. Перезагрузите MetaMask и проверьте ваши токены через несколько секунд. Новый пробный аккаунт должен получит 20 HTCN (или другую сумму, в зависимости от того характеристик контракта) а у владельца контракта (в нашем случае это вы) должно остаться 980 (или около того) токенов HTCN.

Вдобавок вы должны получить 2 ETH.Поздравляю с успехом!

Запуск страницы ICO Чтобы отобразить количество ETH, привлеченное нашим проектом, мы будем использовать а нашем сайте библиотеку JavaScript, под названием Web3.js.

Откройте исходник страницы Hashnode Test Coin ICO и проверьте код в последнем <script> теге. Все очень просто и использует данные Web3.js наряду с двоичным интерфейсом приложения, полученные из вашего контракта.

Искренние поздравление, если вы добрались до этого шага! Помните, что настоящие смарт-контракты и ICO требуют значительных усилий и множества тестирований. Хоть этот урок и дал базовые знания для написания смарт-контрактов для ICO, он не предназначен для публичного использования. Не пытайтесь запустить наш пример на MainNet без детального тестирования.
Перевод - crypt-mining.net

Читать оригинал на английском языке.

242
0.045 GOLOS
На Golos с February 2018
Комментарии (2)
Сортировать по:
Сначала старые