From 4b7319afe92f2d33a2fe2f80f443f41055ea24e9 Mon Sep 17 00:00:00 2001 From: Oleksandr Pravdyvyi Date: Tue, 14 Oct 2025 10:18:54 +0300 Subject: [PATCH] fix: merge updates --- integration_tests/src/lib.rs | 76 +++++---- wallet/src/cli/token_program.rs | 270 ++++++++++++-------------------- wallet/src/lib.rs | 2 +- 3 files changed, 146 insertions(+), 202 deletions(-) diff --git a/integration_tests/src/lib.rs b/integration_tests/src/lib.rs index 0eaae0d..abe1c76 100644 --- a/integration_tests/src/lib.rs +++ b/integration_tests/src/lib.rs @@ -19,7 +19,9 @@ use tempfile::TempDir; use tokio::task::JoinHandle; use wallet::{ Command, SubcommandReturnValue, WalletCore, - cli::token_program::TokenProgramSubcommand, + cli::token_program::{ + TokenProgramSubcommand, TokenProgramSubcommandPrivate, TokenProgramSubcommandPublic, + }, config::PersistentAccountData, helperfunctions::{fetch_config, fetch_persistent_accounts}, }; @@ -351,12 +353,12 @@ pub async fn test_success_token_program() { .expect("Failed to produce new account, not present in persistent accounts"); // Create new token - let subcommand = TokenProgramSubcommand::CreateNewToken { + let subcommand = TokenProgramSubcommand::Public(TokenProgramSubcommandPublic::CreateNewToken { definition_addr: definition_addr.to_string(), supply_addr: supply_addr.to_string(), name: "A NAME".to_string(), total_supply: 37, - }; + }); wallet::execute_subcommand(Command::TokenProgram(subcommand)) .await .unwrap(); @@ -405,11 +407,11 @@ pub async fn test_success_token_program() { ); // Transfer 7 tokens from `supply_acc` to the account at address `recipient_addr` - let subcommand = TokenProgramSubcommand::TransferToken { + let subcommand = TokenProgramSubcommand::Public(TokenProgramSubcommandPublic::TransferToken { sender_addr: supply_addr.to_string(), recipient_addr: recipient_addr.to_string(), balance_to_move: 7, - }; + }); wallet::execute_subcommand(Command::TokenProgram(subcommand)) .await .unwrap(); @@ -485,12 +487,14 @@ pub async fn test_success_token_program_private_owned() { }; // Create new token - let subcommand = TokenProgramSubcommand::CreateNewTokenPrivateOwned { - definition_addr: definition_addr.to_string(), - supply_addr: supply_addr.to_string(), - name: "A NAME".to_string(), - total_supply: 37, - }; + let subcommand = TokenProgramSubcommand::Private( + TokenProgramSubcommandPrivate::CreateNewTokenPrivateOwned { + definition_addr: definition_addr.to_string(), + supply_addr: supply_addr.to_string(), + name: "A NAME".to_string(), + total_supply: 37, + }, + ); wallet::execute_subcommand(Command::TokenProgram(subcommand)) .await @@ -527,11 +531,12 @@ pub async fn test_success_token_program_private_owned() { assert!(verify_commitment_is_in_state(new_commitment1, &seq_client).await); // Transfer 7 tokens from `supply_acc` to the account at address `recipient_addr` - let subcommand = TokenProgramSubcommand::TransferTokenPrivateOwnedNotInitialized { - sender_addr: supply_addr.to_string(), - recipient_addr: recipient_addr.to_string(), - balance_to_move: 7, - }; + let subcommand = + TokenProgramSubcommand::Private(TokenProgramSubcommandPrivate::TransferTokenPrivateOwned { + sender_addr: supply_addr.to_string(), + recipient_addr: recipient_addr.to_string(), + balance_to_move: 7, + }); wallet::execute_subcommand(Command::TokenProgram(subcommand)) .await @@ -554,11 +559,12 @@ pub async fn test_success_token_program_private_owned() { assert!(verify_commitment_is_in_state(new_commitment2, &seq_client).await); // Transfer additional 7 tokens from `supply_acc` to the account at address `recipient_addr` - let subcommand = TokenProgramSubcommand::TransferTokenPrivateOwnedAlreadyInitialized { - sender_addr: supply_addr.to_string(), - recipient_addr: recipient_addr.to_string(), - balance_to_move: 7, - }; + let subcommand = + TokenProgramSubcommand::Private(TokenProgramSubcommandPrivate::TransferTokenPrivateOwned { + sender_addr: supply_addr.to_string(), + recipient_addr: recipient_addr.to_string(), + balance_to_move: 7, + }); wallet::execute_subcommand(Command::TokenProgram(subcommand)) .await @@ -614,12 +620,14 @@ pub async fn test_success_token_program_private_claiming_path() { }; // Create new token - let subcommand = TokenProgramSubcommand::CreateNewTokenPrivateOwned { - definition_addr: definition_addr.to_string(), - supply_addr: supply_addr.to_string(), - name: "A NAME".to_string(), - total_supply: 37, - }; + let subcommand = TokenProgramSubcommand::Private( + TokenProgramSubcommandPrivate::CreateNewTokenPrivateOwned { + definition_addr: definition_addr.to_string(), + supply_addr: supply_addr.to_string(), + name: "A NAME".to_string(), + total_supply: 37, + }, + ); wallet::execute_subcommand(Command::TokenProgram(subcommand)) .await @@ -662,12 +670,14 @@ pub async fn test_success_token_program_private_claiming_path() { .unwrap(); // Transfer 7 tokens from `supply_acc` to the account at address `recipient_addr` - let subcommand = TokenProgramSubcommand::TransferTokenPrivateForeign { - sender_addr: supply_addr.to_string(), - recipient_npk: hex::encode(recipient_keys.nullifer_public_key.0), - recipient_ipk: hex::encode(recipient_keys.incoming_viewing_public_key.0.clone()), - balance_to_move: 7, - }; + let subcommand = TokenProgramSubcommand::Private( + TokenProgramSubcommandPrivate::TransferTokenPrivateForeign { + sender_addr: supply_addr.to_string(), + recipient_npk: hex::encode(recipient_keys.nullifer_public_key.0), + recipient_ipk: hex::encode(recipient_keys.incoming_viewing_public_key.0.clone()), + balance_to_move: 7, + }, + ); let SubcommandReturnValue::PrivacyPreservingTransfer { tx_hash } = wallet::execute_subcommand(Command::TokenProgram(subcommand)) diff --git a/wallet/src/cli/token_program.rs b/wallet/src/cli/token_program.rs index d3b42ea..02c9b53 100644 --- a/wallet/src/cli/token_program.rs +++ b/wallet/src/cli/token_program.rs @@ -5,9 +5,20 @@ use nssa::Address; use crate::{SubcommandReturnValue, WalletCore, cli::WalletSubcommand}; -///Represents CLI subcommand for a wallet working with token_program +///Represents generic CLI subcommand for a wallet working with token_program #[derive(Subcommand, Debug, Clone)] pub enum TokenProgramSubcommand { + ///Public execution + #[command(subcommand)] + Public(TokenProgramSubcommandPublic), + ///Private execution + #[command(subcommand)] + Private(TokenProgramSubcommandPrivate), +} + +///Represents generic public CLI subcommand for a wallet working with token_program +#[derive(Subcommand, Debug, Clone)] +pub enum TokenProgramSubcommandPublic { //Create a new token using the token program CreateNewToken { #[arg(short, long)] @@ -28,6 +39,11 @@ pub enum TokenProgramSubcommand { #[arg(short, long)] balance_to_move: u128, }, +} + +///Represents generic public CLI subcommand for a wallet working with token_program +#[derive(Subcommand, Debug, Clone)] +pub enum TokenProgramSubcommandPrivate { //Create a new token using the token program CreateNewTokenPrivateOwned { #[arg(short, long)] @@ -40,16 +56,7 @@ pub enum TokenProgramSubcommand { total_supply: u128, }, //Transfer tokens using the token program - TransferTokenPrivateOwnedAlreadyInitialized { - #[arg(short, long)] - sender_addr: String, - #[arg(short, long)] - recipient_addr: String, - #[arg(short, long)] - balance_to_move: u128, - }, - //Transfer tokens using the token program - TransferTokenPrivateOwnedNotInitialized { + TransferTokenPrivateOwned { #[arg(short, long)] sender_addr: String, #[arg(short, long)] @@ -72,13 +79,13 @@ pub enum TokenProgramSubcommand { }, } -impl WalletSubcommand for TokenProgramSubcommand { +impl WalletSubcommand for TokenProgramSubcommandPublic { async fn handle_subcommand( self, wallet_core: &mut WalletCore, ) -> Result { match self { - TokenProgramSubcommand::CreateNewToken { + TokenProgramSubcommandPublic::CreateNewToken { definition_addr, supply_addr, name, @@ -101,7 +108,31 @@ impl WalletSubcommand for TokenProgramSubcommand { .await?; Ok(SubcommandReturnValue::Empty) } - TokenProgramSubcommand::CreateNewTokenPrivateOwned { + TokenProgramSubcommandPublic::TransferToken { + sender_addr, + recipient_addr, + balance_to_move, + } => { + wallet_core + .send_transfer_token_transaction( + sender_addr.parse().unwrap(), + recipient_addr.parse().unwrap(), + balance_to_move, + ) + .await?; + Ok(SubcommandReturnValue::Empty) + } + } + } +} + +impl WalletSubcommand for TokenProgramSubcommandPrivate { + async fn handle_subcommand( + self, + wallet_core: &mut WalletCore, + ) -> Result { + match self { + TokenProgramSubcommandPrivate::CreateNewTokenPrivateOwned { definition_addr, supply_addr, name, @@ -135,24 +166,12 @@ impl WalletSubcommand for TokenProgramSubcommand { .await?; if let NSSATransaction::PrivacyPreserving(tx) = transfer_tx { - let supply_ebc = tx.message.encrypted_private_post_states[0].clone(); - let supply_comm = tx.message.new_commitments[0].clone(); + let acc_decode_data = vec![(secret_supply, supply_addr)]; - let res_acc_supply = nssa_core::EncryptionScheme::decrypt( - &supply_ebc.ciphertext, - &secret_supply, - &supply_comm, - 0, - ) - .unwrap(); - - println!("Received new to acc {res_acc_supply:#?}"); - - println!("Transaction data is {:?}", tx.message); - - wallet_core - .storage - .insert_private_account_data(supply_addr, res_acc_supply); + wallet_core.decode_insert_privacy_preserving_transaction_results( + tx, + &acc_decode_data, + )?; } let path = wallet_core.store_persistent_accounts()?; @@ -161,21 +180,7 @@ impl WalletSubcommand for TokenProgramSubcommand { Ok(SubcommandReturnValue::PrivacyPreservingTransfer { tx_hash }) } - TokenProgramSubcommand::TransferToken { - sender_addr, - recipient_addr, - balance_to_move, - } => { - wallet_core - .send_transfer_token_transaction( - sender_addr.parse().unwrap(), - recipient_addr.parse().unwrap(), - balance_to_move, - ) - .await?; - Ok(SubcommandReturnValue::Empty) - } - TokenProgramSubcommand::TransferTokenPrivateOwnedAlreadyInitialized { + TokenProgramSubcommandPrivate::TransferTokenPrivateOwned { sender_addr, recipient_addr, balance_to_move, @@ -183,13 +188,27 @@ impl WalletSubcommand for TokenProgramSubcommand { let sender_addr: Address = sender_addr.parse().unwrap(); let recipient_addr: Address = recipient_addr.parse().unwrap(); - let (res, [secret_sender, secret_recipient]) = wallet_core - .send_transfer_token_transaction_private_owned_account_already_initialized( - sender_addr, - recipient_addr, - balance_to_move, - ) - .await?; + let recipient_initialized = wallet_core + .check_private_account_initialized(&recipient_addr) + .await; + + let (res, [secret_sender, secret_recipient]) = if recipient_initialized { + wallet_core + .send_transfer_token_transaction_private_owned_account_already_initialized( + sender_addr, + recipient_addr, + balance_to_move, + ) + .await? + } else { + wallet_core + .send_transfer_token_transaction_private_owned_account_not_initialized( + sender_addr, + recipient_addr, + balance_to_move, + ) + .await? + }; println!("Results of tx send is {res:#?}"); @@ -199,39 +218,15 @@ impl WalletSubcommand for TokenProgramSubcommand { .await?; if let NSSATransaction::PrivacyPreserving(tx) = transfer_tx { - let sender_ebc = tx.message.encrypted_private_post_states[0].clone(); - let sender_comm = tx.message.new_commitments[0].clone(); + let acc_decode_data = vec![ + (secret_sender, sender_addr), + (secret_recipient, recipient_addr), + ]; - let recipient_ebc = tx.message.encrypted_private_post_states[1].clone(); - let recipient_comm = tx.message.new_commitments[1].clone(); - - let res_acc_sender = nssa_core::EncryptionScheme::decrypt( - &sender_ebc.ciphertext, - &secret_sender, - &sender_comm, - 0, - ) - .unwrap(); - - let res_acc_recipient = nssa_core::EncryptionScheme::decrypt( - &recipient_ebc.ciphertext, - &secret_recipient, - &recipient_comm, - 1, - ) - .unwrap(); - - println!("Received new sender acc {res_acc_sender:#?}"); - println!("Received new recipient acc {res_acc_recipient:#?}"); - - println!("Transaction data is {:?}", tx.message); - - wallet_core - .storage - .insert_private_account_data(sender_addr, res_acc_sender); - wallet_core - .storage - .insert_private_account_data(recipient_addr, res_acc_recipient); + wallet_core.decode_insert_privacy_preserving_transaction_results( + tx, + &acc_decode_data, + )?; } let path = wallet_core.store_persistent_accounts()?; @@ -240,72 +235,7 @@ impl WalletSubcommand for TokenProgramSubcommand { Ok(SubcommandReturnValue::PrivacyPreservingTransfer { tx_hash }) } - TokenProgramSubcommand::TransferTokenPrivateOwnedNotInitialized { - sender_addr, - recipient_addr, - balance_to_move, - } => { - let sender_addr: Address = sender_addr.parse().unwrap(); - let recipient_addr: Address = recipient_addr.parse().unwrap(); - - let (res, [secret_sender, secret_recipient]) = wallet_core - .send_transfer_token_transaction_private_owned_account_not_initialized( - sender_addr, - recipient_addr, - balance_to_move, - ) - .await?; - - println!("Results of tx send is {res:#?}"); - - let tx_hash = res.tx_hash; - let transfer_tx = wallet_core - .poll_native_token_transfer(tx_hash.clone()) - .await?; - - if let NSSATransaction::PrivacyPreserving(tx) = transfer_tx { - let sender_ebc = tx.message.encrypted_private_post_states[0].clone(); - let sender_comm = tx.message.new_commitments[0].clone(); - - let recipient_ebc = tx.message.encrypted_private_post_states[1].clone(); - let recipient_comm = tx.message.new_commitments[1].clone(); - - let res_acc_sender = nssa_core::EncryptionScheme::decrypt( - &sender_ebc.ciphertext, - &secret_sender, - &sender_comm, - 0, - ) - .unwrap(); - - let res_acc_recipient = nssa_core::EncryptionScheme::decrypt( - &recipient_ebc.ciphertext, - &secret_recipient, - &recipient_comm, - 1, - ) - .unwrap(); - - println!("Received new sender acc {res_acc_sender:#?}"); - println!("Received new recipient acc {res_acc_recipient:#?}"); - - println!("Transaction data is {:?}", tx.message); - - wallet_core - .storage - .insert_private_account_data(sender_addr, res_acc_sender); - wallet_core - .storage - .insert_private_account_data(recipient_addr, res_acc_recipient); - } - - let path = wallet_core.store_persistent_accounts()?; - - println!("Stored persistent accounts at {path:#?}"); - - Ok(SubcommandReturnValue::PrivacyPreservingTransfer { tx_hash }) - } - TokenProgramSubcommand::TransferTokenPrivateForeign { + TokenProgramSubcommandPrivate::TransferTokenPrivateForeign { sender_addr, recipient_npk, recipient_ipk, @@ -341,24 +271,12 @@ impl WalletSubcommand for TokenProgramSubcommand { .await?; if let NSSATransaction::PrivacyPreserving(tx) = transfer_tx { - let sender_ebc = tx.message.encrypted_private_post_states[0].clone(); - let sender_comm = tx.message.new_commitments[0].clone(); + let acc_decode_data = vec![(secret_sender, sender_addr)]; - let res_acc_sender = nssa_core::EncryptionScheme::decrypt( - &sender_ebc.ciphertext, - &secret_sender, - &sender_comm, - 0, - ) - .unwrap(); - - println!("Received new sender acc {res_acc_sender:#?}"); - - println!("Transaction data is {:?}", tx.message); - - wallet_core - .storage - .insert_private_account_data(sender_addr, res_acc_sender); + wallet_core.decode_insert_privacy_preserving_transaction_results( + tx, + &acc_decode_data, + )?; } let path = wallet_core.store_persistent_accounts()?; @@ -370,3 +288,19 @@ impl WalletSubcommand for TokenProgramSubcommand { } } } + +impl WalletSubcommand for TokenProgramSubcommand { + async fn handle_subcommand( + self, + wallet_core: &mut WalletCore, + ) -> Result { + match self { + TokenProgramSubcommand::Private(private_subcommand) => { + private_subcommand.handle_subcommand(wallet_core).await + } + TokenProgramSubcommand::Public(public_subcommand) => { + public_subcommand.handle_subcommand(wallet_core).await + } + } + } +} diff --git a/wallet/src/lib.rs b/wallet/src/lib.rs index aacdfcd..ac4cf6d 100644 --- a/wallet/src/lib.rs +++ b/wallet/src/lib.rs @@ -338,7 +338,7 @@ pub enum Command { #[arg(long)] solution: u128, }, - ///Test command + ///Token command #[command(subcommand)] TokenProgram(TokenProgramSubcommand), }