@@ -56,10 +56,10 @@ use crate::ln::msgs::{ChannelMessageHandler, DecodeError, LightningError};
56
56
use crate::ln::outbound_payment;
57
57
use crate::ln::outbound_payment::{OutboundPayments, PaymentAttempts, PendingOutboundPayment, SendAlongPathArgs};
58
58
use crate::ln::wire::Encode;
59
- use crate::offers::offer::{DerivedMetadata, OfferBuilder};
59
+ use crate::offers::offer::{DerivedMetadata, Offer, OfferBuilder};
60
60
use crate::offers::parse::Bolt12SemanticError;
61
61
use crate::offers::refund::RefundBuilder;
62
- use crate::onion_message::{OffersMessage, PendingOnionMessage};
62
+ use crate::onion_message::{Destination, OffersMessage, PendingOnionMessage};
63
63
use crate::sign::{EntropySource, KeysManager, NodeSigner, Recipient, SignerProvider, WriteableEcdsaChannelSigner};
64
64
use crate::util::config::{UserConfig, ChannelConfig, ChannelConfigUpdate};
65
65
use crate::util::wakers::{Future, Notifier};
@@ -7137,6 +7137,71 @@ where
7137
7137
Ok(builder)
7138
7138
}
7139
7139
7140
+ /// Creates an [`InvoiceRequest`] for an [`Offer`] from the given parameters and enqueues it to
7141
+ /// be sent via an onion message.
7142
+ ///
7143
+ /// Uses [`InvoiceRequestBuilder`] such that the [`InvoiceRequest`] it builds is recognized by
7144
+ /// the [`ChannelManager`] when handling [`Bolt12Invoice`] messages for the request.
7145
+ ///
7146
+ /// The provided `payment_id` is used to ensure that only one invoice is paid for the request.
7147
+ ///
7148
+ /// [`InvoiceRequest`]: crate::offers::invoice_request::InvoiceRequest
7149
+ /// [`InvoiceRequestBuilder`]: crate::offers::invoice_request::InvoiceRequestBuilder
7150
+ /// [`Bolt12Invoice`]: crate::offers::invoice::Bolt12Invoice
7151
+ pub fn request_invoice(
7152
+ &self, offer: &Offer, quantity: Option<u64>, amount_msats: Option<u64>,
7153
+ payer_note: Option<String>, payment_id: PaymentId, retry_strategy: Retry,
7154
+ max_total_routing_fee_msat: Option<u64>
7155
+ ) -> Result<(), Bolt12SemanticError> {
7156
+ let expanded_key = &self.inbound_payment_key;
7157
+ let entropy = &*self.entropy_source;
7158
+ let secp_ctx = &self.secp_ctx;
7159
+
7160
+ let builder = offer.request_invoice_deriving_payer_id(
7161
+ expanded_key, entropy, secp_ctx, payment_id
7162
+ )?;
7163
+ let builder = match quantity {
7164
+ None => builder,
7165
+ Some(quantity) => builder.quantity(quantity)?,
7166
+ };
7167
+ let builder = match amount_msats {
7168
+ None => builder,
7169
+ Some(amount_msats) => builder.amount_msats(amount_msats)?,
7170
+ };
7171
+ let builder = match payer_note {
7172
+ None => builder,
7173
+ Some(payer_note) => builder.payer_note(payer_note),
7174
+ };
7175
+
7176
+ let invoice_request = builder.build_and_sign()?;
7177
+ let reply_path = self.create_one_hop_blinded_path();
7178
+
7179
+ self.pending_outbound_payments
7180
+ .add_new_awaiting_invoice(payment_id, retry_strategy, max_total_routing_fee_msat)
7181
+ .map_err(|_| Bolt12SemanticError::DuplicatePaymentId)?;
7182
+
7183
+ let mut pending_offers_messages = self.pending_offers_messages.lock().unwrap();
7184
+ if offer.paths().is_empty() {
7185
+ let message = PendingOnionMessage {
7186
+ contents: OffersMessage::InvoiceRequest(invoice_request),
7187
+ destination: Destination::Node(offer.signing_pubkey()),
7188
+ reply_path: Some(reply_path),
7189
+ };
7190
+ pending_offers_messages.push(message);
7191
+ } else {
7192
+ for path in offer.paths() {
7193
+ let message = PendingOnionMessage {
7194
+ contents: OffersMessage::InvoiceRequest(invoice_request.clone()),
7195
+ destination: Destination::BlindedPath(path.clone()),
7196
+ reply_path: Some(reply_path.clone()),
7197
+ };
7198
+ pending_offers_messages.push(message);
7199
+ }
7200
+ }
7201
+
7202
+ Ok(())
7203
+ }
7204
+
7140
7205
/// Gets a payment secret and payment hash for use in an invoice given to a third party wishing
7141
7206
/// to pay us.
7142
7207
///
0 commit comments