lnv1_lnv2_swap_tests/
swap_tests.rs1use devimint::federation::Client;
2use devimint::{cmd, util};
3use fedimint_core::core::OperationId;
4use fedimint_lnv2_client::FinalSendOperationState;
5use lightning_invoice::Bolt11Invoice;
6use tracing::info;
7
8#[path = "common.rs"]
9mod common;
10
11#[tokio::main]
12async fn main() -> anyhow::Result<()> {
13 devimint::run_devfed_test()
14 .call(|dev_fed, _process_mgr| async move {
15 if !util::supports_lnv2() {
16 info!("lnv2 is disabled, skipping");
17 return Ok(());
18 }
19
20 let federation = dev_fed.fed().await?;
21
22 let client = federation
23 .new_joined_client("lnv1-lnv2-swap-test-client")
24 .await?;
25
26 federation.pegin_client(10_000, &client).await?;
27
28 let gw_lnd = dev_fed.gw_lnd().await?;
29
30 info!("Pegging-in gateway...");
31 federation.pegin_gateways(1_000_000, vec![gw_lnd]).await?;
32
33 info!("Testing LNv1 client can pay LNv2 invoice...");
34 let lnd_gw_id = gw_lnd.gateway_id.clone();
35 let (invoice, receive_op) = common::receive(&client, &gw_lnd.addr, 1_000_000).await?;
36 send_lnv1(&client, &lnd_gw_id, &invoice.to_string()).await?;
37 common::await_receive_claimed(&client, receive_op).await?;
38
39 info!("Testing LNv2 client can pay LNv1 invoice...");
40 let (invoice, receive_op) = receive_lnv1(&client, &lnd_gw_id, 1_000_000).await?;
41 common::send(
42 &client,
43 &gw_lnd.addr,
44 &invoice.to_string(),
45 FinalSendOperationState::Success,
46 )
47 .await?;
48 await_receive_lnv1(&client, receive_op).await?;
49
50 info!("LNv1 <-> LNv2 swap tests complete!");
51
52 Ok(())
53 })
54 .await
55}
56
57async fn receive_lnv1(
58 client: &Client,
59 gateway_id: &String,
60 amount_msats: u64,
61) -> anyhow::Result<(Bolt11Invoice, OperationId)> {
62 let invoice_response = cmd!(
63 client,
64 "module",
65 "ln",
66 "invoice",
67 amount_msats,
68 "--gateway-id",
69 gateway_id
70 )
71 .out_json()
72 .await?;
73 let invoice = serde_json::from_value::<Bolt11Invoice>(
74 invoice_response
75 .get("invoice")
76 .expect("Invoice should be present")
77 .clone(),
78 )?;
79 let operation_id = serde_json::from_value::<OperationId>(
80 invoice_response
81 .get("operation_id")
82 .expect("OperationId should be present")
83 .clone(),
84 )?;
85 Ok((invoice, operation_id))
86}
87
88async fn send_lnv1(client: &Client, gateway_id: &str, invoice: &str) -> anyhow::Result<()> {
89 let payment_result = cmd!(
90 client,
91 "module",
92 "ln",
93 "pay",
94 invoice,
95 "--gateway-id",
96 gateway_id
97 )
98 .out_json()
99 .await?;
100 assert!(
101 payment_result.get("Success").is_some() || payment_result.get("preimage").is_some(),
102 "LNv1 payment failed: {payment_result:?}"
103 );
104 Ok(())
105}
106
107async fn await_receive_lnv1(client: &Client, operation_id: OperationId) -> anyhow::Result<()> {
108 let lnv1_response = cmd!(client, "await-invoice", operation_id.fmt_full())
109 .out_json()
110 .await?;
111 assert!(lnv1_response.get("total_amount_msat").is_some());
112 Ok(())
113}