diff --git a/accounts/src/account_core/mod.rs b/accounts/src/account_core/mod.rs index 1926649..f586019 100644 --- a/accounts/src/account_core/mod.rs +++ b/accounts/src/account_core/mod.rs @@ -25,6 +25,7 @@ pub struct Account { pub key_holder: AddressKeyHolder, pub address: AccountAddress, pub balance: u64, + pub nonce: u64, pub utxos: HashMap, } @@ -33,6 +34,7 @@ pub struct AccountForSerialization { pub key_holder: AddressKeyHolder, pub address: AccountAddress, pub balance: u64, + pub nonce: u64, pub utxos: HashMap, } @@ -42,6 +44,7 @@ impl From for AccountForSerialization { key_holder: value.key_holder, address: value.address, balance: value.balance, + nonce: value.nonce, utxos: value .utxos .into_iter() @@ -57,6 +60,7 @@ impl From for Account { key_holder: value.key_holder, address: value.address, balance: value.balance, + nonce: value.nonce, utxos: value .utxos .into_iter() @@ -120,12 +124,14 @@ impl Account { let public_key = *key_holder.get_pub_account_signing_key().verifying_key(); let address = address::from_public_key(&public_key); let balance = 0; + let nonce = 0; let utxos = HashMap::new(); Self { key_holder, address, balance, + nonce, utxos, } } @@ -134,12 +140,14 @@ impl Account { let key_holder = AddressKeyHolder::new_os_random(); let public_key = *key_holder.get_pub_account_signing_key().verifying_key(); let address = address::from_public_key(&public_key); + let nonce = 0; let utxos = HashMap::new(); Self { key_holder, address, balance, + nonce, utxos, } } diff --git a/ci_scripts/test-ubuntu.sh b/ci_scripts/test-ubuntu.sh index 90aa19e..db14402 100644 --- a/ci_scripts/test-ubuntu.sh +++ b/ci_scripts/test-ubuntu.sh @@ -6,5 +6,5 @@ source env.sh cargo test --release cd integration_tests -export NSSA_WALLET_HOME_DIR=$(pwd)/configs/debug/node/ +export NSSA_WALLET_HOME_DIR=$(pwd)/configs/debug/wallet/ cargo run $(pwd)/configs/debug all \ No newline at end of file diff --git a/integration_tests/configs/debug/wallet/wallet_config.json b/integration_tests/configs/debug/wallet/wallet_config.json index a1edc2f..e4dc7e9 100644 --- a/integration_tests/configs/debug/wallet/wallet_config.json +++ b/integration_tests/configs/debug/wallet/wallet_config.json @@ -40,6 +40,7 @@ 215 ], "balance": 10000, + "nonce": 0, "key_holder": { "address": [ 13, @@ -157,6 +158,7 @@ 100 ], "balance": 20000, + "nonce": 0, "key_holder": { "address": [ 151, diff --git a/integration_tests/src/lib.rs b/integration_tests/src/lib.rs index c323c3b..1f9684d 100644 --- a/integration_tests/src/lib.rs +++ b/integration_tests/src/lib.rs @@ -180,6 +180,72 @@ pub async fn test_failure() { info!("Success!"); } +pub async fn test_success_two_transactions() { + let command = Command::SendNativeTokenTransfer { + from: ACC_SENDER.to_string(), + nonce: 0, + to: ACC_RECEIVER.to_string(), + amount: 100, + }; + + let wallet_config = fetch_config().unwrap(); + + let seq_client = SequencerClient::new(wallet_config.sequencer_addr.clone()).unwrap(); + + wallet::execute_subcommand(command).await.unwrap(); + + info!("Waiting for next block creation"); + tokio::time::sleep(Duration::from_secs(TIME_TO_WAIT_FOR_BLOCK_SECONDS)).await; + + info!("Checking correct balance move"); + let acc_1_balance = seq_client + .get_account_balance(ACC_SENDER.to_string()) + .await + .unwrap(); + let acc_2_balance = seq_client + .get_account_balance(ACC_RECEIVER.to_string()) + .await + .unwrap(); + + info!("Balance of sender : {acc_1_balance:#?}"); + info!("Balance of receiver : {acc_2_balance:#?}"); + + assert_eq!(acc_1_balance.balance, 9900); + assert_eq!(acc_2_balance.balance, 20100); + + info!("First TX Success!"); + + let command = Command::SendNativeTokenTransfer { + from: ACC_SENDER.to_string(), + nonce: 1, + to: ACC_RECEIVER.to_string(), + amount: 100, + }; + + wallet::execute_subcommand(command).await.unwrap(); + + info!("Waiting for next block creation"); + tokio::time::sleep(Duration::from_secs(TIME_TO_WAIT_FOR_BLOCK_SECONDS)).await; + + info!("Checking correct balance move"); + let acc_1_balance = seq_client + .get_account_balance(ACC_SENDER.to_string()) + .await + .unwrap(); + let acc_2_balance = seq_client + .get_account_balance(ACC_RECEIVER.to_string()) + .await + .unwrap(); + + info!("Balance of sender : {acc_1_balance:#?}"); + info!("Balance of receiver : {acc_2_balance:#?}"); + + assert_eq!(acc_1_balance.balance, 9800); + assert_eq!(acc_2_balance.balance, 20200); + + info!("Second TX Success!"); +} + macro_rules! test_cleanup_wrap { ($home_dir:ident, $test_func:ident) => {{ let res = pre_test($home_dir.clone()).await.unwrap(); @@ -212,10 +278,14 @@ pub async fn main_tests_runner() -> Result<()> { "test_failure" => { test_cleanup_wrap!(home_dir, test_failure); } + "test_success_two_transactions" => { + test_cleanup_wrap!(home_dir, test_success_two_transactions); + } "all" => { test_cleanup_wrap!(home_dir, test_success_move_to_another_account); test_cleanup_wrap!(home_dir, test_success); test_cleanup_wrap!(home_dir, test_failure); + test_cleanup_wrap!(home_dir, test_success_two_transactions); } _ => { anyhow::bail!("Unknown test name"); diff --git a/wallet/src/chain_storage/mod.rs b/wallet/src/chain_storage/mod.rs index 4d5e7ab..f0fa6b1 100644 --- a/wallet/src/chain_storage/mod.rs +++ b/wallet/src/chain_storage/mod.rs @@ -115,6 +115,7 @@ mod tests { 249 ], "balance": 100, + "nonce": 0, "key_holder": { "nullifer_public_key": "03A340BECA9FAAB444CED0140681D72EA1318B5C611704FEE017DA9836B17DB718", "pub_account_signing_key": [ @@ -199,6 +200,7 @@ mod tests { 85 ], "balance": 200, + "nonce": 0, "key_holder": { "nullifer_public_key": "02172F50274DE67C4087C344F5D58E11DF761D90285B095060E0994FAA6BCDE271", "pub_account_signing_key": [ diff --git a/wallet/src/lib.rs b/wallet/src/lib.rs index df78de7..9c17751 100644 --- a/wallet/src/lib.rs +++ b/wallet/src/lib.rs @@ -112,6 +112,15 @@ impl WalletCore { } } + ///Helperfunction to increment nonces for all given accounts + fn increment_nonces(&mut self, accounts_to_increment_nonces: &[AccountAddress]) { + for acc_addr in accounts_to_increment_nonces { + if let Some(acc) = self.storage.acc_map.get_mut(acc_addr) { + acc.nonce += 1; + } + } + } + ///Dumps all accounts from acc_map at `path` /// ///Currently storing everything in one file @@ -189,13 +198,20 @@ pub async fn execute_subcommand(command: Command) -> Result<()> { let from = produce_account_addr_from_hex(from)?; let to = produce_account_addr_from_hex(to)?; - let wallet_core = WalletCore::start_from_config_update_chain(wallet_config).await?; + let mut wallet_core = WalletCore::start_from_config_update_chain(wallet_config).await?; let res = wallet_core .send_public_native_token_transfer(from, nonce, to, amount) .await?; info!("Results of tx send is {res:#?}"); + + //ToDo: Insert transaction polling logic here + wallet_core.increment_nonces(&[from, to]); + + let acc_storage_path = wallet_core.store_present_accounts_at_home()?; + + info!("Accounts stored at {acc_storage_path:#?}"); } Command::DumpAccountsOnDisc { dump_path } => { let node_config = fetch_config()?;