Skip to content

Commit d6e6ff7

Browse files
committed
Add SendingParameters to bolt11 send
Updated `Bolt11Payment` `send` method to accept `SendingParameters`, as a parameter. If the user provided sending params the default values are overridden.
1 parent bf4ddff commit d6e6ff7

File tree

8 files changed

+64
-15
lines changed

8 files changed

+64
-15
lines changed

bindings/kotlin/ldk-node-jvm/lib/src/test/kotlin/org/lightningdevkit/ldknode/LibraryTest.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -224,7 +224,7 @@ class LibraryTest {
224224

225225
val invoice = node2.bolt11Payment().receive(2500000u, "asdf", 9217u)
226226

227-
node1.bolt11Payment().send(invoice)
227+
node1.bolt11Payment().send(invoice, null)
228228

229229
val paymentSuccessfulEvent = node1.waitNextEvent()
230230
println("Got event: $paymentSuccessfulEvent")

bindings/ldk_node.udl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,7 @@ interface Node {
9494

9595
interface Bolt11Payment {
9696
[Throws=NodeError]
97-
PaymentId send([ByRef]Bolt11Invoice invoice);
97+
PaymentId send([ByRef]Bolt11Invoice invoice, SendingParameters? sending_parameters);
9898
[Throws=NodeError]
9999
PaymentId send_using_amount([ByRef]Bolt11Invoice invoice, u64 amount_msat);
100100
[Throws=NodeError]

src/lib.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@
5656
//! node.event_handled();
5757
//!
5858
//! let invoice = Bolt11Invoice::from_str("INVOICE_STR").unwrap();
59-
//! node.bolt11_payment().send(&invoice).unwrap();
59+
//! node.bolt11_payment().send(&invoice, None).unwrap();
6060
//!
6161
//! node.stop().unwrap();
6262
//! }

src/payment/bolt11.rs

Lines changed: 44 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ use crate::payment::store::{
1111
LSPFeeLimits, PaymentDetails, PaymentDetailsUpdate, PaymentDirection, PaymentKind,
1212
PaymentStatus, PaymentStore,
1313
};
14+
use crate::payment::SendingParameters;
1415
use crate::peer_store::{PeerInfo, PeerStore};
1516
use crate::types::{ChannelManager, KeysManager};
1617

@@ -69,13 +70,20 @@ impl Bolt11Payment {
6970
}
7071

7172
/// Send a payment given an invoice.
72-
pub fn send(&self, invoice: &Bolt11Invoice) -> Result<PaymentId, Error> {
73+
///
74+
/// If [`SendingParameters`] are provided they will override the node's default routing parameters
75+
/// on a per-field basis. Each field in `SendingParameters` that is set replaces the corresponding
76+
/// default value. Fields that are not set fall back to the node's configured defaults. If no
77+
/// `SendingParameters` are provided, the method fully relies on these defaults.
78+
pub fn send(
79+
&self, invoice: &Bolt11Invoice, sending_parameters: Option<SendingParameters>,
80+
) -> Result<PaymentId, Error> {
7381
let rt_lock = self.runtime.read().unwrap();
7482
if rt_lock.is_none() {
7583
return Err(Error::NotRunning);
7684
}
7785

78-
let (payment_hash, recipient_onion, route_params) = payment::payment_parameters_from_invoice(&invoice).map_err(|_| {
86+
let (payment_hash, recipient_onion, mut route_params) = payment::payment_parameters_from_invoice(&invoice).map_err(|_| {
7987
log_error!(self.logger, "Failed to send payment due to the given invoice being \"zero-amount\". Please use send_using_amount instead.");
8088
Error::InvalidInvoice
8189
})?;
@@ -90,6 +98,40 @@ impl Bolt11Payment {
9098
}
9199
}
92100

101+
if let Some(user_set_params) = sending_parameters {
102+
if let Some(mut default_params) =
103+
self.config.sending_parameters_config.as_ref().cloned()
104+
{
105+
default_params.max_total_routing_fee_msat = user_set_params
106+
.max_total_routing_fee_msat
107+
.or(default_params.max_total_routing_fee_msat);
108+
default_params.max_total_cltv_expiry_delta = user_set_params
109+
.max_total_cltv_expiry_delta
110+
.or(default_params.max_total_cltv_expiry_delta);
111+
default_params.max_path_count =
112+
user_set_params.max_path_count.or(default_params.max_path_count);
113+
default_params.max_channel_saturation_power_of_half = user_set_params
114+
.max_channel_saturation_power_of_half
115+
.or(default_params.max_channel_saturation_power_of_half);
116+
117+
route_params.max_total_routing_fee_msat = default_params.max_total_routing_fee_msat;
118+
route_params.payment_params.max_total_cltv_expiry_delta =
119+
default_params.max_total_cltv_expiry_delta.unwrap_or_default();
120+
route_params.payment_params.max_path_count =
121+
default_params.max_path_count.unwrap_or_default();
122+
route_params.payment_params.max_channel_saturation_power_of_half =
123+
default_params.max_channel_saturation_power_of_half.unwrap_or_default();
124+
}
125+
} else if let Some(default_params) = &self.config.sending_parameters_config {
126+
route_params.max_total_routing_fee_msat = default_params.max_total_routing_fee_msat;
127+
route_params.payment_params.max_total_cltv_expiry_delta =
128+
default_params.max_total_cltv_expiry_delta.unwrap_or_default();
129+
route_params.payment_params.max_path_count =
130+
default_params.max_path_count.unwrap_or_default();
131+
route_params.payment_params.max_channel_saturation_power_of_half =
132+
default_params.max_channel_saturation_power_of_half.unwrap_or_default();
133+
}
134+
93135
let payment_secret = Some(*invoice.payment_secret());
94136
let retry_strategy = Retry::Timeout(LDK_PAYMENT_RETRY_TIMEOUT);
95137

src/payment/unified_qr.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -143,7 +143,7 @@ impl UnifiedQrPayment {
143143
}
144144

145145
if let Some(invoice) = uri_network_checked.extras.bolt11_invoice {
146-
match self.bolt11_invoice.send(&invoice) {
146+
match self.bolt11_invoice.send(&invoice, None) {
147147
Ok(payment_id) => return Ok(QrPaymentResult::Bolt11 { payment_id }),
148148
Err(e) => log_error!(self.logger, "Failed to send BOLT11 invoice: {:?}. This is part of a unified QR code payment. Falling back to the on-chain transaction.", e),
149149
}

tests/common/mod.rs

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -493,8 +493,8 @@ pub(crate) fn do_channel_full_cycle<E: ElectrumApi>(
493493
let invoice = node_b.bolt11_payment().receive(invoice_amount_1_msat, &"asdf", 9217).unwrap();
494494

495495
println!("\nA send");
496-
let payment_id = node_a.bolt11_payment().send(&invoice).unwrap();
497-
assert_eq!(node_a.bolt11_payment().send(&invoice), Err(NodeError::DuplicatePayment));
496+
let payment_id = node_a.bolt11_payment().send(&invoice, None).unwrap();
497+
assert_eq!(node_a.bolt11_payment().send(&invoice, None), Err(NodeError::DuplicatePayment));
498498

499499
assert_eq!(node_a.list_payments().first().unwrap().id, payment_id);
500500

@@ -526,7 +526,7 @@ pub(crate) fn do_channel_full_cycle<E: ElectrumApi>(
526526
assert!(matches!(node_b.payment(&payment_id).unwrap().kind, PaymentKind::Bolt11 { .. }));
527527

528528
// Assert we fail duplicate outbound payments and check the status hasn't changed.
529-
assert_eq!(Err(NodeError::DuplicatePayment), node_a.bolt11_payment().send(&invoice));
529+
assert_eq!(Err(NodeError::DuplicatePayment), node_a.bolt11_payment().send(&invoice, None));
530530
assert_eq!(node_a.payment(&payment_id).unwrap().status, PaymentStatus::Succeeded);
531531
assert_eq!(node_a.payment(&payment_id).unwrap().direction, PaymentDirection::Outbound);
532532
assert_eq!(node_a.payment(&payment_id).unwrap().amount_msat, Some(invoice_amount_1_msat));
@@ -579,7 +579,7 @@ pub(crate) fn do_channel_full_cycle<E: ElectrumApi>(
579579
let determined_amount_msat = 2345_678;
580580
assert_eq!(
581581
Err(NodeError::InvalidInvoice),
582-
node_a.bolt11_payment().send(&variable_amount_invoice)
582+
node_a.bolt11_payment().send(&variable_amount_invoice, None)
583583
);
584584
println!("\nA send_using_amount");
585585
let payment_id = node_a
@@ -616,7 +616,7 @@ pub(crate) fn do_channel_full_cycle<E: ElectrumApi>(
616616
.bolt11_payment()
617617
.receive_for_hash(invoice_amount_3_msat, &"asdf", 9217, manual_payment_hash)
618618
.unwrap();
619-
let manual_payment_id = node_a.bolt11_payment().send(&manual_invoice).unwrap();
619+
let manual_payment_id = node_a.bolt11_payment().send(&manual_invoice, None).unwrap();
620620

621621
let claimable_amount_msat = expect_payment_claimable_event!(
622622
node_b,
@@ -654,7 +654,7 @@ pub(crate) fn do_channel_full_cycle<E: ElectrumApi>(
654654
.bolt11_payment()
655655
.receive_for_hash(invoice_amount_3_msat, &"asdf", 9217, manual_fail_payment_hash)
656656
.unwrap();
657-
let manual_fail_payment_id = node_a.bolt11_payment().send(&manual_fail_invoice).unwrap();
657+
let manual_fail_payment_id = node_a.bolt11_payment().send(&manual_fail_invoice, None).unwrap();
658658

659659
expect_payment_claimable_event!(
660660
node_b,

tests/integration_tests_cln.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -98,7 +98,7 @@ fn test_cln() {
9898
cln_client.invoice(Some(10_000_000), &rand_label, &rand_label, None, None, None).unwrap();
9999
let parsed_invoice = Bolt11Invoice::from_str(&cln_invoice.bolt11).unwrap();
100100

101-
node.bolt11_payment().send(&parsed_invoice).unwrap();
101+
node.bolt11_payment().send(&parsed_invoice, None).unwrap();
102102
common::expect_event!(node, PaymentSuccessful);
103103
let cln_listed_invoices =
104104
cln_client.listinvoices(Some(&rand_label), None, None, None).unwrap().invoices;

tests/integration_tests_rust.rs

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ use common::{
77
setup_node, setup_two_nodes, wait_for_tx, TestSyncStore,
88
};
99

10-
use ldk_node::payment::{PaymentKind, QrPaymentResult};
10+
use ldk_node::payment::{PaymentKind, QrPaymentResult, SendingParameters};
1111
use ldk_node::{Builder, Event, NodeError};
1212

1313
use lightning::ln::channelmanager::PaymentId;
@@ -156,8 +156,15 @@ fn multi_hop_sending() {
156156
// Sleep a bit for gossip to propagate.
157157
std::thread::sleep(std::time::Duration::from_secs(1));
158158

159+
let sending_params = SendingParameters {
160+
max_total_routing_fee_msat: Some(75_000),
161+
max_total_cltv_expiry_delta: Some(1000),
162+
max_path_count: Some(10),
163+
max_channel_saturation_power_of_half: Some(2),
164+
};
165+
159166
let invoice = nodes[4].bolt11_payment().receive(2_500_000, &"asdf", 9217).unwrap();
160-
nodes[0].bolt11_payment().send(&invoice).unwrap();
167+
nodes[0].bolt11_payment().send(&invoice, Some(sending_params)).unwrap();
161168

162169
let payment_id = expect_payment_received_event!(&nodes[4], 2_500_000);
163170
let fee_paid_msat = Some(2000);

0 commit comments

Comments
 (0)