Skip to content

Commit 15fb61e

Browse files
Remove APIs to create static invoice/async offers
Now that we've implemented the static invoice server protocol, these methods are not intended to ever be called by users. If someone did want to use these apis, they could use the equivalent methods on the OffersMessageFlow.
1 parent de2005a commit 15fb61e

File tree

2 files changed

+73
-92
lines changed

2 files changed

+73
-92
lines changed

lightning/src/ln/async_payments_tests.rs

Lines changed: 67 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ use crate::events::{
1717
use crate::ln::blinded_payment_tests::{fail_blinded_htlc_backwards, get_blinded_route_parameters};
1818
use crate::ln::channelmanager::{PaymentId, RecipientOnionFields};
1919
use crate::ln::functional_test_utils::*;
20+
use crate::ln::inbound_payment;
2021
use crate::ln::msgs;
2122
use crate::ln::msgs::{
2223
BaseMessageHandler, ChannelMessageHandler, MessageSendEvent, OnionMessageHandler,
@@ -36,8 +37,11 @@ use crate::offers::flow::{
3637
};
3738
use crate::offers::invoice_request::InvoiceRequest;
3839
use crate::offers::nonce::Nonce;
39-
use crate::offers::offer::Offer;
40-
use crate::offers::static_invoice::StaticInvoice;
40+
use crate::offers::offer::{Amount, Offer};
41+
use crate::offers::static_invoice::{
42+
StaticInvoice, StaticInvoiceBuilder,
43+
DEFAULT_RELATIVE_EXPIRY as STATIC_INVOICE_DEFAULT_RELATIVE_EXPIRY,
44+
};
4145
use crate::onion_message::async_payments::{AsyncPaymentsMessage, AsyncPaymentsMessageHandler};
4246
use crate::onion_message::messenger::{
4347
Destination, MessageRouter, MessageSendInstructions, PeeledOnion,
@@ -240,10 +244,50 @@ fn pass_async_payments_oms(
240244
(held_htlc_available_om_1_2, release_held_htlc)
241245
}
242246

247+
fn create_static_invoice_builder<'a>(
248+
recipient: &Node, offer: &'a Offer, offer_nonce: Nonce, relative_expiry: Option<Duration>,
249+
) -> StaticInvoiceBuilder<'a> {
250+
let entropy = recipient.keys_manager;
251+
let amount_msat = offer.amount().and_then(|amount| match amount {
252+
Amount::Bitcoin { amount_msats } => Some(amount_msats),
253+
Amount::Currency { .. } => None,
254+
});
255+
256+
let relative_expiry = relative_expiry.unwrap_or(STATIC_INVOICE_DEFAULT_RELATIVE_EXPIRY);
257+
let relative_expiry_secs: u32 = relative_expiry.as_secs().try_into().unwrap_or(u32::MAX);
258+
259+
let created_at = recipient.node.duration_since_epoch();
260+
let payment_secret = inbound_payment::create_for_spontaneous_payment(
261+
&recipient.keys_manager.get_inbound_payment_key(),
262+
amount_msat,
263+
relative_expiry_secs,
264+
created_at.as_secs(),
265+
None,
266+
)
267+
.unwrap();
268+
269+
recipient
270+
.node
271+
.flow
272+
.create_static_invoice_builder(
273+
&recipient.router,
274+
entropy,
275+
offer,
276+
offer_nonce,
277+
payment_secret,
278+
relative_expiry_secs,
279+
recipient.node.list_usable_channels(),
280+
recipient.node.test_get_peers_for_blinded_path(),
281+
)
282+
.unwrap()
283+
}
284+
243285
fn create_static_invoice<T: secp256k1::Signing + secp256k1::Verification>(
244286
always_online_counterparty: &Node, recipient: &Node, relative_expiry: Option<Duration>,
245287
secp_ctx: &Secp256k1<T>,
246288
) -> (Offer, StaticInvoice) {
289+
let entropy_source = recipient.keys_manager;
290+
247291
let blinded_paths_to_always_online_node = always_online_counterparty
248292
.message_router
249293
.create_blinded_paths(
@@ -256,15 +300,14 @@ fn create_static_invoice<T: secp256k1::Signing + secp256k1::Verification>(
256300
.unwrap();
257301
let (offer_builder, offer_nonce) = recipient
258302
.node
259-
.create_async_receive_offer_builder(blinded_paths_to_always_online_node)
303+
.flow
304+
.create_async_receive_offer_builder(entropy_source, blinded_paths_to_always_online_node)
260305
.unwrap();
261306
let offer = offer_builder.build().unwrap();
262-
let static_invoice = recipient
263-
.node
264-
.create_static_invoice_builder(&offer, offer_nonce, relative_expiry)
265-
.unwrap()
266-
.build_and_sign(&secp_ctx)
267-
.unwrap();
307+
let static_invoice =
308+
create_static_invoice_builder(recipient, &offer, offer_nonce, relative_expiry)
309+
.build_and_sign(&secp_ctx)
310+
.unwrap();
268311
(offer, static_invoice)
269312
}
270313

@@ -377,6 +420,7 @@ fn static_invoice_unknown_required_features() {
377420
let node_cfgs = create_node_cfgs(3, &chanmon_cfgs);
378421
let node_chanmgrs = create_node_chanmgrs(3, &node_cfgs, &[None, None, None]);
379422
let nodes = create_network(3, &node_cfgs, &node_chanmgrs);
423+
let entropy_source = nodes[2].keys_manager;
380424
create_announced_chan_between_nodes_with_value(&nodes, 0, 1, 1_000_000, 0);
381425
create_unannounced_chan_between_nodes_with_value(&nodes, 1, 2, 1_000_000, 0);
382426

@@ -393,16 +437,15 @@ fn static_invoice_unknown_required_features() {
393437
.unwrap();
394438
let (offer_builder, nonce) = nodes[2]
395439
.node
396-
.create_async_receive_offer_builder(blinded_paths_to_always_online_node)
440+
.flow
441+
.create_async_receive_offer_builder(entropy_source, blinded_paths_to_always_online_node)
397442
.unwrap();
398443
let offer = offer_builder.build().unwrap();
399-
let static_invoice_unknown_req_features = nodes[2]
400-
.node
401-
.create_static_invoice_builder(&offer, nonce, None)
402-
.unwrap()
403-
.features_unchecked(Bolt12InvoiceFeatures::unknown())
404-
.build_and_sign(&secp_ctx)
405-
.unwrap();
444+
let static_invoice_unknown_req_features =
445+
create_static_invoice_builder(&nodes[2], &offer, nonce, None)
446+
.features_unchecked(Bolt12InvoiceFeatures::unknown())
447+
.build_and_sign(&secp_ctx)
448+
.unwrap();
406449

407450
// Initiate payment to the offer corresponding to the manually-constructed invoice that has
408451
// unknown required features.
@@ -1073,6 +1116,7 @@ fn invalid_async_receive_with_retry<F1, F2>(
10731116
create_node_chanmgrs(3, &node_cfgs, &[None, Some(allow_priv_chan_fwds_cfg), None]);
10741117

10751118
let nodes = create_network(3, &node_cfgs, &node_chanmgrs);
1119+
let entropy_source = nodes[2].keys_manager;
10761120
create_announced_chan_between_nodes_with_value(&nodes, 0, 1, 1_000_000, 0);
10771121
create_unannounced_chan_between_nodes_with_value(&nodes, 1, 2, 1_000_000, 0);
10781122

@@ -1102,7 +1146,8 @@ fn invalid_async_receive_with_retry<F1, F2>(
11021146
.unwrap();
11031147
let (offer_builder, offer_nonce) = nodes[2]
11041148
.node
1105-
.create_async_receive_offer_builder(blinded_paths_to_always_online_node)
1149+
.flow
1150+
.create_async_receive_offer_builder(entropy_source, blinded_paths_to_always_online_node)
11061151
.unwrap();
11071152
let offer = offer_builder.build().unwrap();
11081153
let amt_msat = 5000;
@@ -1112,12 +1157,10 @@ fn invalid_async_receive_with_retry<F1, F2>(
11121157
// use the same nodes to avoid complicating the test with a bunch of extra nodes.
11131158
let mut static_invoice_paths = Vec::new();
11141159
for _ in 0..3 {
1115-
let static_inv_for_path = nodes[2]
1116-
.node
1117-
.create_static_invoice_builder(&offer, offer_nonce, None)
1118-
.unwrap()
1119-
.build_and_sign(&secp_ctx)
1120-
.unwrap();
1160+
let static_inv_for_path =
1161+
create_static_invoice_builder(&nodes[2], &offer, offer_nonce, None)
1162+
.build_and_sign(&secp_ctx)
1163+
.unwrap();
11211164
static_invoice_paths.push(static_inv_for_path.payment_paths()[0].clone());
11221165
}
11231166
nodes[2].router.expect_blinded_payment_paths(static_invoice_paths);

lightning/src/ln/channelmanager.rs

Lines changed: 6 additions & 68 deletions
Original file line numberDiff line numberDiff line change
@@ -138,12 +138,7 @@ use crate::util::wakers::{Future, Notifier};
138138
use crate::blinded_path::payment::BlindedPaymentPath;
139139
#[cfg(async_payments)]
140140
use {
141-
crate::blinded_path::message::BlindedMessagePath,
142-
crate::offers::offer::Amount,
143-
crate::offers::static_invoice::{
144-
StaticInvoice, StaticInvoiceBuilder,
145-
DEFAULT_RELATIVE_EXPIRY as STATIC_INVOICE_DEFAULT_RELATIVE_EXPIRY,
146-
},
141+
crate::blinded_path::message::BlindedMessagePath, crate::offers::static_invoice::StaticInvoice,
147142
};
148143

149144
#[cfg(feature = "dnssec")]
@@ -11900,68 +11895,6 @@ where
1190011895
Ok(offer)
1190111896
}
1190211897

11903-
/// Create an offer for receiving async payments as an often-offline recipient.
11904-
///
11905-
/// Instead of using this method, it is preferable to call
11906-
/// [`Self::set_paths_to_static_invoice_server`] and retrieve the automatically built offer via
11907-
/// [`Self::get_async_receive_offer`].
11908-
///
11909-
/// If you want to build the [`StaticInvoice`] manually using this method instead, you MUST:
11910-
/// 1. Provide at least 1 [`BlindedMessagePath`] terminating at an always-online node that will
11911-
/// serve the [`StaticInvoice`] created from this offer on our behalf.
11912-
/// 2. Use [`Self::create_static_invoice_builder`] to create a [`StaticInvoice`] from this
11913-
/// [`Offer`] plus the returned [`Nonce`], and provide the static invoice to the
11914-
/// aforementioned always-online node.
11915-
#[cfg(async_payments)]
11916-
pub fn create_async_receive_offer_builder(
11917-
&self, message_paths_to_always_online_node: Vec<BlindedMessagePath>,
11918-
) -> Result<(OfferBuilder<DerivedMetadata, secp256k1::All>, Nonce), Bolt12SemanticError> {
11919-
let entropy = &*self.entropy_source;
11920-
self.flow.create_async_receive_offer_builder(entropy, message_paths_to_always_online_node)
11921-
}
11922-
11923-
/// Creates a [`StaticInvoiceBuilder`] from the corresponding [`Offer`] and [`Nonce`] that were
11924-
/// created via [`Self::create_async_receive_offer_builder`]. If `relative_expiry` is unset, the
11925-
/// invoice's expiry will default to [`STATIC_INVOICE_DEFAULT_RELATIVE_EXPIRY`].
11926-
///
11927-
/// Instead of using this method to manually build the invoice, it is preferable to set
11928-
/// [`Self::set_paths_to_static_invoice_server`] and retrieve the automatically built offer via
11929-
/// [`Self::get_async_receive_offer`].
11930-
#[cfg(async_payments)]
11931-
pub fn create_static_invoice_builder<'a>(
11932-
&self, offer: &'a Offer, offer_nonce: Nonce, relative_expiry: Option<Duration>,
11933-
) -> Result<StaticInvoiceBuilder<'a>, Bolt12SemanticError> {
11934-
let entropy = &*self.entropy_source;
11935-
let amount_msat = offer.amount().and_then(|amount| match amount {
11936-
Amount::Bitcoin { amount_msats } => Some(amount_msats),
11937-
Amount::Currency { .. } => None,
11938-
});
11939-
11940-
let relative_expiry = relative_expiry.unwrap_or(STATIC_INVOICE_DEFAULT_RELATIVE_EXPIRY);
11941-
let relative_expiry_secs: u32 = relative_expiry.as_secs().try_into().unwrap_or(u32::MAX);
11942-
11943-
let created_at = self.duration_since_epoch();
11944-
let payment_secret = inbound_payment::create_for_spontaneous_payment(
11945-
&self.inbound_payment_key,
11946-
amount_msat,
11947-
relative_expiry_secs,
11948-
created_at.as_secs(),
11949-
None,
11950-
)
11951-
.map_err(|()| Bolt12SemanticError::InvalidAmount)?;
11952-
11953-
self.flow.create_static_invoice_builder(
11954-
&self.router,
11955-
entropy,
11956-
offer,
11957-
offer_nonce,
11958-
payment_secret,
11959-
relative_expiry_secs,
11960-
self.list_usable_channels(),
11961-
self.get_peers_for_blinded_path(),
11962-
)
11963-
}
11964-
1196511898
/// Sets the [`BlindedMessagePath`]s that we will use as an async recipient to interactively build
1196611899
/// [`Offer`]s with a static invoice server, so the server can serve [`StaticInvoice`]s to payers
1196711900
/// on our behalf when we're offline.
@@ -12413,6 +12346,11 @@ where
1241312346
.collect::<Vec<_>>()
1241412347
}
1241512348

12349+
#[cfg(all(test, async_payments))]
12350+
pub(super) fn test_get_peers_for_blinded_path(&self) -> Vec<MessageForwardNode> {
12351+
self.get_peers_for_blinded_path()
12352+
}
12353+
1241612354
#[cfg(all(test, async_payments))]
1241712355
/// Creates multi-hop blinded payment paths for the given `amount_msats` by delegating to
1241812356
/// [`Router::create_blinded_payment_paths`].

0 commit comments

Comments
 (0)