Глоссарий / Lightning и layer 2
Оффер BOLT12
Другие названия: offer.
- Что такое оффер BOLT12?
- Оффер BOLT12 представляет собой многоразовый платежный код Lightning, начинающийся с lno1, который любое число плательщиков может превратить в собственный новый счет, запросив его у стороны, выпустившей оффер, по самой сети Lightning.
Оффер (offer) представляет собой запрос на оплату, который сохраняет силу после оплаты, поэтому один напечатанный код обслуживает каждого клиента. Офферы не несут подписи и контрольной суммы, а их поля занимают типы TLV с 2 по 22, намеренно достаточно короткие для камеры недорогого смартфона. Если вы получаете биткоин, в этом состоит разница между кодом, который вы печатаете один раз, и счетом, который он создает и который истекает через 7200 секунд.
Как это работает
Оффер BOLT12 представляет собой поток записей «тип-длина-значение», записанных с человекочитаемым префиксом lno, разделителем 1 и затем символами в стиле bech32, которые передают эти записи по порядку.
Контрольной суммы из шести символов в конце нет. Спецификация отказывается от нее на том основании, что QR-коды несут собственные контрольные суммы, а поврежденный оффер дает неразбираемую строку, а не потерянный платеж. Длинные офферы можно разбивать знаком плюс, за которым необязательно следуют пробельные символы, чтобы они сохранялись при вставке в текстовое поле с ограничением числа символов, и читающая сторона должна удалить плюс и пробельные символы перед декодированием. Записывающая сторона должна использовать либо только строчные, либо только заглавные буквы, и для QR-кодов ей следует выбирать заглавные.
Сами поля пронумерованы. offer_chains имеет номер 2, offer_metadata 4, offer_currency 6, offer_amount 8, offer_description 10, offer_features 12, offer_absolute_expiry 14, offer_paths 16, offer_issuer 18, offer_quantity_max 20 и offer_issuer_id 22. Записывающая сторона должна оставаться в пределах типов с 1 по 79, а второй диапазон с 1000000000 по 1999999999 отведен под эксперименты. Ничто в этом списке не является подписью, и это сделано намеренно: подпись удлинила бы строку без всякой пользы, поскольку каждое поле, не являющееся подписью, копируется в следующий за ним запрос, так что измененный оффер просто не порождает счета.
Оплата затем требует еще двух сообщений. Ваш кошелек отправляет invoice_request с префиксом lnr в составе лукового сообщения (onion message), копируя каждое поле оффера, включая те, которых он не понимает, и подписывает результат подписью BIP340 над корнем Меркла. Эмитент отвечает подписанным счетом. Конструкция Меркла сопоставляет лист каждого поля с листом nonce, и именно это позволяет плательщику впоследствии раскрыть одно поле спорного счета, не раскрывая соседние, чего не может подпись BOLT11 над всей строкой.
Два из этих трех сообщений работают в обратном направлении для возвратов и банкоматов. Продавец публикует invoice_request с указанием суммы, которую хочет отправить, вы отвечаете счетом, а продавец подтверждает invoice_node_id перед оплатой.
Почему это важно при покупке биткоина
Оффер меняет то, как вы публикуете способ получить оплату, и совершенно ничего не меняет в том, во что вам обходится получение оплаты.
Возьмите обзор Phoenix на этом сайте. ACINQ публикует таблицу комиссий, а не оставляет их выяснение на вас: отправка через Lightning стоит 0,4 % плюс 4 сатоши, получение бесплатно, когда входящая ликвидность у вас уже есть, а получение, когда кошельку приходится выходить ончейн, чтобы освободить место, стоит 1 % плюс комиссии за майнинг, при этом новый канал стоит 1000 сатоши. Выдача оффера вместо счета не затрагивает ни одну из этих цифр. Она убирает шаг, на котором вы создаете новый код для каждого плательщика, а не шаг, на котором кто-то платит за ликвидность.
Выигрыш в приватности реален, но невелик. Адрес Lightning направляет каждый запрос счета через веб-сервер на чьем-то домене, и этот оператор видит суммы и время. Оффер направляет запрос через Lightning как луковое сообщение, а offer_paths позволяет узлу, все каналы которого приватны, оставаться доступным, вообще не публикуя идентификатор узла. Чего это вам не дает, так это приватности от вашего собственного провайдера: в нашем обзоре Phoenix прямо приводятся слова из FAQ ACINQ о том, что он знает конечный пункт назначения и сумму платежей.
Практическое предупреждение касается вставки. Форма вывода на бирже запрашивает счет Lightning, а строка lno1 таковым не является. Strike, одна из 63 записей о биржах на этом сайте, является Lightning-нативным сервисом и не добавляет собственной комиссии при переводах более чем в 100 стран, и это как раз тот тип операции, где два формата путаются. Ни в одном из 41 обзора кошельков, ни в одной из 63 записей о биржах на этом сайте сейчас не описывается поддержка офферов в качестве функции, поэтому считайте это тем, что нужно подтвердить в примечаниях к выпуску вашего собственного кошелька, а не тем, что можно предполагать.
Оффер лотка с шляпами и счет, в который она превращается
Лоток, продающий шляпы по 25 $, записывает оффер с offer_currency, установленным в USD, и offer_amount, установленным в 2500.
Таково правило спецификации для валюты, отличной от биткоина: трехбуквенный код ISO 4217 и сумма в единице валюты, скорректированная показателем степени ISO 4217, что для долларов означает центы. Само по себе указание offer_amount делает offer_description обязательным, потому что плательщик, с которого взимают плату за что-то конкретное, должен знать, за что. Если осталось три шляпы, offer_quantity_max равен 3, а если у лотка нет фиксированного предела, он равен 0. Значение 1 прямо разрешено, как бы странно оно ни выглядело, чтобы системе учета запасов никогда не требовался особый случай для последнего товара. offer_issuer мог бы выглядеть как hats@example.com Hat Stall, поскольку спецификация требует сначала домен, а после пробела любой пояснительный текст.
Ваш кошелек читает это, называет вам цену 25 $ и отправляет invoice_request с invreq_quantity, равным 2 для двух шляп, invreq_payer_id и, необязательно, invreq_payer_note. В ответ приходит счет с хешем платежа, меткой времени создания, по крайней мере одним ослепленным маршрутом и расценкой комиссии по каждому маршруту, охватывающей базовую комиссию, пропорциональную комиссию, CLTV-дельту и наименьший и наибольший HTLC, который он способен передать. Здесь вас защищают два правила. Ваш кошелек должен отклонить счет, если какое-либо поле в диапазонах с 0 по 159 не совпадает с отправленным, и он должен предупредить вас, если сумма в миллисатоши существенно отличается от оценки в долларах, которую дал оффер. Если эмитент не установил invoice_relative_expiry, счет должен быть отклонен через 7200 секунд после его создания.
Оффер BOLT12 vs счет BOLT11
Оффер BOLT12 представляет собой запрос на создание запроса на оплату; счет BOLT11 и есть запрос на оплату.
Текст BOLT12 открывается восемью претензиями к своему предшественнику, и те, что ощущает плательщик, таковы. Счет BOLT11 подписывается целиком, поэтому доказать одно поле означает раскрыть все. Его суммы, читаемые человеком, по оценке спецификации, оказались проблемными: множитель p часто обрабатывался неправильно, а пикобиткоин считать труднее, чем сатоши. Его payment_secret предотвращал зондирование лишь пока счет оставался приватным между плательщиком и получателем, а опубликованный счет таковым не является. И, по собственным словам спецификации, счета должны выдаваться для каждого пользователя отдельно и активно опасны, если для одного и того же пользователя предпринимаются две попытки оплаты. Оффер отвечает на все четыре тем, что вообще не является счетом.
Оффер BOLT12 vs адрес Lightning
Оффер BOLT12 представляет собой самодостаточную строку; адрес Lightning является именем, которое для вас разрешает чей-то сервер.
Оба многоразовые, поэтому их и путают. Адрес зависит от домена, сертификата и оператора, который поддерживает работу сервиса, и он перестает работать в тот день, когда отказывает любое из трех. Оффер зависит от того, что оба узла говорят на луковых сообщениях, и ни от чего больше, что представляет собой меньшую поверхность отказов, хотя нужно подтвердить, что ваш кошелек ее поддерживает, а не предполагать это. Адрес выигрывает в том, что его можно произнести вслух. Длинная строка lno1 является QR-кодом, а не тем, что вы начитываете в микрофон.