@@ -103,9 +103,8 @@ use logger::{log_error, log_info, FilesystemLogger, Logger};
103103
104104use lightning:: chain:: keysinterface:: EntropySource ;
105105use lightning:: chain:: { chainmonitor, BestBlock , Confirm , Watch } ;
106- use lightning:: ln:: channelmanager;
107106use lightning:: ln:: channelmanager:: {
108- ChainParameters , ChannelDetails , ChannelManagerReadArgs , PaymentId , Retry ,
107+ self , ChainParameters , ChannelDetails , ChannelManagerReadArgs , PaymentId , Retry ,
109108} ;
110109use lightning:: ln:: peer_handler:: { IgnoringMessageHandler , MessageHandler } ;
111110use lightning:: ln:: { PaymentHash , PaymentPreimage } ;
@@ -843,6 +842,73 @@ impl Node {
843842 self . channel_manager . list_channels ( )
844843 }
845844
845+ /// Connect to a node on the peer-to-peer network.
846+ ///
847+ /// If `permanently` is set to `true`, we'll remember the peer and reconnect to it on restart.
848+ pub fn connect (
849+ & self , node_id : & PublicKey , address : & SocketAddr , permanently : bool ,
850+ ) -> Result < ( ) , Error > {
851+ let runtime_lock = self . running . read ( ) . unwrap ( ) ;
852+ if runtime_lock. is_none ( ) {
853+ return Err ( Error :: NotRunning ) ;
854+ }
855+
856+ let runtime = runtime_lock. as_ref ( ) . unwrap ( ) ;
857+
858+ let peer_info = PeerInfo { pubkey : node_id. clone ( ) , address : address. clone ( ) } ;
859+
860+ let con_peer_pubkey = peer_info. pubkey . clone ( ) ;
861+ let con_peer_addr = peer_info. address . clone ( ) ;
862+ let con_success = Arc :: new ( AtomicBool :: new ( false ) ) ;
863+ let con_success_cloned = Arc :: clone ( & con_success) ;
864+ let con_logger = Arc :: clone ( & self . logger ) ;
865+ let con_pm = Arc :: clone ( & self . peer_manager ) ;
866+
867+ tokio:: task:: block_in_place ( move || {
868+ runtime. tokio_runtime . block_on ( async move {
869+ let res =
870+ connect_peer_if_necessary ( con_peer_pubkey, con_peer_addr, con_pm, con_logger)
871+ . await ;
872+ con_success_cloned. store ( res. is_ok ( ) , Ordering :: Release ) ;
873+ } )
874+ } ) ;
875+
876+ if !con_success. load ( Ordering :: Acquire ) {
877+ return Err ( Error :: ConnectionFailed ) ;
878+ }
879+
880+ if permanently {
881+ self . peer_store . add_peer ( peer_info. clone ( ) ) ?;
882+ }
883+
884+ log_info ! ( self . logger, "Connected to peer {}@{}. " , peer_info. pubkey, peer_info. address, ) ;
885+
886+ Ok ( ( ) )
887+ }
888+
889+ /// Disconnects the peer with the given node id.
890+ ///
891+ /// Will also remove the peer from the peer store, i.e., after this has been called we won't
892+ /// try to reconnect on restart.
893+ pub fn disconnect ( & self , counterparty_node_id : & PublicKey ) -> Result < ( ) , Error > {
894+ let runtime_lock = self . running . read ( ) . unwrap ( ) ;
895+ if runtime_lock. is_none ( ) {
896+ return Err ( Error :: NotRunning ) ;
897+ }
898+
899+ log_info ! ( self . logger, "Disconnecting peer {}.." , counterparty_node_id) ;
900+
901+ match self . peer_store . remove_peer ( & counterparty_node_id) {
902+ Ok ( ( ) ) => { }
903+ Err ( e) => {
904+ log_error ! ( self . logger, "Failed to remove peer {}: {}" , counterparty_node_id, e)
905+ }
906+ }
907+
908+ self . peer_manager . disconnect_by_node_id ( * counterparty_node_id) ;
909+ Ok ( ( ) )
910+ }
911+
846912 /// Connect to a node and open a new channel. Disconnects and re-connects are handled automatically
847913 ///
848914 /// Returns a temporary channel id
0 commit comments