Как запустить свой блокчейн

Как запустить свой блокчейн: поднимаем тестовую сеть и оцениваем производительность

СТАТЬИ 

14.05.2020

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

Чтобы помочь проектам избежать таких ошибок, руководитель отдела исследований MixBytes Сергей Прилуцкий подготовил пошаговое руководство по запуску тестнета и оценки его производительности.

Итак, вы выбрали блокчейн-движок и реализовали первую версию собственного блокчейна. Теперь, чтобы проверить стабильность сети при изменениях, потребуется полномасштабное тестирование. А чтобы будущие пользователи и валидаторы смогли заранее подготовить свои сервисы к реальным условиям, требуется тестовая сеть (или testnet) — максимально полная копия основной сети.

Без тестнета вы не сможете качественно проверить разрабатываемый код, а пользователи не смогут попробовать ваши сервисы в “лабораторных” условиях.

Тестирование и мониторинг блокчейна

Я уже неоднократно писал про тестирование блокчейнов (читайте здесь и здесь), поэтому предлагаю сосредоточиться на практических вопросах. При работе блокчейна в основной сети вы можете столкнуться со множеством проблем, которые стоит решить заранее. Приведу несколько примеров возможных технических проблем:

  • блокчейн оперирует транзакциями, сохраняющими довольно объемные данные. Запуск и поддержка ноды могут потребовать слишком много места на диске, а стоимость владения нодой для валидаторов быть очень высокой.
  • вы все правильно оценили, эффективно сжали данные транзакций, и на тестовых машинах разработчиков рост блокчейна стал удовлетворительным. Однако сжатие данных потребовало от нод много ресурсов процессора, что сильно замедлило общую производительность сети.
  • вы нашли оптимальный баланс между размером и сложностью обработки транзакций, и блокчейн отлично работает на машинах разработчиков. Однако между ними локальная сеть, и после ее запуска в глобальной сети блоки стали передаваться медленно, а скорость сети сильно снизилась.
  • вы оптимизировали сеть за счет более эффективного консенсуса, но теперь финализация блоков стала отставать.

Продолжать можно бесконечно. И это только верхушка айсберга — ведь еще есть экономические и организационные проблемы. Многие из них можно решить за счет грамотного проектирования и подбора алгоритмов, но лучше использовать комплексный подход.

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

Мониторинг

Практически во всех современных блокчейнах предусмотрена возможность подключения внешнего мониторинга для своевременного выявления ошибок. Это не только система уведомлений, сообщающая о критических проблемах, но и сбор важных метрик с нод. Задача системы сбора метрик — проинформировать вас о резких изменениях в одном из компонентов и помочь быстрее найти причину деградации сети.

Необходимо отслеживать как стандартные системные параметры (загрузку процессора и жесткого диска, объем потребляемой оперативной памяти, сетевой трафик), так и специфичные метрики (консенсуса и логики процессинга).

Если вы вносите изменения в сетевой консенсус, то важными метриками будут те, что относятся к его внутренней логике. Для finalitу gadget важно, насколько последний финализированный блок отстал от последних блоков цепочки. Если изменяется сетевой p2p-слой, то полезной метрикой может быть количество активных пиров (peers — равноправные участники сети). Для сложных транзакций можно измерять время и ресурсы, необходимые для того, чтобы упаковать их в блок.

К сожалению, универсального набора метрик не существует. Обязательно добавляйте в мониторинг метрики (например, время процессинга транзакций, или отставание последнего финализированного блока), позволяющие увидеть проблемы в компонентах — так вы сэкономите время и вовремя заметите ошибки. Сделать это несложно, так как во всех современных блокчейн-движках можно отправлять данные на мониторинговые сервера (обычно это комплекс Prometheus + Grafana). Для добавления новой метрики просто скопируйте пару строчек кода.

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

Тестирование

С точки зрения тестирования, блокчейны выглядят как базы данных с механизмом репликации типа master-master. Для тестирования распределенных БД существует набор инструкций бенчмарков. Например, TPC или YCSB используют при тестировании новых алгоритмов репликации.

Подобных стандартов для блокчейнов пока не существует. В блокчейне возможно изменить число валидаторов при получении нескольких транзакций (добавить новых или исключить старых). Как я уже говорил, блокчейны — это сети, которые должны оставаться работоспособными при массированных атаках и сговорах, даже если часть валидаторов будет отключена или захвачена атакующими.

