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

В конце концов, есть официальная документация и stackoverflow.

В то же время, долго разбираться в документации не хочется, и многие разработчики в последнее время хотят побыстрее что-то пощупать руками и написать что-нибудь под эфириум, а так как вопросов возникает масса и источники разрознены, я решил собрать в одном месте простой пошаговый мануал с картинками по созданию своего первого dapp (от decentralized app) — децентрализованного приложения. Он будет представлять из себя связку смарт-контракта с веб-интерфейсом. То есть чтобы с помощью веба можно было доставать информацию из блокчейна и пихать ее туда. Постараюсь быть кратким, шаги буду объяснять по ходу дела.

Делай раз: ставим geth

Тут ничего сложного нет — качаем отсюда дистрибутив под свою систему, устанавливаем в какую-нибудь папку.

Картинка
image

Затем заходим в папку проводником, и видим примерно следующее:

Картинка
image

Прямо в строке, где прописывается путь до папки, image вызываем командную строку: вместо пути набираем в ней cmd, жмем Enter.
image

В командной строке вызываем geth --dev --rpc --rpcport 8545 --rpcaddr 0.0.0.0 --rpccorsdomain "*" --rpcapi "eth,web3,personal" console

В результате получаем что-то вроде этого:

image

Поздравляю, ваш локальный блокчейн в режиме develpment успешно создан! Более того, вы попросили geth работать в режиме RPC-сервера (от remote procedure call) и чтобы он слушал порт 8545.

Если вы что-нибудь испортите в вашем тестовом блокчейне — ничего страшного, его можно в любой момент создать заново, предварительно удалив все файлы из папки C:\Users\Имя_Пользователя\AppData\Local\Temp\ethereum_dev_mode\geth\chaindata. Если вы хотите хранить ваш локальный блокчейн в другой папке, то тогда вам придется попросить об этом geth примерно вот так: geth --dev --datadir "D:\testlocalchain"

Все возможные флаги и параметры вашей текущей версии geth можно получить, как водится, вызовом из консоли вашего geth c флагом помощи: geth --help

Начать пользоваться web3.js можно уже сейчас, но я предложу сделать еще пару действий.

Делай два: запускаем программу-кошелек

Качаем и устанавливаем эфириум-кошелек. Например, Mist

В папке, куда вы его поставили находим файл Mist.exe и создаем для него ярлык.

Картинка
image

В свойствах ярлыка указываем --rpc http://localhost:8545

Картинка
image

и запускаем его.

Теперь можно создать основной кошелек из этой программы, нажав на «Добавить аккаунт».

Картинка
image

Тут, я думаю, сами разберетесь.

Делай три: деплоим в локальный блокчейн самый простой контракт

Прежде, чем устанавливать новый контракт, на вашем счету должно быть хоть немного эфира.
Как же его получить? Переходим в нашу geth-консоль и пишем там команду miner.start(), после чего через пару секунд прям поверх бегущих строчек вызываем miner.stop() и жмем Enter

У меня за пару секунд получилось намайнить 48 локальных эфиров, что сразу же отразилось в кошельке Mist. Теперь можно приступить к установке простого контракта.

В Mist заходим в раздел Контракты -> Установить новый контракт

В Исходный код контракта на Solidity вставляем

pragma solidity ^0.4.13;

contract Simple{
    
    uint256 private a;
    
    function getA() constant returns (uint256) {
        return a;
    }
    
    function setA(uint256 newValue) {
        a = newValue;
    }
}

Выбираем в выпадающем списке справа Simple и жмем установить. Вводим пароль кошелька. Тем самым вы создали транзакцию, которую нужно еще замайнить. Опять запускаем в geth-консоли miner.start() и получаем наш новый контракт.
После того, как транзакция получит 12 подтверждений, остановите майнер. Теперь нас ждет самое инересное!

Делай четыре: качаем библиотеку web3.js и создаем простой html

https://github.com/ethereum/web3.js/tree/develop/dist Возьмем оттуда файл web3.js и сохраним в какую-нибудь папку. В этой же папке создадим файл a.html следующего содержания:

<script src="web3.js"></script>
<script type="text/javascript">
try {
web3 = new Web3(new Web3.providers.HttpProvider("http://127.0.0.1:8545"));
alert (web3.eth.accounts[0]);
}
catch (error) {
alert(error);
}
</script>

Если ваш geth в это время работает в режиме RPC-сервера, то запустив эту страницу вы увидите что-то вроде

image

То есть эта страница покажет адрес вашего кошелька. Либо же:

image

, если сервер не запущен, либо произошла какая-то другая ошибка соединения.

Обычно, типичная задача — это взаимодействие страницы с каким-либо контрактом.

Делай пять: взаимодействуем с контрактом

Для того, чтобы из страницы связаться с контрактом, необходимо знать две вещи: его адрес и его ABI — интерфейс взаимодействия с этим контрактом. Адрес мы можем посмотреть в Mist.

image

В моем случае он вот такой: 0x000193dC23d006DFd048533e31C66B0f0Dd9aEbA

Можем прямо здесь же вызвать функцию SetA нашего контракта.

image

Я поставил 777. Нажимаем выполнить. Теперь нужно эту транзакцию замайнить, вызвав miner.start()

Теперь я хочу получить это значение на нашей веб-странице. Зайдем на remix.ethereum.org создадим новый файл simple.sol и в разделе details сможем найти наш ABI интерфейс. Пишу не сильно подробно, благо получить этот самый интерфейс, зная код контракта, не так сложно. В нашем случае он выглядит так:

[{"constant":true,"inputs":[],"name":"getA","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"newValue","type":"uint256"}],"name":"setA","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"}]

Теперь возвращаемся к редактированию нашего файла a.html и внутри скрипта, удаляем первый алерт и пишем следующие строки, чтобы в итоге получилось следующее:

<script src="web3.js"></script>

<script type="text/javascript">
try {
web3 = new Web3(new Web3.providers.HttpProvider("http://127.0.0.1:8545"));
	
var SimpleABI = [{"constant":true,"inputs":[],"name":"getA","outputs":
[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"newValue","type":"uint256"}],"name":"setA","outputs":
[],"payable":false,"stateMutability":"nonpayable","type":"function"}];

var ContractAdress = "0x000193dC23d006DFd048533e31C66B0f0Dd9aEbA";

var SimpleContract = web3.eth.contract(SimpleABI);
var Simple = SimpleContract.at(ContractAdress);

alert (Simple.getA());
}
catch (error) {
alert(error);
}
</script>

Обновляем страничку, и что мы видим?

image

Все, профит. Таким же образом можно из JavaScript вызывать функции вашего контракта, передавая им параметры ну и всякое там делать, что позволяет либа web3.js. А позволяет она многое (курим доки).

Чтобы работать с боевым блокчейном, необходимо будет либо на своей машине держать синхронизированную ноду, либо знать адрес и порт какого-нибудь RPC-сервера. Всё, всем добра!

Комментарии (1)


  1. Psychosynthesis
    11.12.2017 08:25

    Спасибо, статья познавательная!