@@ -22,7 +22,7 @@ use crate::ln::msgs;
22
22
use crate :: ln:: msgs:: ChannelMessageHandler ;
23
23
use crate :: ln:: outbound_payment:: Retry ;
24
24
use crate :: routing:: gossip:: RoutingFees ;
25
- use crate :: routing:: router:: { get_route, PaymentParameters , RouteHint , RouteHintHop , RouteParameters } ;
25
+ use crate :: routing:: router:: { get_route, PaymentParameters , Route , RouteHint , RouteHintHop , RouteHop , RouteParameters } ;
26
26
use crate :: util:: events:: { ClosureReason , Event , HTLCDestination , MessageSendEvent , MessageSendEventsProvider } ;
27
27
use crate :: util:: test_utils;
28
28
use crate :: util:: errors:: APIError ;
@@ -1755,3 +1755,201 @@ fn do_automatic_retries(test: AutoRetry) {
1755
1755
}
1756
1756
}
1757
1757
}
1758
+
1759
+ #[ test]
1760
+ fn auto_retry_partial_failure ( ) {
1761
+ // Test that we'll retry appropriately on send partial failure and retry partial failure.
1762
+ let chanmon_cfgs = create_chanmon_cfgs ( 2 ) ;
1763
+ let node_cfgs = create_node_cfgs ( 2 , & chanmon_cfgs) ;
1764
+ let node_chanmgrs = create_node_chanmgrs ( 2 , & node_cfgs, & [ None , None ] ) ;
1765
+ let mut nodes = create_network ( 2 , & node_cfgs, & node_chanmgrs) ;
1766
+
1767
+ let chan_1_id = create_announced_chan_between_nodes ( & nodes, 0 , 1 , channelmanager:: provided_init_features ( ) , channelmanager:: provided_init_features ( ) ) . 0 . contents . short_channel_id ;
1768
+ let chan_2_id = create_announced_chan_between_nodes ( & nodes, 0 , 1 , channelmanager:: provided_init_features ( ) , channelmanager:: provided_init_features ( ) ) . 0 . contents . short_channel_id ;
1769
+ let chan_3_id = create_announced_chan_between_nodes ( & nodes, 0 , 1 , channelmanager:: provided_init_features ( ) , channelmanager:: provided_init_features ( ) ) . 0 . contents . short_channel_id ;
1770
+
1771
+ // Marshall data to send the payment
1772
+ let amt_msat = 20_000 ;
1773
+ let ( _, payment_hash, payment_preimage, payment_secret) = get_route_and_payment_hash ! ( & nodes[ 0 ] , nodes[ 1 ] , amt_msat) ;
1774
+ #[ cfg( feature = "std" ) ]
1775
+ let payment_expiry_secs = SystemTime :: UNIX_EPOCH . elapsed ( ) . unwrap ( ) . as_secs ( ) + 60 * 60 ;
1776
+ #[ cfg( not( feature = "std" ) ) ]
1777
+ let payment_expiry_secs = 60 * 60 ;
1778
+ let mut invoice_features = InvoiceFeatures :: empty ( ) ;
1779
+ invoice_features. set_variable_length_onion_required ( ) ;
1780
+ invoice_features. set_payment_secret_required ( ) ;
1781
+ invoice_features. set_basic_mpp_optional ( ) ;
1782
+ let payment_params = PaymentParameters :: from_node_id ( nodes[ 1 ] . node . get_our_node_id ( ) )
1783
+ . with_expiry_time ( payment_expiry_secs as u64 )
1784
+ . with_features ( invoice_features) ;
1785
+ let route_params = RouteParameters {
1786
+ payment_params,
1787
+ final_value_msat : amt_msat,
1788
+ final_cltv_expiry_delta : TEST_FINAL_CLTV ,
1789
+ } ;
1790
+
1791
+ // Ensure the first monitor update (for the initial send path1 over chan_1) succeeds, but the
1792
+ // second (for the initial send path2 over chan_2) fails.
1793
+ chanmon_cfgs[ 0 ] . persister . set_next_update_ret ( ChannelMonitorUpdateStatus :: Completed ) ;
1794
+ chanmon_cfgs[ 0 ] . persister . set_next_update_ret ( ChannelMonitorUpdateStatus :: PermanentFailure ) ;
1795
+ // Ensure third monitor update (for the retry1's path1 over chan_1) succeeds, but the fourth (for
1796
+ // the retry1's path2 over chan_3) fails, and monitor updates succeed after that.
1797
+ chanmon_cfgs[ 0 ] . persister . set_next_update_ret ( ChannelMonitorUpdateStatus :: Completed ) ;
1798
+ chanmon_cfgs[ 0 ] . persister . set_next_update_ret ( ChannelMonitorUpdateStatus :: PermanentFailure ) ;
1799
+ chanmon_cfgs[ 0 ] . persister . set_next_update_ret ( ChannelMonitorUpdateStatus :: Completed ) ;
1800
+
1801
+ // Configure the initial send, retry1 and retry2's paths.
1802
+ let send_route = Route {
1803
+ paths : vec ! [
1804
+ vec![ RouteHop {
1805
+ pubkey: nodes[ 1 ] . node. get_our_node_id( ) ,
1806
+ node_features: channelmanager:: provided_node_features( ) ,
1807
+ short_channel_id: chan_1_id,
1808
+ channel_features: channelmanager:: provided_channel_features( ) ,
1809
+ fee_msat: amt_msat / 2 ,
1810
+ cltv_expiry_delta: 100 ,
1811
+ } ] ,
1812
+ vec![ RouteHop {
1813
+ pubkey: nodes[ 1 ] . node. get_our_node_id( ) ,
1814
+ node_features: channelmanager:: provided_node_features( ) ,
1815
+ short_channel_id: chan_2_id,
1816
+ channel_features: channelmanager:: provided_channel_features( ) ,
1817
+ fee_msat: amt_msat / 2 ,
1818
+ cltv_expiry_delta: 100 ,
1819
+ } ] ,
1820
+ ] ,
1821
+ payment_params : Some ( PaymentParameters :: from_node_id ( nodes[ 1 ] . node . get_our_node_id ( ) ) ) ,
1822
+ } ;
1823
+ let retry_1_route = Route {
1824
+ paths : vec ! [
1825
+ vec![ RouteHop {
1826
+ pubkey: nodes[ 1 ] . node. get_our_node_id( ) ,
1827
+ node_features: channelmanager:: provided_node_features( ) ,
1828
+ short_channel_id: chan_1_id,
1829
+ channel_features: channelmanager:: provided_channel_features( ) ,
1830
+ fee_msat: amt_msat / 4 ,
1831
+ cltv_expiry_delta: 100 ,
1832
+ } ] ,
1833
+ vec![ RouteHop {
1834
+ pubkey: nodes[ 1 ] . node. get_our_node_id( ) ,
1835
+ node_features: channelmanager:: provided_node_features( ) ,
1836
+ short_channel_id: chan_3_id,
1837
+ channel_features: channelmanager:: provided_channel_features( ) ,
1838
+ fee_msat: amt_msat / 4 ,
1839
+ cltv_expiry_delta: 100 ,
1840
+ } ] ,
1841
+ ] ,
1842
+ payment_params : Some ( PaymentParameters :: from_node_id ( nodes[ 1 ] . node . get_our_node_id ( ) ) ) ,
1843
+ } ;
1844
+ let retry_2_route = Route {
1845
+ paths : vec ! [
1846
+ vec![ RouteHop {
1847
+ pubkey: nodes[ 1 ] . node. get_our_node_id( ) ,
1848
+ node_features: channelmanager:: provided_node_features( ) ,
1849
+ short_channel_id: chan_1_id,
1850
+ channel_features: channelmanager:: provided_channel_features( ) ,
1851
+ fee_msat: amt_msat / 4 ,
1852
+ cltv_expiry_delta: 100 ,
1853
+ } ] ,
1854
+ ] ,
1855
+ payment_params : Some ( PaymentParameters :: from_node_id ( nodes[ 1 ] . node . get_our_node_id ( ) ) ) ,
1856
+ } ;
1857
+ nodes[ 0 ] . router . expect_find_route ( Ok ( send_route) ) ;
1858
+ nodes[ 0 ] . router . expect_find_route ( Ok ( retry_1_route) ) ;
1859
+ nodes[ 0 ] . router . expect_find_route ( Ok ( retry_2_route) ) ;
1860
+
1861
+ // Send a payment that will partially fail on send, then partially fail on retry, then succeed.
1862
+ nodes[ 0 ] . node . send_payment_with_retry ( payment_hash, & Some ( payment_secret) , PaymentId ( payment_hash. 0 ) , route_params, Retry :: Attempts ( 3 ) ) . unwrap ( ) ;
1863
+ let closed_chan_events = nodes[ 0 ] . node . get_and_clear_pending_events ( ) ;
1864
+ assert_eq ! ( closed_chan_events. len( ) , 2 ) ;
1865
+ match closed_chan_events[ 0 ] {
1866
+ Event :: ChannelClosed { .. } => { } ,
1867
+ _ => panic ! ( "Unexpected event" ) ,
1868
+ }
1869
+ match closed_chan_events[ 1 ] {
1870
+ Event :: ChannelClosed { .. } => { } ,
1871
+ _ => panic ! ( "Unexpected event" ) ,
1872
+ }
1873
+
1874
+ // Pass the first part of the payment along the path.
1875
+ check_added_monitors ! ( nodes[ 0 ] , 5 ) ; // three outbound channel updates succeeded, two permanently failed
1876
+ let mut msg_events = nodes[ 0 ] . node . get_and_clear_pending_msg_events ( ) ;
1877
+
1878
+ // First message is the first update_add, remaining messages are broadcasting channel updates and
1879
+ // errors for the permfailed channels
1880
+ assert_eq ! ( msg_events. len( ) , 5 ) ;
1881
+ let mut payment_event = SendEvent :: from_event ( msg_events. remove ( 0 ) ) ;
1882
+
1883
+ nodes[ 1 ] . node . handle_update_add_htlc ( & nodes[ 0 ] . node . get_our_node_id ( ) , & payment_event. msgs [ 0 ] ) ;
1884
+ nodes[ 1 ] . node . handle_commitment_signed ( & nodes[ 0 ] . node . get_our_node_id ( ) , & payment_event. commitment_msg ) ;
1885
+ check_added_monitors ! ( nodes[ 1 ] , 1 ) ;
1886
+ let ( bs_first_raa, bs_first_cs) = get_revoke_commit_msgs ! ( nodes[ 1 ] , nodes[ 0 ] . node. get_our_node_id( ) ) ;
1887
+
1888
+ nodes[ 0 ] . node . handle_revoke_and_ack ( & nodes[ 1 ] . node . get_our_node_id ( ) , & bs_first_raa) ;
1889
+ check_added_monitors ! ( nodes[ 0 ] , 1 ) ;
1890
+ let as_second_htlc_updates = SendEvent :: from_node ( & nodes[ 0 ] ) ;
1891
+
1892
+ nodes[ 0 ] . node . handle_commitment_signed ( & nodes[ 1 ] . node . get_our_node_id ( ) , & bs_first_cs) ;
1893
+ check_added_monitors ! ( nodes[ 0 ] , 1 ) ;
1894
+ let as_first_raa = get_event_msg ! ( nodes[ 0 ] , MessageSendEvent :: SendRevokeAndACK , nodes[ 1 ] . node. get_our_node_id( ) ) ;
1895
+
1896
+ nodes[ 1 ] . node . handle_revoke_and_ack ( & nodes[ 0 ] . node . get_our_node_id ( ) , & as_first_raa) ;
1897
+ check_added_monitors ! ( nodes[ 1 ] , 1 ) ;
1898
+
1899
+ nodes[ 1 ] . node . handle_update_add_htlc ( & nodes[ 0 ] . node . get_our_node_id ( ) , & as_second_htlc_updates. msgs [ 0 ] ) ;
1900
+ nodes[ 1 ] . node . handle_update_add_htlc ( & nodes[ 0 ] . node . get_our_node_id ( ) , & as_second_htlc_updates. msgs [ 1 ] ) ;
1901
+ nodes[ 1 ] . node . handle_commitment_signed ( & nodes[ 0 ] . node . get_our_node_id ( ) , & as_second_htlc_updates. commitment_msg ) ;
1902
+ check_added_monitors ! ( nodes[ 1 ] , 1 ) ;
1903
+ let ( bs_second_raa, bs_second_cs) = get_revoke_commit_msgs ! ( nodes[ 1 ] , nodes[ 0 ] . node. get_our_node_id( ) ) ;
1904
+
1905
+ nodes[ 0 ] . node . handle_revoke_and_ack ( & nodes[ 1 ] . node . get_our_node_id ( ) , & bs_second_raa) ;
1906
+ check_added_monitors ! ( nodes[ 0 ] , 1 ) ;
1907
+
1908
+ nodes[ 0 ] . node . handle_commitment_signed ( & nodes[ 1 ] . node . get_our_node_id ( ) , & bs_second_cs) ;
1909
+ check_added_monitors ! ( nodes[ 0 ] , 1 ) ;
1910
+ let as_second_raa = get_event_msg ! ( nodes[ 0 ] , MessageSendEvent :: SendRevokeAndACK , nodes[ 1 ] . node. get_our_node_id( ) ) ;
1911
+
1912
+ nodes[ 1 ] . node . handle_revoke_and_ack ( & nodes[ 0 ] . node . get_our_node_id ( ) , & as_second_raa) ;
1913
+ check_added_monitors ! ( nodes[ 1 ] , 1 ) ;
1914
+
1915
+ expect_pending_htlcs_forwardable_ignore ! ( nodes[ 1 ] ) ;
1916
+ nodes[ 1 ] . node . process_pending_htlc_forwards ( ) ;
1917
+ expect_payment_claimable ! ( nodes[ 1 ] , payment_hash, payment_secret, amt_msat) ;
1918
+ nodes[ 1 ] . node . claim_funds ( payment_preimage) ;
1919
+ expect_payment_claimed ! ( nodes[ 1 ] , payment_hash, amt_msat) ;
1920
+ let bs_claim_update = get_htlc_update_msgs ! ( nodes[ 1 ] , nodes[ 0 ] . node. get_our_node_id( ) ) ;
1921
+ assert_eq ! ( bs_claim_update. update_fulfill_htlcs. len( ) , 1 ) ;
1922
+
1923
+ nodes[ 0 ] . node . handle_update_fulfill_htlc ( & nodes[ 1 ] . node . get_our_node_id ( ) , & bs_claim_update. update_fulfill_htlcs [ 0 ] ) ;
1924
+ nodes[ 0 ] . node . handle_commitment_signed ( & nodes[ 1 ] . node . get_our_node_id ( ) , & bs_claim_update. commitment_signed ) ;
1925
+ check_added_monitors ! ( nodes[ 0 ] , 1 ) ;
1926
+ let ( as_third_raa, as_third_cs) = get_revoke_commit_msgs ! ( nodes[ 0 ] , nodes[ 1 ] . node. get_our_node_id( ) ) ;
1927
+
1928
+ nodes[ 1 ] . node . handle_revoke_and_ack ( & nodes[ 0 ] . node . get_our_node_id ( ) , & as_third_raa) ;
1929
+ check_added_monitors ! ( nodes[ 1 ] , 4 ) ;
1930
+ let bs_second_claim_update = get_htlc_update_msgs ! ( nodes[ 1 ] , nodes[ 0 ] . node. get_our_node_id( ) ) ;
1931
+
1932
+ nodes[ 1 ] . node . handle_commitment_signed ( & nodes[ 0 ] . node . get_our_node_id ( ) , & as_third_cs) ;
1933
+ check_added_monitors ! ( nodes[ 1 ] , 1 ) ;
1934
+ let bs_third_raa = get_event_msg ! ( nodes[ 1 ] , MessageSendEvent :: SendRevokeAndACK , nodes[ 0 ] . node. get_our_node_id( ) ) ;
1935
+
1936
+ nodes[ 0 ] . node . handle_revoke_and_ack ( & nodes[ 1 ] . node . get_our_node_id ( ) , & bs_third_raa) ;
1937
+ check_added_monitors ! ( nodes[ 0 ] , 1 ) ;
1938
+
1939
+ nodes[ 0 ] . node . handle_update_fulfill_htlc ( & nodes[ 1 ] . node . get_our_node_id ( ) , & bs_second_claim_update. update_fulfill_htlcs [ 0 ] ) ;
1940
+ nodes[ 0 ] . node . handle_update_fulfill_htlc ( & nodes[ 1 ] . node . get_our_node_id ( ) , & bs_second_claim_update. update_fulfill_htlcs [ 1 ] ) ;
1941
+ nodes[ 0 ] . node . handle_commitment_signed ( & nodes[ 1 ] . node . get_our_node_id ( ) , & bs_second_claim_update. commitment_signed ) ;
1942
+ check_added_monitors ! ( nodes[ 0 ] , 1 ) ;
1943
+ let ( as_fourth_raa, as_fourth_cs) = get_revoke_commit_msgs ! ( nodes[ 0 ] , nodes[ 1 ] . node. get_our_node_id( ) ) ;
1944
+
1945
+ nodes[ 1 ] . node . handle_revoke_and_ack ( & nodes[ 0 ] . node . get_our_node_id ( ) , & as_fourth_raa) ;
1946
+ check_added_monitors ! ( nodes[ 1 ] , 1 ) ;
1947
+
1948
+ nodes[ 1 ] . node . handle_commitment_signed ( & nodes[ 0 ] . node . get_our_node_id ( ) , & as_fourth_cs) ;
1949
+ check_added_monitors ! ( nodes[ 1 ] , 1 ) ;
1950
+ let bs_second_raa = get_event_msg ! ( nodes[ 1 ] , MessageSendEvent :: SendRevokeAndACK , nodes[ 0 ] . node. get_our_node_id( ) ) ;
1951
+
1952
+ nodes[ 0 ] . node . handle_revoke_and_ack ( & nodes[ 1 ] . node . get_our_node_id ( ) , & bs_second_raa) ;
1953
+ check_added_monitors ! ( nodes[ 0 ] , 1 ) ;
1954
+ expect_payment_sent ! ( nodes[ 0 ] , payment_preimage) ;
1955
+ }
0 commit comments