Чтобы проверить устойчивость сети под нагрузкой, необходимо запускать тест каждый раз после внесения изменений в консенсус или логику основных транзакций. Например, если в транзакцию добавились новые объемные метаданные или использовался новый алгоритм. При этом важна повторяемость теста — недостаточно просто запустить небольшую тестовую сеть, обновить код на нодах и запустить скрипт, отправляющий транзакции. Без воспроизведения всех начальных условий в тест будут вмешиваться внешние факторы. Хороший пример — дисковый кэш. В первом тесте данные будут считываться и записываться на диск с одной скоростью, а во второй — гораздо быстрее, и вы можете ошибочно принять это ускорение за улучшение производительности блокчейна.

Подбор последовательностей транзакций для теста тоже важен. Например, 1000 транзакций, переводящих некоторую сумму токенов между 2-мя аккаунтами — совсем не то же самое, что транзакции, переводящие токены между 1000 разными аккаунтами. Последние порождают разное поведение памяти, диска и процессора на нодах. Для хороших результатов тестов паттерн должен быть таким, чтобы система могла минимально «помочь» ускорить его в уязвимых местах. Для тестирования платежных транзакций разумно использовать N случайных аккаунтов (каждый раз новых) и транзакции, переводящие случайные количества токенов, а для хранения файлов — файлы со случайным содержимым.

Для блокчейнов и смарт-контрактов лучше всего подходит парадигма «разработки через тестирование» (Test Driven Development или TDD), которая подразумевает постоянное добавление новых сценариев тестирования, и принятие кода только, если он успешно проходит их все. Сценариев взаимодействия — множество, и незначительная ошибка в одном из них может привести к плохим последствиям в другом. Также TDD с первых дней заставит вас заниматься автоматизацией разворачивания блокчейна и сэкономит много времени на последующих этапах.

Автоматизация развертывания тестовой сети

Автоматизация запуска блокчейна «с нуля» позволяет разработчикам и команде проекта:

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

Разворачивание блокчейна не сильно отличается от сценариев запуска кластера БД, и местами может быть даже проще благодаря peer-to-peer сети. Вот часть сценариев по развертыванию тестовой сети Polkadot с boot-нодой для массивных тестов производительности сети на основе движка Parity Substrate. Такие же сценарии для тестирования движка Haya сэкономили нам огромное количество времени на запуск сети.

Сценарии для развертывания валидаторов могут требовать жестко прописать peer-id всех валидаторов. Таким образом они никогда не исключат друг друга из списков и в случае проблем с сетью просто дождутся восстановления подключения к сети.

Автоматическое создание аккаунтов

Эту процедуру можно начать на ранних этапах тестирования. В блокчейне потребуется стартовый аккаунт, чтобы с него раздать балансы для тестов, выделить ресурсы или провести процедуры конфигурирования. Обычно для этих задач используются аккаунты самих валидаторов.

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

Запуск и эксплуатация тестовой сети

Наступает важнейший этап запуска тестовой сети. Проект доказывает, что код работоспособен, сеть может долгое время существовать без остановок, и кто угодно может ее использовать. Этим блокчейны сильно отличаются от централизованных систем — с этого момента скрыть ошибки и недочеты будет сложно.

Для проектов, которые пишут собственный блокчейн без использования существующих движков, запуск тестнета — событие более важное, чем запуск основной сети. Если до этого можно было легко «обнулить» блокчейн и начать с первого блока, то, когда в testnet уже работает часть сервисов, которые изучают тестировщики, аудиторы, внешние команды, это крайне нежелательно.

Для удобного запуска имеет смысл иметь одну или несколько boot-нод с публичными фиксированными адресами. Новые ноды не будут искать в сети ноды тестнета, а обратятся по фиксированным адресам, получат актуальный список пиров и смогут быстро синхронизироваться с сетью. Задача поддержания актуальных boot-нод лежит на команде проекта.

При работе testnet возможен сценарий replay — транзакции «перепроигрываются» всеми нодами, начиная с генезис-блока. Это необходимо, если произошли изменения в логике обработки транзакций и необходимо перестроить состояние всех нод с самого начала, не потеряв транзакции пользователей. В случае критических ошибок этот сценарий возможен и в основной сети, поэтому стоит отладить его в тестовой.

Иногда тестовая сеть может требовать даже большего внимания devops, чем основная. В мейннете проект может держать только одного-двух валидаторов и следить за вспомогательными сервисами. В testnet может потребоваться обновление большого количества нод. В этот момент вам пригодится вся ранее созданная автоматизация обновления ПО.

Запуск testnet также могут провести команды, планирующие строить решения под ваш блокчейн и быть валидаторами вашей сети. Это идеальный вариант, потому что переход от тестовой сети к mainnet будет наиболее простым, без неприятных сюрпризов. Удачи с запуском!