@@ -89,14 +89,16 @@ mod logger;
8989mod message_handler;
9090mod payment_store;
9191mod peer_store;
92+ mod pj_new_crate;
9293mod sweep;
9394mod tx_broadcaster;
9495mod types;
9596#[ cfg( feature = "uniffi" ) ]
9697mod uniffi_types;
9798mod wallet;
9899
99- pub use bip39;
100+ use crate :: pj_new_crate:: ScheduledChannel ;
101+ use crate :: pjoin:: LDKPayjoin ;
100102pub use bitcoin;
101103pub use lightning;
102104pub use lightning_invoice;
@@ -108,6 +110,8 @@ use error::Error;
108110
109111pub use event:: Event ;
110112pub use types:: { BestBlock , ChannelConfig } ;
113+ use payjoin:: Uri ;
114+ mod pjoin;
111115
112116pub use io:: utils:: generate_entropy_mnemonic;
113117
@@ -157,16 +161,17 @@ use lightning_transaction_sync::EsploraSyncClient;
157161use lightning:: routing:: router:: { PaymentParameters , RouteParameters } ;
158162use lightning_invoice:: { payment, Bolt11Invoice , Currency } ;
159163
160- use bitcoin:: hashes:: sha256:: Hash as Sha256 ;
161164use bitcoin:: hashes:: Hash ;
162165use bitcoin:: secp256k1:: PublicKey ;
166+ use bitcoin:: { hashes:: sha256:: Hash as Sha256 , Amount } ;
163167
164168use bitcoin:: { Address , Txid } ;
165169
166170use rand:: Rng ;
167171
168172use std:: default:: Default ;
169- use std:: net:: ToSocketAddrs ;
173+ use std:: net:: { SocketAddr , ToSocketAddrs } ;
174+ use std:: str:: FromStr ;
170175use std:: sync:: atomic:: { AtomicBool , Ordering } ;
171176use std:: sync:: { Arc , Mutex , RwLock } ;
172177use std:: time:: { Duration , Instant , SystemTime , UNIX_EPOCH } ;
@@ -189,6 +194,7 @@ pub struct Node<K: KVStore + Sync + Send + 'static> {
189194 channel_manager : Arc < ChannelManager < K > > ,
190195 chain_monitor : Arc < ChainMonitor < K > > ,
191196 output_sweeper : Arc < Sweeper < K > > ,
197+ payjoin : Arc < LDKPayjoin < K > > ,
192198 peer_manager : Arc < PeerManager < K > > ,
193199 keys_manager : Arc < KeysManager > ,
194200 network_graph : Arc < NetworkGraph > ,
@@ -500,7 +506,30 @@ impl<K: KVStore + Sync + Send + 'static> Node<K> {
500506 } ) ;
501507 }
502508
503- // Regularly reconnect to persisted peers.
509+ let payjoin_handler = Arc :: clone ( & self . payjoin ) ;
510+ let mut stop_payjoin_server = self . stop_sender . subscribe ( ) ;
511+ let pj_port = self . config . payjoin_server_port ;
512+ runtime. spawn ( async move {
513+ let addr = SocketAddr :: from ( ( [ 127 , 0 , 0 , 1 ] , pj_port) ) ;
514+ let listener = tokio:: net:: TcpListener :: bind ( addr) . await . unwrap ( ) ;
515+ loop {
516+ let ( stream, _) = match listener. accept ( ) . await {
517+ Ok ( res) => res,
518+ Err ( e) => {
519+ println ! ( "Failed to accept incoming payjoin connection: {}" , e) ;
520+ continue ;
521+ } ,
522+ } ;
523+ tokio:: select! {
524+ _ = stop_payjoin_server. changed( ) => {
525+ return ;
526+ }
527+ _ = payjoin_handler. serve( stream) => { }
528+ }
529+ }
530+ } ) ;
531+
532+ // Regularly reconnect to channel peers.
504533 let connect_pm = Arc :: clone ( & self . peer_manager ) ;
505534 let connect_logger = Arc :: clone ( & self . logger ) ;
506535 let connect_peer_store = Arc :: clone ( & self . peer_store ) ;
@@ -707,6 +736,33 @@ impl<K: KVStore + Sync + Send + 'static> Node<K> {
707736 Ok ( ( ) )
708737 }
709738
739+ /// Request a new channel to be opened with a remote peer.
740+ pub async fn schedule_payjoin_channel (
741+ & self , channel_amount_sats : u64 , push_msat : Option < u64 > , announce_channel : bool ,
742+ node_id : PublicKey ,
743+ ) -> Result < String , Error > {
744+ let channel =
745+ ScheduledChannel :: new ( channel_amount_sats, push_msat, announce_channel, node_id) ;
746+ self . payjoin . schedule ( channel) . await ;
747+ let bip21 = self . payjoin_bip21 ( channel_amount_sats) ;
748+ bip21
749+ }
750+
751+ /// Generate a BIP21 URI for a payjoin request.
752+ pub fn payjoin_bip21 ( & self , amount_sats : u64 ) -> Result < String , Error > {
753+ let address = self . wallet . get_new_address ( ) ?;
754+ let amount = Amount :: from_sat ( amount_sats) ;
755+ let pj = format ! ( "https://0.0.0.0:{}/payjoin" , self . config. payjoin_server_port) ;
756+ let pj_uri_string = format ! ( "{}?amount={}&pj={}" , address. to_qr_uri( ) , amount. to_btc( ) , pj) ;
757+ assert ! ( Uri :: from_str( & pj_uri_string) . is_ok( ) ) ;
758+ Ok ( pj_uri_string)
759+ }
760+
761+ /// List all scheduled payjoin channels.
762+ pub async fn list_scheduled_channels ( & self ) -> Result < Vec < ScheduledChannel > , Error > {
763+ Ok ( self . payjoin . list_scheduled_channels ( ) . await )
764+ }
765+
710766 /// Disconnects all peers, stops all running background tasks, and shuts down [`Node`].
711767 ///
712768 /// After this returns most API methods will return [`Error::NotRunning`].
0 commit comments