Взаимодействие Blockchain2Blochain

В чем проблема

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

Данное взаимодействие значительно влияет на скорость обработки транзакций.

Варианты решения

  1. Сделать прямое взаимодействие по сети.

    • Значительно снижает производительность.

  2. Запускать ядро и прочие процессы в одном адресном пространстве.

    • Крайне сложный запуск - дополнительно надо запускать tendermint для ядра и строго следить, чтобы ни где ничего не перепуталось.

    • Высокое потребление ресурсов.

  3. Дублировать данные ядра во вторичных сервисах.

    • Усложняется схема взаимодействия.

    • Непонятно API и протокол взаимодействия. Tendermint пердполагает что все запросы идут через query метод.

    • Сложность с чтением genesis-состояния (т.к. оно не в виде блока).

    • Возможно pull/push модели взаимодействия.

  4. Вынос проверки ЭЦП из пира на промежуточный слой.

    • Подходит только для полностью закрытой сети.

    • Очень хорошо масштабируется.

    • Возможно проведение "левых" транзакций, если вклиниться после промежуточного слоя.

      • Варианты защиты:

        • Авторизация на tendermint-порту через HTTPS-ключ.

        • Дополнительная ЭЦП, которую добавляет промежуточный слой и которая валидируется на пире.

    • Необходим полноценный парсинг обрабатываемых команд - для выявления подписантов и проверки существования всех упоминаемых аккаунтов.

В целом, варианты (1/2/3) могут быть объединены на уровне API и различаться в реализации. Вариант (4) может быть реализован подменой IEdsChecker и промежуточным сервисом.

Взаимодействуйте по сети

Tendermint в своей природе имеет однопоточное взаимодействие, что приводит к значительным просадкам производительности при сетевом взаимодействии.

В целом есть пути оптимизации взаимодействия, но они не смогут ускорить работу пира в десятки раз.

Сейчас используется именно такое взаимодействие.

Единое адресное пространство

graph LR

    FrontC[CoreFront] -- HTTP --> TMC
    TMC(CoreTendermint) -- TSP --> App[Peer]

    bot --> TMC
    bot --> TMP

    FrontP[CoinFront] -- HTTP --> TMP
    TMP(CoinTendermint) -- TSP --> App

    App --> App

Плюсы:

  • Крайне быстрое взаимодействие - в рамках одного процесса.

  • Возможен доступ к историческим данным ядра.

  • Нет необходимости в сложных схемах кеширования данных.

Минусы:

  • Значительно усложняется запуск пира.

  • Значительно вырастают требования по железу.

  • Необходимо будет отключить механизм авто-определения плагинов (потому как 2 пира в рамках одного процесса имеют разный набор плагинов).

Проблема 1: Необходимо 2 пира заставить работать синхронно

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

  • Отправка транзакции с информацией о текущем блоке на платежный пир.

    • Проверяем следующим образом:

      • Новый блок свежее предыдущих данных.

      • Блок есть в блокчейне ядра.

    • Если блока в ядре нет, то транзакцию считаем невалидной.

      • Надо изучить, как ведет себя tendermint, если он один раз блок посчитал невалидным - будет ли он этот же блок пытаться переимпортировать?

    • Учитывая, что в tendermint наблюдатели могут отстать от генераторов (даже отдельные генераторы могут отставать), то основной вопрос - с какой задержкой данные о блоке в ядре должны попадать в платежный блокчейн.

  • А что произойдет при реимпорте истории?

    • Транзакция о блоке в ядре может быть в 3х состояниях:

      • Такой блок уже у ядра локально есть.

        • Транзакция гарантирвоанно валидна.

      • Блока такой высоты нет локально.

        • Для обработки непродтвержденных считаем транзакцию невалидной.

        • При подтверждении блока ждем определенности.

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

          • Альтернативно можем "громко упасть". Но сомневаюсь, что это выход. Сеть может упасть.

      • Блок такой высоты есть, но он другой.

        • Транзакция гарантированно невалидна.

Дублирование данных по клячам и мультиподписи

Вынос проверки ЭЦП

Очень хороший вариант в плане горизонтального масштабирования. Но для правильной работы необходимо уметь "правильно" парсить команды целевого сервиса.

В перспективе есть планы перейти на этот сценарий.

Реализация

Для реализации предлагается сделать модуль в Core, который будет запускаться с пиром и имея прямой доступ к нужным данным, будет вылидировать ЭЦП транзакций, после чего будет переотправлять их на подтверждение в пиры tendermint payment-сети.

Плюсы:

  • Прямой доступ к данным аккаунтов, быстрая проверка ЭЦП.

Минусы:

  • Необходимо следить за текущим снепшотом и всегда смотреть на актуальные данные.

  • Усложнение работы пира ядра и пира платежного сервиса.

  • Необходимо транзакции платежного сервиса уметь парсить и в ядре.

Last updated