# Спецификация каналов оплаты `L2` ## Оригина https://github.com/serokell/ton-paychan/blob/master/doc/Payment-channel.md https://github.com/zeropoolnetwork/zeropool-core/blob/master/smart-contracts/ZeroPool.full.sol https://habr.com/ru/company/distributedlab/blog/418853/ https://uniswap.org/docs/v2 ## Обзор Предположим, что две стороны, Алиса и Боб, хотели бы сделать серию платежей друг другу, и по соображениям эффективности они решили выполнять их через платежный канал, а не по цепочке. Они согласовывают параметры канала, такие как доли, которые они должны внести (которые будут определять, сколько каждый из них может друг другу в процессе), время ожидания бездействия и штраф за неправильное поведение. Затем контракт канала оплаты предварительно конфигурируется и развертывается в сети блокчейна (это может сделать либо Алиса, либо Боб, либо кто-то еще). Контракт начинается в состоянии «ожидания», что означает, что он ожидает первоначальных обязательств от обеих сторон. Алиса и Боб должны отправить в контракт суммы токенов, равные их долям, плюс дополнительные депозиты, которые будут заблокированы для использования в качестве штрафа в случае неправильного поведения. Как только обе стороны вносят свои доли, токены блокируются в договоре, **и канал оплаты считается открытым.** Теперь, если одна из сторон хочет отправить платеж другой, они готовят специальное `IOU`[^IOU] сообщение, которое содержит сумму транзакции и два значения, которые записывают, сколько каждая из них передала другой. Сообщение подписывается и передается через любую коммуникационную среду, которую Алиса и Боб предпочитают использовать. Включение общих сумм, которые они должны друг другу, в каждое сообщение необходимо, чтобы убедиться, что если в какой-то момент одна из сторон исчезнет, у другой стороны будет подписано сообщение с указанием последнего распределения средств, на которое они согласились. Эти микротранзакции могут быть отправлены в любое время и столько раз, сколько пожелают стороны, при условии, что типы данных, используемые для отслеживания их обязательств, не переполняются, и до тех пор, пока они остаются в пределах, которые они взяли на себя во время конфигурации контракта, то есть должно быть достаточно средств, хранящихся в договоре. Обратите внимание, что канал является двунаправленным, и получение платежа уменьшает задолженность получателя, поэтому, пока взаимные долги сбалансированы и остаются в допустимых пределах, канал может оставаться открытым в течение длительного периода времени. Сторонам рекомендуется подтверждать получение каждого микроплатежа (например, это может произойти естественным образом стороной, предоставляющей услуги, за которые они были оплачены); однако безопасность канала не зависит от этого. Также не требуется, чтобы сообщения `IOU` доставлялись в порядке или фактически доставлялись вообще. **???** Поскольку каждое сообщение `IOU` несет всю информацию о текущих долгах, необходимое и достаточное условие платежа в канале - получение последнее `IOU` до закрытия канала. Когда Алиса и Боб не ожидают дальнейших микротранзакций, они начинают закрывать канал. Рекомендуется, чтобы они обменялись двумя заключительными сообщениями `IOU`, посылая друг другу `0`, чтобы подтвердить, что они согласны в отношении окончательных сумм, причитающихся друг другу. Когда все будет готово, Алиса отправляет в контракт запрос на выплату и прикрепляет последнюю `IOU`, которую она получила от Боба. Затем у Боба есть фиксированное время, чтобы либо подтвердить, что он согласен с предложенным распределением, либо, если это не так, предложить другое распространение. В любом случае, поскольку предложения о распространении поддерживаются расписками, подписанными другой стороной, смарт-контракт канала платежей сможет принять решение о справедливом распределении, которое будет гарантировать, что обе стороны получат как минимум столько средств, сколько они ожидают получить , исходя из входящих платежей, которые они видели. ## Внецепной протокол ### Формат сообщения В следующем `IOU` типе данных указан проводной формат сообщения `IOU`: ```javascript= data Signed a = MkSigned { payload :: a // Произвольные данные , signature :: Signature // Подпись для полезной нагрузки } -- serialisation: -- / signature (= 512) / -- \ bits \ -- ref1 = payload // Данные полезной нагрузки data IouPayload = MkIouPayload { channel :: Address // Адрес контракта канала оплаты , amount :: UInt120 // Эта сумма микроплатежа , iou :: UInt248 // Общая сумма, переданная другой стороне , uome :: UInt248 // Общая сумма, полученная от другой стороны } -- serialisation: -- / channel (= 8 + 256) / amount (<= 124) / iou (<= 253) / uome (<= 253) / -- \ uint8 + uint256 \ varuint16 \ varuint32 \ varuint32 \ type Iou = Signed IouPayload ``` Адрес канала включен как форма защиты воспроизведения; это гарантирует, что каждый конкретный `IOU` может использоваться только в контексте одного канала. Никакой другой защиты от повторного воспроизведения не требуется, поскольку поля `iou` и `uome` не уменьшаются и, таким образом, естественно играют роль никогда не повторяющихся порядковых номеров. [^IOU]: I Own You - Я тебе должен, долговая расписка