Add payer note to BOLT12 invoice request (#930)

* Add payer note to BOLT12 invoice request

* Fix regtest

* Address review feedback
This commit is contained in:
Ross Savage
2025-05-23 14:21:26 +00:00
committed by GitHub
parent defa2e4890
commit e090c858bf
24 changed files with 1099 additions and 930 deletions

1047
cli/Cargo.lock generated

File diff suppressed because it is too large Load Diff

View File

@@ -425,6 +425,7 @@ pub(crate) async fn handle_command(
.prepare_send_payment(&PrepareSendRequest {
destination,
amount,
comment: None,
})
.await?;

818
lib/Cargo.lock generated

File diff suppressed because it is too large Load Diff

View File

@@ -260,6 +260,7 @@ typedef struct wire_cst_SendDestination_Bolt12 {
struct wire_cst_ln_offer *offer;
uint64_t receiver_amount_sat;
struct wire_cst_list_prim_u_8_strict *bip353_address;
struct wire_cst_list_prim_u_8_strict *payer_note;
} wire_cst_SendDestination_Bolt12;
typedef union SendDestinationKind {
@@ -433,6 +434,7 @@ typedef struct wire_cst_prepare_refund_request {
typedef struct wire_cst_prepare_send_request {
struct wire_cst_list_prim_u_8_strict *destination;
struct wire_cst_pay_amount *amount;
struct wire_cst_list_prim_u_8_strict *comment;
} wire_cst_prepare_send_request;
typedef struct wire_cst_prepare_receive_response {

View File

@@ -434,13 +434,14 @@ dictionary LnUrlPayRequest {
dictionary PrepareSendRequest {
string destination;
PayAmount? amount = null;
string? comment = null;
};
[Enum]
interface SendDestination {
LiquidAddress(LiquidAddressData address_data, string? bip353_address);
Bolt11(LNInvoice invoice, string? bip353_address);
Bolt12(LNOffer offer, u64 receiver_amount_sat, string? bip353_address);
Bolt12(LNOffer offer, u64 receiver_amount_sat, string? bip353_address, string? payer_note);
};
dictionary PrepareSendResponse {

View File

@@ -13,8 +13,8 @@ frb = ["dep:flutter_rust_bridge"]
# Uniffi features required to build using cargo-lipo
uniffi-25 = []
uniffi-28 = []
regtest = [] # Enable regtest tests
browser-tests = [] # Enable browser wasm-pack tests
regtest = [] # Enable regtest tests
browser-tests = [] # Enable browser wasm-pack tests
test-utils = ["sdk-common/test-utils"]
[lints]
@@ -34,7 +34,7 @@ lwk_common = "0.9.0"
lwk_signer = { version = "0.9.0", default-features = false }
mockall = "0.13.1"
tokio = { version = "1", default-features = false, features = ["rt", "macros"] }
tokio_with_wasm = { version = "0.8.2", features = [
tokio_with_wasm = { version = "=0.8.2", features = [
"macros",
"rt",
"sync",
@@ -64,7 +64,9 @@ tempfile = "3"
ecies = { version = "0.2.7", default-features = false, features = ["pure"] }
semver = "1.0.23"
lazy_static = "1.5.0"
esplora-client = { git = "https://github.com/hydra-yse/rust-esplora-client", branch = "scripthash-utxo", features = ["async-https-rustls"] }
esplora-client = { git = "https://github.com/hydra-yse/rust-esplora-client", branch = "scripthash-utxo", features = [
"async-https-rustls",
] }
# Non-Wasm dependencies
[target.'cfg(not(all(target_family = "wasm", target_os = "unknown")))'.dependencies]
@@ -77,8 +79,9 @@ maybe-sync = { version = "0.1.1", features = ["sync"] }
prost = "^0.11"
tonic = { version = "^0.8", features = ["tls", "tls-webpki-roots"] }
uuid = { version = "1.8.0", features = ["v4"] }
boltz-client = { git = "https://github.com/breez/boltz-rust", rev = "d44295fa20da9c665a1f5580d16e387ff7245339", features = [
boltz-client = { git = "https://github.com/SatoshiPortal/boltz-rust", rev = "f25a8c180c5f1017677bc8ea01ed934ca0f8d2e1", features = [
"electrum",
"ws",
] }
rusqlite = { git = "https://github.com/Spxg/rusqlite", rev = "e36644127f31fa6e7ea0999b59432deb4a07f220", features = [
"backup",
@@ -98,11 +101,13 @@ tonic = { version = "0.12", default-features = false, features = [
"codegen",
"prost",
] }
boltz-client = { git = "https://github.com/breez/boltz-rust", rev = "d44295fa20da9c665a1f5580d16e387ff7245339" }
boltz-client = { git = "https://github.com/SatoshiPortal/boltz-rust", rev = "f25a8c180c5f1017677bc8ea01ed934ca0f8d2e1", features = [
"ws",
] }
rusqlite = { git = "https://github.com/Spxg/rusqlite", rev = "e36644127f31fa6e7ea0999b59432deb4a07f220", features = [
"backup",
"bundled",
"serialize"
"serialize",
] }
[dev-dependencies]

View File

@@ -4403,9 +4403,11 @@ impl SseDecode for crate::model::PrepareSendRequest {
fn sse_decode(deserializer: &mut flutter_rust_bridge::for_generated::SseDeserializer) -> Self {
let mut var_destination = <String>::sse_decode(deserializer);
let mut var_amount = <Option<crate::model::PayAmount>>::sse_decode(deserializer);
let mut var_comment = <Option<String>>::sse_decode(deserializer);
return crate::model::PrepareSendRequest {
destination: var_destination,
amount: var_amount,
comment: var_comment,
};
}
}
@@ -4708,10 +4710,12 @@ impl SseDecode for crate::model::SendDestination {
let mut var_offer = <crate::bindings::LNOffer>::sse_decode(deserializer);
let mut var_receiverAmountSat = <u64>::sse_decode(deserializer);
let mut var_bip353Address = <Option<String>>::sse_decode(deserializer);
let mut var_payerNote = <Option<String>>::sse_decode(deserializer);
return crate::model::SendDestination::Bolt12 {
offer: var_offer,
receiver_amount_sat: var_receiverAmountSat,
bip353_address: var_bip353Address,
payer_note: var_payerNote,
};
}
_ => {
@@ -6907,6 +6911,7 @@ impl flutter_rust_bridge::IntoDart for crate::model::PrepareSendRequest {
[
self.destination.into_into_dart().into_dart(),
self.amount.into_into_dart().into_dart(),
self.comment.into_into_dart().into_dart(),
]
.into_dart()
}
@@ -7267,11 +7272,13 @@ impl flutter_rust_bridge::IntoDart for crate::model::SendDestination {
offer,
receiver_amount_sat,
bip353_address,
payer_note,
} => [
2.into_dart(),
offer.into_into_dart().into_dart(),
receiver_amount_sat.into_into_dart().into_dart(),
bip353_address.into_into_dart().into_dart(),
payer_note.into_into_dart().into_dart(),
]
.into_dart(),
_ => {
@@ -9159,6 +9166,7 @@ impl SseEncode for crate::model::PrepareSendRequest {
fn sse_encode(self, serializer: &mut flutter_rust_bridge::for_generated::SseSerializer) {
<String>::sse_encode(self.destination, serializer);
<Option<crate::model::PayAmount>>::sse_encode(self.amount, serializer);
<Option<String>>::sse_encode(self.comment, serializer);
}
}
@@ -9384,11 +9392,13 @@ impl SseEncode for crate::model::SendDestination {
offer,
receiver_amount_sat,
bip353_address,
payer_note,
} => {
<i32>::sse_encode(2, serializer);
<crate::bindings::LNOffer>::sse_encode(offer, serializer);
<u64>::sse_encode(receiver_amount_sat, serializer);
<Option<String>>::sse_encode(bip353_address, serializer);
<Option<String>>::sse_encode(payer_note, serializer);
}
_ => {
unimplemented!("");
@@ -11407,6 +11417,7 @@ mod io {
crate::model::PrepareSendRequest {
destination: self.destination.cst_decode(),
amount: self.amount.cst_decode(),
comment: self.comment.cst_decode(),
}
}
}
@@ -11649,6 +11660,7 @@ mod io {
offer: ans.offer.cst_decode(),
receiver_amount_sat: ans.receiver_amount_sat.cst_decode(),
bip353_address: ans.bip353_address.cst_decode(),
payer_note: ans.payer_note.cst_decode(),
}
}
_ => unreachable!(),
@@ -12808,6 +12820,7 @@ mod io {
Self {
destination: core::ptr::null_mut(),
amount: core::ptr::null_mut(),
comment: core::ptr::null_mut(),
}
}
}
@@ -15278,6 +15291,7 @@ mod io {
pub struct wire_cst_prepare_send_request {
destination: *mut wire_cst_list_prim_u_8_strict,
amount: *mut wire_cst_pay_amount,
comment: *mut wire_cst_list_prim_u_8_strict,
}
#[repr(C)]
#[derive(Clone, Copy)]
@@ -15499,6 +15513,7 @@ mod io {
offer: *mut wire_cst_ln_offer,
receiver_amount_sat: u64,
bip353_address: *mut wire_cst_list_prim_u_8_strict,
payer_note: *mut wire_cst_list_prim_u_8_strict,
}
#[repr(C)]
#[derive(Clone, Copy)]

View File

@@ -690,10 +690,11 @@ pub struct PrepareSendRequest {
/// The destination we intend to pay to.
/// Supports BIP21 URIs, BOLT11 invoices, BOLT12 offers and Liquid addresses
pub destination: String,
/// Should only be set when paying directly onchain or to a BIP21 URI
/// where no amount is specified, or when the caller wishes to drain
pub amount: Option<PayAmount>,
/// An optional comment when paying a BOLT12 offer
pub comment: Option<String>,
}
/// Specifies the supported destinations which can be payed by the SDK
@@ -714,6 +715,8 @@ pub enum SendDestination {
receiver_amount_sat: u64,
/// A BIP353 address, in case one was used to resolve this BOLT12
bip353_address: Option<String>,
/// An optional payer note
payer_note: Option<String>,
},
}

View File

@@ -1204,6 +1204,7 @@ impl LiquidSdk {
/// - [PayAmount::Drain] which uses all Bitcoin funds
/// - [PayAmount::Bitcoin] which sets the amount in satoshi that will be received
/// - [PayAmount::Asset] which sets the amount of an asset that will be received
/// * `comment` - The optional comment to be included in the payment
///
/// # Returns
/// Returns a [PrepareSendResponse] containing:
@@ -1505,6 +1506,7 @@ impl LiquidSdk {
offer,
receiver_amount_sat,
bip353_address,
payer_note: req.comment.clone(),
};
}
_ => {
@@ -1628,11 +1630,16 @@ impl LiquidSdk {
offer,
receiver_amount_sat,
bip353_address,
payer_note,
} => {
let fees_sat = fees_sat.ok_or(PaymentError::InsufficientFunds)?;
let bolt12_info = self
.swapper
.get_bolt12_info(&offer.offer, *receiver_amount_sat)
.get_bolt12_info(GetBolt12FetchRequest {
offer: offer.offer.clone(),
amount: *receiver_amount_sat,
note: payer_note.clone(),
})
.await?;
let mut response = self
.pay_bolt12_invoice(
@@ -4155,6 +4162,7 @@ impl LiquidSdk {
.prepare_send_payment(&PrepareSendRequest {
destination: data.pr.clone(),
amount: Some(req.amount.clone()),
comment: req.comment.clone(),
})
.await
.map_err(|e| LnUrlPayError::Generic { err: e.to_string() })?;

View File

@@ -10,9 +10,9 @@ use boltz_client::{
boltz::{
self, BoltzApiClientV2, ChainPair, Cooperative, CreateBolt12OfferRequest,
CreateChainRequest, CreateChainResponse, CreateReverseRequest, CreateReverseResponse,
CreateSubmarineRequest, CreateSubmarineResponse, GetBolt12FetchResponse,
GetBolt12ParamsResponse, GetNodesResponse, ReversePair, SubmarineClaimTxResponse,
SubmarinePair, UpdateBolt12OfferRequest, WsRequest,
CreateSubmarineRequest, CreateSubmarineResponse, GetBolt12FetchRequest,
GetBolt12FetchResponse, GetBolt12ParamsResponse, GetNodesResponse, ReversePair,
SubmarineClaimTxResponse, SubmarinePair, UpdateBolt12OfferRequest, WsRequest,
},
elements::secp256k1_zkp::{MusigPartialSignature, MusigPubNonce},
network::Chain,
@@ -513,14 +513,13 @@ impl<P: ProxyUrlFetcher> Swapper for BoltzSwapper<P> {
async fn get_bolt12_info(
&self,
offer: &str,
amount_sat: u64,
req: GetBolt12FetchRequest,
) -> Result<GetBolt12FetchResponse, PaymentError> {
let invoice_res = self
.get_boltz_client()
.await?
.inner
.get_bolt12_invoice(offer, amount_sat)
.get_bolt12_invoice(req)
.await?;
info!("Received BOLT12 invoice response: {invoice_res:?}");
Ok(invoice_res)

View File

@@ -3,8 +3,9 @@ use boltz_client::{
boltz::{
ChainPair, CreateBolt12OfferRequest, CreateChainRequest, CreateChainResponse,
CreateReverseRequest, CreateReverseResponse, CreateSubmarineRequest,
CreateSubmarineResponse, GetBolt12FetchResponse, GetBolt12ParamsResponse, GetNodesResponse,
ReversePair, SubmarineClaimTxResponse, SubmarinePair, UpdateBolt12OfferRequest,
CreateSubmarineResponse, GetBolt12FetchRequest, GetBolt12FetchResponse,
GetBolt12ParamsResponse, GetNodesResponse, ReversePair, SubmarineClaimTxResponse,
SubmarinePair, UpdateBolt12OfferRequest,
},
network::Chain,
Amount,
@@ -127,8 +128,7 @@ pub trait Swapper: MaybeSend + MaybeSync {
async fn get_bolt12_info(
&self,
offer: &str,
amount_sat: u64,
req: GetBolt12FetchRequest,
) -> Result<GetBolt12FetchResponse, PaymentError>;
async fn create_bolt12_offer(&self, req: CreateBolt12OfferRequest) -> Result<(), SdkError>;

View File

@@ -2,7 +2,7 @@ use anyhow::Result;
use boltz_client::{
boltz::{
ChainFees, ChainMinerFees, ChainPair, ChainSwapDetails, CreateBolt12OfferRequest,
CreateChainResponse, CreateReverseResponse, CreateSubmarineResponse,
CreateChainResponse, CreateReverseResponse, CreateSubmarineResponse, GetBolt12FetchRequest,
GetBolt12FetchResponse, GetBolt12ParamsResponse, GetNodesResponse, Leaf, Node, PairLimits,
PairMinerFees, ReverseFees, ReverseLimits, ReversePair, SubmarineClaimTxResponse,
SubmarineFees, SubmarinePair, SubmarinePairLimits, SwapTree, UpdateBolt12OfferRequest,
@@ -347,8 +347,7 @@ impl Swapper for MockSwapper {
async fn get_bolt12_info(
&self,
_offer: &str,
_amount_sat: u64,
_req: GetBolt12FetchRequest,
) -> Result<GetBolt12FetchResponse, PaymentError> {
unimplemented!()
}

View File

@@ -117,6 +117,7 @@ async fn bolt11(mut handle_alice: SdkNodeHandle, mut handle_bob: SdkNodeHandle)
.send_payment(&PrepareSendRequest {
destination: invoice,
amount: None,
comment: None,
})
.await
.unwrap();
@@ -182,6 +183,7 @@ async fn bolt11(mut handle_alice: SdkNodeHandle, mut handle_bob: SdkNodeHandle)
.send_payment(&PrepareSendRequest {
destination: invoice,
amount: None,
comment: None,
})
.await
.unwrap();

View File

@@ -104,6 +104,7 @@ async fn bolt12(mut handle_alice: SdkNodeHandle, mut handle_bob: SdkNodeHandle)
amount: Some(PayAmount::Bitcoin {
receiver_amount_sat,
}),
comment: None,
})
.await
.unwrap();

View File

@@ -95,6 +95,7 @@ async fn liquid(mut handle: SdkNodeHandle) {
amount: Some(PayAmount::Bitcoin {
receiver_amount_sat,
}),
comment: None,
})
.await
.unwrap();

View File

@@ -434,6 +434,7 @@ pub struct OnchainPaymentLimitsResponse {
pub struct PrepareSendRequest {
pub destination: String,
pub amount: Option<PayAmount>,
pub comment: Option<String>,
}
#[sdk_macros::extern_wasm_bindgen(breez_sdk_liquid::prelude::SendDestination)]
@@ -450,6 +451,7 @@ pub enum SendDestination {
offer: LNOffer,
receiver_amount_sat: u64,
bip353_address: Option<String>,
payer_note: Option<String>,
},
}

View File

@@ -3074,10 +3074,11 @@ class RustLibApiImpl extends RustLibApiImplPlatform implements RustLibApi {
PrepareSendRequest dco_decode_prepare_send_request(dynamic raw) {
// Codec=Dco (DartCObject based), see doc to use other codecs
final arr = raw as List<dynamic>;
if (arr.length != 2) throw Exception('unexpected arr length: expect 2 but see ${arr.length}');
if (arr.length != 3) throw Exception('unexpected arr length: expect 3 but see ${arr.length}');
return PrepareSendRequest(
destination: dco_decode_String(arr[0]),
amount: dco_decode_opt_box_autoadd_pay_amount(arr[1]),
comment: dco_decode_opt_String(arr[2]),
);
}
@@ -3282,6 +3283,7 @@ class RustLibApiImpl extends RustLibApiImplPlatform implements RustLibApi {
offer: dco_decode_box_autoadd_ln_offer(raw[1]),
receiverAmountSat: dco_decode_u_64(raw[2]),
bip353Address: dco_decode_opt_String(raw[3]),
payerNote: dco_decode_opt_String(raw[4]),
);
default:
throw Exception("unreachable");
@@ -5498,7 +5500,8 @@ class RustLibApiImpl extends RustLibApiImplPlatform implements RustLibApi {
// Codec=Sse (Serialization based), see doc to use other codecs
var var_destination = sse_decode_String(deserializer);
var var_amount = sse_decode_opt_box_autoadd_pay_amount(deserializer);
return PrepareSendRequest(destination: var_destination, amount: var_amount);
var var_comment = sse_decode_opt_String(deserializer);
return PrepareSendRequest(destination: var_destination, amount: var_amount, comment: var_comment);
}
@protected
@@ -5728,10 +5731,12 @@ class RustLibApiImpl extends RustLibApiImplPlatform implements RustLibApi {
var var_offer = sse_decode_box_autoadd_ln_offer(deserializer);
var var_receiverAmountSat = sse_decode_u_64(deserializer);
var var_bip353Address = sse_decode_opt_String(deserializer);
var var_payerNote = sse_decode_opt_String(deserializer);
return SendDestination_Bolt12(
offer: var_offer,
receiverAmountSat: var_receiverAmountSat,
bip353Address: var_bip353Address,
payerNote: var_payerNote,
);
default:
throw UnimplementedError('');
@@ -7749,6 +7754,7 @@ class RustLibApiImpl extends RustLibApiImplPlatform implements RustLibApi {
// Codec=Sse (Serialization based), see doc to use other codecs
sse_encode_String(self.destination, serializer);
sse_encode_opt_box_autoadd_pay_amount(self.amount, serializer);
sse_encode_opt_String(self.comment, serializer);
}
@protected
@@ -7921,11 +7927,13 @@ class RustLibApiImpl extends RustLibApiImplPlatform implements RustLibApi {
offer: final offer,
receiverAmountSat: final receiverAmountSat,
bip353Address: final bip353Address,
payerNote: final payerNote,
):
sse_encode_i_32(2, serializer);
sse_encode_box_autoadd_ln_offer(offer, serializer);
sse_encode_u_64(receiverAmountSat, serializer);
sse_encode_opt_String(bip353Address, serializer);
sse_encode_opt_String(payerNote, serializer);
}
}

View File

@@ -3728,6 +3728,7 @@ abstract class RustLibApiImplPlatform extends BaseApiImpl<RustLibWire> {
) {
wireObj.destination = cst_encode_String(apiObj.destination);
wireObj.amount = cst_encode_opt_box_autoadd_pay_amount(apiObj.amount);
wireObj.comment = cst_encode_opt_String(apiObj.comment);
}
@protected
@@ -3941,10 +3942,12 @@ abstract class RustLibApiImplPlatform extends BaseApiImpl<RustLibWire> {
var pre_offer = cst_encode_box_autoadd_ln_offer(apiObj.offer);
var pre_receiver_amount_sat = cst_encode_u_64(apiObj.receiverAmountSat);
var pre_bip353_address = cst_encode_opt_String(apiObj.bip353Address);
var pre_payer_note = cst_encode_opt_String(apiObj.payerNote);
wireObj.tag = 2;
wireObj.kind.Bolt12.offer = pre_offer;
wireObj.kind.Bolt12.receiver_amount_sat = pre_receiver_amount_sat;
wireObj.kind.Bolt12.bip353_address = pre_bip353_address;
wireObj.kind.Bolt12.payer_note = pre_payer_note;
return;
}
}
@@ -6663,6 +6666,8 @@ final class wire_cst_SendDestination_Bolt12 extends ffi.Struct {
external int receiver_amount_sat;
external ffi.Pointer<wire_cst_list_prim_u_8_strict> bip353_address;
external ffi.Pointer<wire_cst_list_prim_u_8_strict> payer_note;
}
final class SendDestinationKind extends ffi.Union {
@@ -6908,6 +6913,8 @@ final class wire_cst_prepare_send_request extends ffi.Struct {
external ffi.Pointer<wire_cst_list_prim_u_8_strict> destination;
external ffi.Pointer<wire_cst_pay_amount> amount;
external ffi.Pointer<wire_cst_list_prim_u_8_strict> comment;
}
final class wire_cst_prepare_receive_response extends ffi.Struct {

View File

@@ -1419,10 +1419,13 @@ class PrepareSendRequest {
/// where no amount is specified, or when the caller wishes to drain
final PayAmount? amount;
const PrepareSendRequest({required this.destination, this.amount});
/// An optional comment when paying a BOLT12 offer
final String? comment;
const PrepareSendRequest({required this.destination, this.amount, this.comment});
@override
int get hashCode => destination.hashCode ^ amount.hashCode;
int get hashCode => destination.hashCode ^ amount.hashCode ^ comment.hashCode;
@override
bool operator ==(Object other) =>
@@ -1430,7 +1433,8 @@ class PrepareSendRequest {
other is PrepareSendRequest &&
runtimeType == other.runtimeType &&
destination == other.destination &&
amount == other.amount;
amount == other.amount &&
comment == other.comment;
}
/// Returned when calling [crate::sdk::LiquidSdk::prepare_send_payment].
@@ -1694,6 +1698,9 @@ sealed class SendDestination with _$SendDestination {
/// A BIP353 address, in case one was used to resolve this BOLT12
String? bip353Address,
/// An optional payer note
String? payerNote,
}) = SendDestination_Bolt12;
}

View File

@@ -2332,13 +2332,15 @@ as String?,
class SendDestination_Bolt12 extends SendDestination {
const SendDestination_Bolt12({required this.offer, required this.receiverAmountSat, this.bip353Address}): super._();
const SendDestination_Bolt12({required this.offer, required this.receiverAmountSat, this.bip353Address, this.payerNote}): super._();
final LNOffer offer;
final BigInt receiverAmountSat;
/// A BIP353 address, in case one was used to resolve this BOLT12
@override final String? bip353Address;
/// An optional payer note
final String? payerNote;
/// Create a copy of SendDestination
/// with the given fields replaced by the non-null parameter values.
@@ -2350,16 +2352,16 @@ $SendDestination_Bolt12CopyWith<SendDestination_Bolt12> get copyWith => _$SendDe
@override
bool operator ==(Object other) {
return identical(this, other) || (other.runtimeType == runtimeType&&other is SendDestination_Bolt12&&(identical(other.offer, offer) || other.offer == offer)&&(identical(other.receiverAmountSat, receiverAmountSat) || other.receiverAmountSat == receiverAmountSat)&&(identical(other.bip353Address, bip353Address) || other.bip353Address == bip353Address));
return identical(this, other) || (other.runtimeType == runtimeType&&other is SendDestination_Bolt12&&(identical(other.offer, offer) || other.offer == offer)&&(identical(other.receiverAmountSat, receiverAmountSat) || other.receiverAmountSat == receiverAmountSat)&&(identical(other.bip353Address, bip353Address) || other.bip353Address == bip353Address)&&(identical(other.payerNote, payerNote) || other.payerNote == payerNote));
}
@override
int get hashCode => Object.hash(runtimeType,offer,receiverAmountSat,bip353Address);
int get hashCode => Object.hash(runtimeType,offer,receiverAmountSat,bip353Address,payerNote);
@override
String toString() {
return 'SendDestination.bolt12(offer: $offer, receiverAmountSat: $receiverAmountSat, bip353Address: $bip353Address)';
return 'SendDestination.bolt12(offer: $offer, receiverAmountSat: $receiverAmountSat, bip353Address: $bip353Address, payerNote: $payerNote)';
}
@@ -2370,7 +2372,7 @@ abstract mixin class $SendDestination_Bolt12CopyWith<$Res> implements $SendDesti
factory $SendDestination_Bolt12CopyWith(SendDestination_Bolt12 value, $Res Function(SendDestination_Bolt12) _then) = _$SendDestination_Bolt12CopyWithImpl;
@override @useResult
$Res call({
LNOffer offer, BigInt receiverAmountSat, String? bip353Address
LNOffer offer, BigInt receiverAmountSat, String? bip353Address, String? payerNote
});
@@ -2387,11 +2389,12 @@ class _$SendDestination_Bolt12CopyWithImpl<$Res>
/// Create a copy of SendDestination
/// with the given fields replaced by the non-null parameter values.
@override @pragma('vm:prefer-inline') $Res call({Object? offer = null,Object? receiverAmountSat = null,Object? bip353Address = freezed,}) {
@override @pragma('vm:prefer-inline') $Res call({Object? offer = null,Object? receiverAmountSat = null,Object? bip353Address = freezed,Object? payerNote = freezed,}) {
return _then(SendDestination_Bolt12(
offer: null == offer ? _self.offer : offer // ignore: cast_nullable_to_non_nullable
as LNOffer,receiverAmountSat: null == receiverAmountSat ? _self.receiverAmountSat : receiverAmountSat // ignore: cast_nullable_to_non_nullable
as BigInt,bip353Address: freezed == bip353Address ? _self.bip353Address : bip353Address // ignore: cast_nullable_to_non_nullable
as String?,payerNote: freezed == payerNote ? _self.payerNote : payerNote // ignore: cast_nullable_to_non_nullable
as String?,
));
}

View File

@@ -4509,6 +4509,8 @@ final class wire_cst_SendDestination_Bolt12 extends ffi.Struct {
external int receiver_amount_sat;
external ffi.Pointer<wire_cst_list_prim_u_8_strict> bip353_address;
external ffi.Pointer<wire_cst_list_prim_u_8_strict> payer_note;
}
final class SendDestinationKind extends ffi.Union {
@@ -4754,6 +4756,8 @@ final class wire_cst_prepare_send_request extends ffi.Struct {
external ffi.Pointer<wire_cst_list_prim_u_8_strict> destination;
external ffi.Pointer<wire_cst_pay_amount> amount;
external ffi.Pointer<wire_cst_list_prim_u_8_strict> comment;
}
final class wire_cst_prepare_receive_response extends ffi.Struct {

View File

@@ -2326,13 +2326,15 @@ fun asPrepareSendRequest(prepareSendRequest: ReadableMap): PrepareSendRequest? {
}
val destination = prepareSendRequest.getString("destination")!!
val amount = if (hasNonNullKey(prepareSendRequest, "amount")) prepareSendRequest.getMap("amount")?.let { asPayAmount(it) } else null
return PrepareSendRequest(destination, amount)
val comment = if (hasNonNullKey(prepareSendRequest, "comment")) prepareSendRequest.getString("comment") else null
return PrepareSendRequest(destination, amount, comment)
}
fun readableMapOf(prepareSendRequest: PrepareSendRequest): ReadableMap =
readableMapOf(
"destination" to prepareSendRequest.destination,
"amount" to prepareSendRequest.amount?.let { readableMapOf(it) },
"comment" to prepareSendRequest.comment,
)
fun asPrepareSendRequestList(arr: ReadableArray): List<PrepareSendRequest> {
@@ -3926,7 +3928,8 @@ fun asSendDestination(sendDestination: ReadableMap): SendDestination? {
val offer = sendDestination.getMap("offer")?.let { asLnOffer(it) }!!
val receiverAmountSat = sendDestination.getDouble("receiverAmountSat").toULong()
val bip353Address = if (hasNonNullKey(sendDestination, "bip353Address")) sendDestination.getString("bip353Address") else null
return SendDestination.Bolt12(offer, receiverAmountSat, bip353Address)
val payerNote = if (hasNonNullKey(sendDestination, "payerNote")) sendDestination.getString("payerNote") else null
return SendDestination.Bolt12(offer, receiverAmountSat, bip353Address, payerNote)
}
return null
}
@@ -3949,6 +3952,7 @@ fun readableMapOf(sendDestination: SendDestination): ReadableMap? {
pushToMap(map, "offer", readableMapOf(sendDestination.offer))
pushToMap(map, "receiverAmountSat", sendDestination.receiverAmountSat)
pushToMap(map, "bip353Address", sendDestination.bip353Address)
pushToMap(map, "payerNote", sendDestination.payerNote)
}
}
return map

View File

@@ -2708,13 +2708,22 @@ enum BreezSDKLiquidMapper {
amount = try asPayAmount(payAmount: amountTmp)
}
return PrepareSendRequest(destination: destination, amount: amount)
var comment: String?
if hasNonNilKey(data: prepareSendRequest, key: "comment") {
guard let commentTmp = prepareSendRequest["comment"] as? String else {
throw SdkError.Generic(message: errUnexpectedValue(fieldName: "comment"))
}
comment = commentTmp
}
return PrepareSendRequest(destination: destination, amount: amount, comment: comment)
}
static func dictionaryOf(prepareSendRequest: PrepareSendRequest) -> [String: Any?] {
return [
"destination": prepareSendRequest.destination,
"amount": prepareSendRequest.amount == nil ? nil : dictionaryOf(payAmount: prepareSendRequest.amount!),
"comment": prepareSendRequest.comment == nil ? nil : prepareSendRequest.comment,
]
}
@@ -4961,7 +4970,9 @@ enum BreezSDKLiquidMapper {
}
let _bip353Address = sendDestination["bip353Address"] as? String
return SendDestination.bolt12(offer: _offer, receiverAmountSat: _receiverAmountSat, bip353Address: _bip353Address)
let _payerNote = sendDestination["payerNote"] as? String
return SendDestination.bolt12(offer: _offer, receiverAmountSat: _receiverAmountSat, bip353Address: _bip353Address, payerNote: _payerNote)
}
throw SdkError.Generic(message: "Unexpected type \(type) for enum SendDestination")
@@ -4988,13 +4999,14 @@ enum BreezSDKLiquidMapper {
]
case let .bolt12(
offer, receiverAmountSat, bip353Address
offer, receiverAmountSat, bip353Address, payerNote
):
return [
"type": "bolt12",
"offer": dictionaryOf(lnOffer: offer),
"receiverAmountSat": receiverAmountSat,
"bip353Address": bip353Address == nil ? nil : bip353Address,
"payerNote": payerNote == nil ? nil : payerNote,
]
}
}

View File

@@ -400,6 +400,7 @@ export interface PrepareRefundResponse {
export interface PrepareSendRequest {
destination: string
amount?: PayAmount
comment?: string
}
export interface PrepareSendResponse {
@@ -846,6 +847,7 @@ export type SendDestination = {
offer: LnOffer
receiverAmountSat: number
bip353Address?: string
payerNote?: string
}
export enum SuccessActionVariant {