use std::collections::HashMap;
use std::env;
use serde_json::json;
use tx3_sdk::tii::Protocol;
use tx3_sdk::trp::{Client, ClientOptions};
use tx3_sdk::{CardanoSigner, Party, PollConfig, Tx3Client};
fn get_required_env(var: &str) -> Option<String> {
match env::var(var) {
Ok(val) => Some(val),
Err(_) => {
println!("Required environment variable {} is not set", var);
None
}
}
}
fn get_test_config() -> Option<(String, String, String)> {
let party_a = get_required_env("TEST_PARTY_A_ADDRESS")?;
let mnemonic_a = get_required_env("TEST_PARTY_A_MNEMONIC")?;
let party_b = env::var("TEST_PARTY_B_ADDRESS").unwrap_or_else(|_| party_a.clone());
let _mnemonic_b = env::var("TEST_PARTY_B_MNEMONIC").unwrap_or_else(|_| mnemonic_a.clone());
Some((party_a, mnemonic_a, party_b))
}
fn get_trp_api_key() -> Option<String> {
env::var("TRP_API_KEY_PREPROD").ok()
}
fn create_trp_client() -> Option<Client> {
let endpoint = get_required_env("TRP_ENDPOINT_PREPROD")?;
let mut headers = HashMap::new();
if let Some(api_key) = get_trp_api_key() {
headers.insert("dmtr-api-key".to_string(), api_key);
}
Some(Client::new(ClientOptions {
endpoint,
headers: if headers.is_empty() {
None
} else {
Some(headers)
},
}))
}
fn load_transfer_protocol() -> Protocol {
let manifest_dir = env!("CARGO_MANIFEST_DIR");
let tii_path = format!("{manifest_dir}/tests/fixtures/transfer.tii");
Protocol::from_file(&tii_path).expect("Failed to load transfer.tii")
}
#[tokio::test]
async fn test_trp_happy_path_lifecycle() {
let Some(trp) = create_trp_client() else {
println!("Skipping test: TRP_ENDPOINT_PREPROD not set");
return;
};
let Some((party_a, mnemonic_a, party_b)) = get_test_config() else {
println!("Skipping test: Missing required test configuration");
println!("Required: TEST_PARTY_A_ADDRESS, TEST_PARTY_A_MNEMONIC");
return;
};
let protocol = load_transfer_protocol();
let signer =
CardanoSigner::from_mnemonic(&party_a, &mnemonic_a).expect("Invalid mnemonic or address");
let tx3 = Tx3Client::new(protocol, trp.clone())
.with_profile("preprod")
.with_party("sender", Party::signer(signer))
.with_party("middleman", Party::address(&party_b))
.with_party("receiver", Party::address(&party_b));
let resolved = tx3
.tx("transfer")
.arg("quantity", json!(10_000_000))
.resolve()
.await
.expect("RESOLVE FAILED: Transaction resolution must succeed");
let signed = resolved
.sign()
.expect("SIGN FAILED: Transaction signing must succeed");
let submitted = signed
.submit()
.await
.expect("SUBMIT FAILED: Transaction submission must succeed");
let poll_config = PollConfig::default();
let _status = match submitted.wait_for_confirmed(poll_config).await {
Ok(status) => status,
Err(err) => {
let _ = trp.check_status(vec![submitted.hash.clone()]).await;
panic!("CONFIRMED CHECK FAILED: Transaction did not confirm in time: {err}");
}
};
}