@@ -28,9 +28,7 @@ use crate::blinded_path::payment::{
28
28
BlindedPaymentPath , Bolt12OfferContext , Bolt12RefundContext , PaymentContext ,
29
29
} ;
30
30
use crate :: events:: PaymentFailureReason ;
31
- use crate :: ln:: channelmanager:: {
32
- Bolt12PaymentError , PaymentId , Verification , OFFERS_MESSAGE_REQUEST_LIMIT ,
33
- } ;
31
+ use crate :: ln:: channelmanager:: { Bolt12PaymentError , PaymentId , Verification } ;
34
32
use crate :: ln:: inbound_payment;
35
33
use crate :: ln:: outbound_payment:: { Retry , RetryableInvoiceRequest , StaleExpiration } ;
36
34
use crate :: offers:: invoice:: {
73
71
///
74
72
/// [`ChannelManager`]: crate::ln::channelmanager::ChannelManager
75
73
pub trait OffersMessageCommons {
76
- /// Get pending offers messages
77
- fn get_pending_offers_messages (
78
- & self ,
79
- ) -> MutexGuard < ' _ , Vec < ( OffersMessage , MessageSendInstructions ) > > ;
80
-
81
74
#[ cfg( feature = "dnssec" ) ]
82
75
/// Get pending DNS onion messages
83
76
fn get_pending_dns_onion_messages (
@@ -176,11 +169,6 @@ pub trait OffersMessageCommons {
176
169
/// [`MessageRouter::create_blinded_paths`]: crate::onion_message::messenger::MessageRouter::create_blinded_paths
177
170
fn create_blinded_paths ( & self , context : MessageContext ) -> Result < Vec < BlindedMessagePath > , ( ) > ;
178
171
179
- /// Enqueue invoice request
180
- fn enqueue_invoice_request (
181
- & self , invoice_request : InvoiceRequest , reply_paths : Vec < BlindedMessagePath > ,
182
- ) -> Result < ( ) , Bolt12SemanticError > ;
183
-
184
172
/// Get the current time determined by highest seen timestamp
185
173
fn get_current_blocktime ( & self ) -> Duration ;
186
174
@@ -575,6 +563,11 @@ where
575
563
576
564
message_router : MR ,
577
565
566
+ #[ cfg( not( any( test, feature = "_test_utils" ) ) ) ]
567
+ pending_offers_messages : Mutex < Vec < ( OffersMessage , MessageSendInstructions ) > > ,
568
+ #[ cfg( any( test, feature = "_test_utils" ) ) ]
569
+ pub ( crate ) pending_offers_messages : Mutex < Vec < ( OffersMessage , MessageSendInstructions ) > > ,
570
+
578
571
#[ cfg( feature = "_test_utils" ) ]
579
572
/// In testing, it is useful be able to forge a name -> offer mapping so that we can pay an
580
573
/// offer generated in the test.
@@ -607,9 +600,13 @@ where
607
600
inbound_payment_key : expanded_inbound_key,
608
601
our_network_pubkey,
609
602
secp_ctx,
603
+ entropy_source,
604
+
610
605
commons,
606
+
611
607
message_router,
612
- entropy_source,
608
+
609
+ pending_offers_messages : Mutex :: new ( Vec :: new ( ) ) ,
613
610
#[ cfg( feature = "_test_utils" ) ]
614
611
testing_dnssec_proof_offer_resolution_override : Mutex :: new ( new_hash_map ( ) ) ,
615
612
logger,
@@ -642,6 +639,13 @@ where
642
639
/// [`Refund`]: crate::offers::refund
643
640
pub const MAX_SHORT_LIVED_RELATIVE_EXPIRY : Duration = Duration :: from_secs ( 60 * 60 * 24 ) ;
644
641
642
+ /// Defines the maximum number of [`OffersMessage`] including different reply paths to be sent
643
+ /// along different paths.
644
+ /// Sending multiple requests increases the chances of successful delivery in case some
645
+ /// paths are unavailable. However, only one invoice for a given [`PaymentId`] will be paid,
646
+ /// even if multiple invoices are received.
647
+ pub const OFFERS_MESSAGE_REQUEST_LIMIT : usize = 10 ;
648
+
645
649
impl < ES : Deref , OMC : Deref , MR : Deref , L : Deref > OffersMessageFlow < ES , OMC , MR , L >
646
650
where
647
651
ES :: Target : EntropySource ,
@@ -700,6 +704,42 @@ where
700
704
)
701
705
. and_then ( |paths| ( !paths. is_empty ( ) ) . then ( || paths) . ok_or ( ( ) ) )
702
706
}
707
+
708
+ fn enqueue_invoice_request (
709
+ & self , invoice_request : InvoiceRequest , reply_paths : Vec < BlindedMessagePath > ,
710
+ ) -> Result < ( ) , Bolt12SemanticError > {
711
+ let mut pending_offers_messages = self . pending_offers_messages . lock ( ) . unwrap ( ) ;
712
+ if !invoice_request. paths ( ) . is_empty ( ) {
713
+ reply_paths
714
+ . iter ( )
715
+ . flat_map ( |reply_path| {
716
+ invoice_request. paths ( ) . iter ( ) . map ( move |path| ( path, reply_path) )
717
+ } )
718
+ . take ( OFFERS_MESSAGE_REQUEST_LIMIT )
719
+ . for_each ( |( path, reply_path) | {
720
+ let instructions = MessageSendInstructions :: WithSpecifiedReplyPath {
721
+ destination : Destination :: BlindedPath ( path. clone ( ) ) ,
722
+ reply_path : reply_path. clone ( ) ,
723
+ } ;
724
+ let message = OffersMessage :: InvoiceRequest ( invoice_request. clone ( ) ) ;
725
+ pending_offers_messages. push ( ( message, instructions) ) ;
726
+ } ) ;
727
+ } else if let Some ( node_id) = invoice_request. issuer_signing_pubkey ( ) {
728
+ for reply_path in reply_paths {
729
+ let instructions = MessageSendInstructions :: WithSpecifiedReplyPath {
730
+ destination : Destination :: Node ( node_id) ,
731
+ reply_path,
732
+ } ;
733
+ let message = OffersMessage :: InvoiceRequest ( invoice_request. clone ( ) ) ;
734
+ pending_offers_messages. push ( ( message, instructions) ) ;
735
+ }
736
+ } else {
737
+ debug_assert ! ( false ) ;
738
+ return Err ( Bolt12SemanticError :: MissingIssuerSigningPubkey ) ;
739
+ }
740
+
741
+ Ok ( ( ) )
742
+ }
703
743
}
704
744
705
745
impl < ES : Deref , OMC : Deref , MR : Deref , L : Deref > OffersMessageFlow < ES , OMC , MR , L >
@@ -756,7 +796,7 @@ where
756
796
757
797
create_pending_payment ( & invoice_request, nonce) ?;
758
798
759
- self . commons . enqueue_invoice_request ( invoice_request, reply_paths)
799
+ self . enqueue_invoice_request ( invoice_request, reply_paths)
760
800
}
761
801
}
762
802
@@ -1024,7 +1064,7 @@ where
1024
1064
} ) ;
1025
1065
match self . commons . create_blinded_paths ( context) {
1026
1066
Ok ( reply_paths) => {
1027
- match self . commons . enqueue_invoice_request ( invoice_request, reply_paths) {
1067
+ match self . enqueue_invoice_request ( invoice_request, reply_paths) {
1028
1068
Ok ( _) => { } ,
1029
1069
Err ( _) => {
1030
1070
log_warn ! (
@@ -1048,7 +1088,7 @@ where
1048
1088
}
1049
1089
1050
1090
fn release_pending_messages ( & self ) -> Vec < ( OffersMessage , MessageSendInstructions ) > {
1051
- core:: mem:: take ( & mut self . commons . get_pending_offers_messages ( ) )
1091
+ core:: mem:: take ( & mut self . pending_offers_messages . lock ( ) . unwrap ( ) )
1052
1092
}
1053
1093
}
1054
1094
@@ -1382,7 +1422,7 @@ where
1382
1422
. create_blinded_paths ( context)
1383
1423
. map_err ( |_| Bolt12SemanticError :: MissingPaths ) ?;
1384
1424
1385
- let mut pending_offers_messages = self . commons . get_pending_offers_messages ( ) ;
1425
+ let mut pending_offers_messages = self . pending_offers_messages . lock ( ) . unwrap ( ) ;
1386
1426
if refund. paths ( ) . is_empty ( ) {
1387
1427
for reply_path in reply_paths {
1388
1428
let instructions = MessageSendInstructions :: WithSpecifiedReplyPath {
0 commit comments