}
}
-#[cfg(test)]
#[macro_export]
-macro_rules! get_route_and_payment_hash {
- ($send_node: expr, $recv_node: expr, $recv_value: expr) => {{
- $crate::get_route_and_payment_hash!($send_node, $recv_node, vec![], $recv_value, TEST_FINAL_CLTV)
- }};
- ($send_node: expr, $recv_node: expr, $last_hops: expr, $recv_value: expr, $cltv: expr) => {{
+macro_rules! get_route {
+ ($send_node: expr, $payment_params: expr, $recv_value: expr, $cltv: expr) => {{
use $crate::chain::keysinterface::KeysInterface;
- let (payment_preimage, payment_hash, payment_secret) = $crate::get_payment_preimage_hash!($recv_node, Some($recv_value));
- let payment_params = $crate::routing::router::PaymentParameters::from_node_id($recv_node.node.get_our_node_id())
- .with_features($crate::ln::features::InvoiceFeatures::known())
- .with_route_hints($last_hops);
let scorer = $crate::util::test_utils::TestScorer::with_penalty(0);
let keys_manager = $crate::util::test_utils::TestKeysInterface::new(&[0u8; 32], bitcoin::network::constants::Network::Testnet);
let random_seed_bytes = keys_manager.get_secure_random_bytes();
- let route = $crate::routing::router::get_route(
- &$send_node.node.get_our_node_id(), &payment_params, &$send_node.network_graph.read_only(),
+ $crate::routing::router::get_route(
+ &$send_node.node.get_our_node_id(), &$payment_params, &$send_node.network_graph.read_only(),
Some(&$send_node.node.list_usable_channels().iter().collect::<Vec<_>>()),
$recv_value, $cltv, $send_node.logger, &scorer, &random_seed_bytes
- ).unwrap();
- (route, payment_hash, payment_preimage, payment_secret)
+ )
+ }}
+}
+
+#[cfg(test)]
+#[macro_export]
+macro_rules! get_route_and_payment_hash {
+ ($send_node: expr, $recv_node: expr, $recv_value: expr) => {{
+ let payment_params = $crate::routing::router::PaymentParameters::from_node_id($recv_node.node.get_our_node_id())
+ .with_features($crate::ln::features::InvoiceFeatures::known());
+ $crate::get_route_and_payment_hash!($send_node, $recv_node, payment_params, $recv_value, TEST_FINAL_CLTV)
+ }};
+ ($send_node: expr, $recv_node: expr, $payment_params: expr, $recv_value: expr, $cltv: expr) => {{
+ let (payment_preimage, payment_hash, payment_secret) = $crate::get_payment_preimage_hash!($recv_node, Some($recv_value));
+ let route = $crate::get_route!($send_node, $payment_params, $recv_value, $cltv);
+ (route.unwrap(), payment_hash, payment_preimage, payment_secret)
}}
}
}
macro_rules! expect_payment_forwarded {
- ($node: expr, $expected_fee: expr, $upstream_force_closed: expr) => {
+ ($node: expr, $source_node: expr, $expected_fee: expr, $upstream_force_closed: expr) => {
let events = $node.node.get_and_clear_pending_events();
assert_eq!(events.len(), 1);
match events[0] {
- Event::PaymentForwarded { fee_earned_msat, claim_from_onchain_tx } => {
+ Event::PaymentForwarded { fee_earned_msat, source_channel_id, claim_from_onchain_tx } => {
assert_eq!(fee_earned_msat, $expected_fee);
+ if fee_earned_msat.is_some() {
+ // Is the event channel_id in one of the channels between the two nodes?
+ assert!($node.node.list_channels().iter().any(|x| x.counterparty.node_id == $source_node.node.get_our_node_id() && x.channel_id == source_channel_id.unwrap()));
+ }
assert_eq!(claim_from_onchain_tx, $upstream_force_closed);
},
_ => panic!("Unexpected event"),
}
}
macro_rules! mid_update_fulfill_dance {
- ($node: expr, $prev_node: expr, $new_msgs: expr) => {
+ ($node: expr, $prev_node: expr, $next_node: expr, $new_msgs: expr) => {
{
$node.node.handle_update_fulfill_htlc(&$prev_node.node.get_our_node_id(), &next_msgs.as_ref().unwrap().0);
let fee = $node.node.channel_state.lock().unwrap().by_id.get(&next_msgs.as_ref().unwrap().0.channel_id).unwrap().config.forwarding_fee_base_msat;
- expect_payment_forwarded!($node, Some(fee as u64), false);
+ expect_payment_forwarded!($node, $next_node, Some(fee as u64), false);
expected_total_fee_msat += fee as u64;
check_added_monitors!($node, 1);
let new_next_msgs = if $new_msgs {
assert_eq!(expected_next_node, node.node.get_our_node_id());
let update_next_msgs = !skip_last || idx != expected_route.len() - 1;
if next_msgs.is_some() {
- mid_update_fulfill_dance!(node, prev_node, update_next_msgs);
+ // Since we are traversing in reverse, next_node is actually the previous node
+ let next_node: &Node;
+ if idx == expected_route.len() - 1 {
+ next_node = origin_node;
+ } else {
+ next_node = expected_route[expected_route.len() - 1 - idx - 1];
+ }
+ mid_update_fulfill_dance!(node, prev_node, next_node, update_next_msgs);
} else {
assert!(!update_next_msgs);
assert!(node.node.get_and_clear_pending_msg_events().is_empty());
pub fn route_payment<'a, 'b, 'c>(origin_node: &Node<'a, 'b, 'c>, expected_route: &[&Node<'a, 'b, 'c>], recv_value: u64) -> (PaymentPreimage, PaymentHash, PaymentSecret) {
let payment_params = PaymentParameters::from_node_id(expected_route.last().unwrap().node.get_our_node_id())
.with_features(InvoiceFeatures::known());
- let network_graph = origin_node.network_graph.read_only();
- let scorer = test_utils::TestScorer::with_penalty(0);
- let seed = [0u8; 32];
- let keys_manager = test_utils::TestKeysInterface::new(&seed, Network::Testnet);
- let random_seed_bytes = keys_manager.get_secure_random_bytes();
- let route = get_route(
- &origin_node.node.get_our_node_id(), &payment_params, &network_graph,
- Some(&origin_node.node.list_usable_channels().iter().collect::<Vec<_>>()),
- recv_value, TEST_FINAL_CLTV, origin_node.logger, &scorer, &random_seed_bytes).unwrap();
+ let route = get_route!(origin_node, payment_params, recv_value, TEST_FINAL_CLTV).unwrap();
assert_eq!(route.paths.len(), 1);
assert_eq!(route.paths[0].len(), expected_route.len());
for (node, hop) in expected_route.iter().zip(route.paths[0].iter()) {