diff --git a/magicblock-aperture/src/requests/http/mod.rs b/magicblock-aperture/src/requests/http/mod.rs index b7a8c0beb..b0432a365 100644 --- a/magicblock-aperture/src/requests/http/mod.rs +++ b/magicblock-aperture/src/requests/http/mod.rs @@ -10,7 +10,7 @@ use log::*; use magicblock_core::{ link::transactions::SanitizeableTransaction, traits::AccountsBank, }; -use magicblock_metrics::metrics::ENSURE_ACCOUNTS_TIME; +use magicblock_metrics::metrics::{AccountFetchOrigin, ENSURE_ACCOUNTS_TIME}; use prelude::JsonBody; use solana_account::AccountSharedData; use solana_pubkey::Pubkey; @@ -107,7 +107,7 @@ impl HttpDispatcher { .start_timer(); let _ = self .chainlink - .ensure_accounts(&[*pubkey], None) + .ensure_accounts(&[*pubkey], None, AccountFetchOrigin::GetAccount) .await .inspect_err(|e| { // There is nothing we can do if fetching the account fails @@ -129,7 +129,11 @@ impl HttpDispatcher { .start_timer(); let _ = self .chainlink - .ensure_accounts(pubkeys, None) + .ensure_accounts( + pubkeys, + None, + AccountFetchOrigin::GetMultipleAccounts, + ) .await .inspect_err(|e| { // There is nothing we can do if fetching the accounts fails diff --git a/magicblock-chainlink/src/chainlink/fetch_cloner.rs b/magicblock-chainlink/src/chainlink/fetch_cloner.rs index 96c133191..f2266f96e 100644 --- a/magicblock-chainlink/src/chainlink/fetch_cloner.rs +++ b/magicblock-chainlink/src/chainlink/fetch_cloner.rs @@ -12,7 +12,7 @@ use dlp::{ }; use log::*; use magicblock_core::traits::AccountsBank; -use magicblock_metrics::metrics; +use magicblock_metrics::metrics::{self, AccountFetchOrigin}; use solana_account::{AccountSharedData, ReadableAccount}; use solana_pubkey::Pubkey; use solana_sdk::system_program; @@ -293,6 +293,7 @@ where self, pubkey, account.remote_slot(), + AccountFetchOrigin::GetAccount, ) .await { @@ -361,6 +362,7 @@ where pubkey, delegation_record_pubkey, account.remote_slot(), + AccountFetchOrigin::GetAccount, ) .await { @@ -492,6 +494,7 @@ where &self, account_pubkey: Pubkey, min_context_slot: u64, + fetch_origin: metrics::AccountFetchOrigin, ) -> Option { let delegation_record_pubkey = delegation_record_pda_from_delegated_account(&account_pubkey); @@ -507,6 +510,7 @@ where min_context_slot: Some(min_context_slot), ..Default::default() }), + fetch_origin, ) .await { @@ -569,6 +573,7 @@ where pubkeys: &[Pubkey], mark_empty_if_not_found: Option<&[Pubkey]>, slot: Option, + fetch_origin: AccountFetchOrigin, ) -> ChainlinkResult { if log::log_enabled!(log::Level::Trace) { let pubkeys = pubkeys @@ -603,7 +608,7 @@ where let accs = self .remote_account_provider - .try_get_multi(pubkeys, mark_empty_if_not_found) + .try_get_multi(pubkeys, mark_empty_if_not_found, fetch_origin) .await?; trace!("Fetched {accs:?}"); @@ -741,6 +746,7 @@ where self.task_to_fetch_with_delegation_record( *pubkey, effective_slot, + fetch_origin, ), ); } @@ -898,6 +904,7 @@ where min_context_slot: batch_min_context_slot, ..Default::default() }), + fetch_origin, ) .await } else { @@ -1106,6 +1113,7 @@ where &self, pubkey: &Pubkey, in_bank: &AccountSharedData, + fetch_origin: AccountFetchOrigin, ) -> bool { if in_bank.undelegating() { debug!("Fetching undelegating account {pubkey}. delegated={}, undelegating={}", in_bank.delegated(), in_bank.undelegating()); @@ -1113,6 +1121,7 @@ where .fetch_and_parse_delegation_record( *pubkey, self.remote_account_provider.chain_slot(), + fetch_origin, ) .await; let delegated_on_chain = deleg_record.as_ref().is_some_and(|dr| { @@ -1154,6 +1163,7 @@ where pubkeys: &[Pubkey], mark_empty_if_not_found: Option<&[Pubkey]>, slot: Option, + fetch_origin: AccountFetchOrigin, ) -> ChainlinkResult { // We cannot clone blacklisted accounts, thus either they are already // in the bank (e.g. native programs) or they don't exist and the transaction @@ -1182,6 +1192,7 @@ where .should_refresh_undelegating_in_bank_account( pubkey, &account_in_bank, + fetch_origin, ) .await; if should_refresh_undelegating { @@ -1230,6 +1241,7 @@ where &fetch_new, mark_empty_if_not_found, slot, + fetch_origin, ) .await } else { @@ -1285,6 +1297,7 @@ where &self, pubkey: Pubkey, slot: u64, + fetch_origin: AccountFetchOrigin, ) -> task::JoinHandle> { let delegation_record_pubkey = delegation_record_pda_from_delegated_account(&pubkey); @@ -1292,6 +1305,7 @@ where pubkey, delegation_record_pubkey, slot, + fetch_origin, ) } @@ -1299,10 +1313,16 @@ where &self, pubkey: Pubkey, slot: u64, + fetch_origin: AccountFetchOrigin, ) -> task::JoinHandle> { let program_data_pubkey = get_loaderv3_get_program_data_address(&pubkey); - self.task_to_fetch_with_companion(pubkey, program_data_pubkey, slot) + self.task_to_fetch_with_companion( + pubkey, + program_data_pubkey, + slot, + fetch_origin, + ) } fn task_to_fetch_with_companion( @@ -1310,6 +1330,7 @@ where pubkey: Pubkey, companion_pubkey: Pubkey, slot: u64, + fetch_origin: AccountFetchOrigin, ) -> task::JoinHandle> { let provider = self.remote_account_provider.clone(); let bank = self.accounts_bank.clone(); @@ -1327,6 +1348,7 @@ where min_context_slot: Some(slot), ..Default::default() }), + fetch_origin, ) .await // SAFETY: we always get two results here @@ -1861,7 +1883,12 @@ mod tests { .await; let result = fetch_cloner - .fetch_and_clone_accounts(&[account_pubkey], None, None) + .fetch_and_clone_accounts( + &[account_pubkey], + None, + None, + AccountFetchOrigin::GetAccount, + ) .await; debug!("Test result: {result:?}"); @@ -1894,7 +1921,12 @@ mod tests { .await; let result = fetch_cloner - .fetch_and_clone_accounts(&[non_existing_pubkey], None, None) + .fetch_and_clone_accounts( + &[non_existing_pubkey], + None, + None, + AccountFetchOrigin::GetAccount, + ) .await; debug!("Test result: {result:?}"); @@ -1948,7 +1980,12 @@ mod tests { // Test fetch and clone let result = fetch_cloner - .fetch_and_clone_accounts(&[account_pubkey], None, None) + .fetch_and_clone_accounts( + &[account_pubkey], + None, + None, + AccountFetchOrigin::GetAccount, + ) .await; debug!("Test result: {result:?}"); @@ -2020,7 +2057,12 @@ mod tests { ); let result = fetch_cloner - .fetch_and_clone_accounts(&[account_pubkey], None, None) + .fetch_and_clone_accounts( + &[account_pubkey], + None, + None, + AccountFetchOrigin::GetAccount, + ) .await; debug!("Test result: {result:?}"); @@ -2097,7 +2139,12 @@ mod tests { account_owner, ); let result = fetch_cloner - .fetch_and_clone_accounts(&[deleg_record_pubkey], None, None) + .fetch_and_clone_accounts( + &[deleg_record_pubkey], + None, + None, + AccountFetchOrigin::GetAccount, + ) .await; assert!(result.is_ok()); @@ -2106,7 +2153,12 @@ mod tests { // Fetch and clone the delegated account let result = fetch_cloner - .fetch_and_clone_accounts(&[account_pubkey], None, None) + .fetch_and_clone_accounts( + &[account_pubkey], + None, + None, + AccountFetchOrigin::GetAccount, + ) .await; assert!(result.is_ok()); @@ -2203,6 +2255,7 @@ mod tests { ], None, None, + AccountFetchOrigin::GetAccount, ) .await; @@ -2305,6 +2358,7 @@ mod tests { &[delegated_pubkey, invalid_delegated_pubkey], None, None, + AccountFetchOrigin::GetAccount, ) .await; @@ -2372,7 +2426,12 @@ mod tests { // Initially we should not be able to clone the account since we cannot // find a valid delegation record (up to date the same way the account is) let result = fetch_cloner - .fetch_and_clone_accounts(&[account_pubkey], None, None) + .fetch_and_clone_accounts( + &[account_pubkey], + None, + None, + AccountFetchOrigin::GetAccount, + ) .await; debug!("Test result: {result:?}"); @@ -2388,7 +2447,12 @@ mod tests { // at the required slot then all is ok rpc_client.account_override_slot(&deleg_record_pubkey, CURRENT_SLOT); let result = fetch_cloner - .fetch_and_clone_accounts(&[account_pubkey], None, None) + .fetch_and_clone_accounts( + &[account_pubkey], + None, + None, + AccountFetchOrigin::GetAccount, + ) .await; debug!("Test result after updating delegation record: {result:?}"); assert!(result.is_ok()); @@ -2437,7 +2501,12 @@ mod tests { // Initially we should not be able to clone the account since the account // is stale (delegation record is up to date but account is behind) let result = fetch_cloner - .fetch_and_clone_accounts(&[account_pubkey], None, None) + .fetch_and_clone_accounts( + &[account_pubkey], + None, + None, + AccountFetchOrigin::GetAccount, + ) .await; debug!("Test result: {result:?}"); @@ -2452,7 +2521,12 @@ mod tests { // After the RPC provider updates the account to the current slot rpc_client.account_override_slot(&account_pubkey, CURRENT_SLOT); let result = fetch_cloner - .fetch_and_clone_accounts(&[account_pubkey], None, None) + .fetch_and_clone_accounts( + &[account_pubkey], + None, + None, + AccountFetchOrigin::GetAccount, + ) .await; debug!("Test result after updating account: {result:?}"); assert!(result.is_ok()); @@ -2512,6 +2586,7 @@ mod tests { &[account_pubkey], None, None, + AccountFetchOrigin::GetAccount, ) .await }) @@ -2580,6 +2655,7 @@ mod tests { &[account_pubkey], None, None, + AccountFetchOrigin::GetAccount, ) .await }) @@ -2651,7 +2727,12 @@ mod tests { // Initially fetch and clone the delegated account // This should result in no active subscription since it's delegated to us let result = fetch_cloner - .fetch_and_clone_accounts(&[account_pubkey], None, None) + .fetch_and_clone_accounts( + &[account_pubkey], + None, + None, + AccountFetchOrigin::GetAccount, + ) .await; assert!(result.is_ok()); @@ -2738,7 +2819,12 @@ mod tests { let fetch_cloner = fetch_cloner.clone(); tokio::spawn(async move { fetch_cloner - .fetch_and_clone_accounts_with_dedup(&accounts, None, None) + .fetch_and_clone_accounts_with_dedup( + &accounts, + None, + None, + AccountFetchOrigin::GetAccount, + ) .await }) }; @@ -2823,6 +2909,7 @@ mod tests { ], Some(&[marked_non_existing_account_pubkey]), None, + AccountFetchOrigin::GetAccount, ) .await .expect("Fetch and clone failed"); diff --git a/magicblock-chainlink/src/chainlink/mod.rs b/magicblock-chainlink/src/chainlink/mod.rs index d2ced15c1..2e0082d59 100644 --- a/magicblock-chainlink/src/chainlink/mod.rs +++ b/magicblock-chainlink/src/chainlink/mod.rs @@ -8,6 +8,7 @@ use errors::ChainlinkResult; use fetch_cloner::FetchCloner; use log::*; use magicblock_core::traits::AccountsBank; +use magicblock_metrics::metrics::AccountFetchOrigin; use solana_account::{AccountSharedData, ReadableAccount}; use solana_pubkey::Pubkey; use solana_sdk::{ @@ -270,7 +271,11 @@ Kept: {} delegated, {} blacklisted", // Ensure accounts let res = self - .ensure_accounts(&pubkeys, mark_empty_if_not_found) + .ensure_accounts( + &pubkeys, + mark_empty_if_not_found, + AccountFetchOrigin::SendTransaction, + ) .await?; // Best-effort auto airdrop for fee payer if configured @@ -309,6 +314,7 @@ Kept: {} delegated, {} blacklisted", &self, pubkeys: &[Pubkey], mark_empty_if_not_found: Option<&[Pubkey]>, + fetch_origin: AccountFetchOrigin, ) -> ChainlinkResult { let Some(fetch_cloner) = self.fetch_cloner() else { return Ok(FetchAndCloneResult::default()); @@ -317,6 +323,7 @@ Kept: {} delegated, {} blacklisted", fetch_cloner, pubkeys, mark_empty_if_not_found, + fetch_origin, ) .await } @@ -328,6 +335,7 @@ Kept: {} delegated, {} blacklisted", pub async fn fetch_accounts( &self, pubkeys: &[Pubkey], + fetch_origin: AccountFetchOrigin, ) -> ChainlinkResult>> { if log::log_enabled!(log::Level::Trace) { let pubkeys = pubkeys @@ -345,7 +353,7 @@ Kept: {} delegated, {} blacklisted", .collect()); }; let _ = self - .fetch_accounts_common(fetch_cloner, pubkeys, None) + .fetch_accounts_common(fetch_cloner, pubkeys, None, fetch_origin) .await?; let accounts = pubkeys @@ -360,6 +368,7 @@ Kept: {} delegated, {} blacklisted", fetch_cloner: &FetchCloner, pubkeys: &[Pubkey], mark_empty_if_not_found: Option<&[Pubkey]>, + fetch_origin: AccountFetchOrigin, ) -> ChainlinkResult { if log::log_enabled!(log::Level::Trace) { let pubkeys_str = pubkeys @@ -389,6 +398,7 @@ Kept: {} delegated, {} blacklisted", pubkeys, mark_empty_if_not_found, None, + fetch_origin, ) .await?; trace!("Fetched and cloned accounts: {result:?}"); diff --git a/magicblock-chainlink/src/lib.rs b/magicblock-chainlink/src/lib.rs index 3989deef0..bb757a4fa 100644 --- a/magicblock-chainlink/src/lib.rs +++ b/magicblock-chainlink/src/lib.rs @@ -6,6 +6,7 @@ pub mod remote_account_provider; pub mod submux; pub use chainlink::*; +pub use magicblock_metrics::metrics::AccountFetchOrigin; #[cfg(any(test, feature = "dev-context"))] pub mod testing; diff --git a/magicblock-chainlink/src/remote_account_provider/mod.rs b/magicblock-chainlink/src/remote_account_provider/mod.rs index c41318767..d618472e7 100644 --- a/magicblock-chainlink/src/remote_account_provider/mod.rs +++ b/magicblock-chainlink/src/remote_account_provider/mod.rs @@ -51,7 +51,7 @@ use magicblock_metrics::{ metrics::{ inc_account_fetches_failed, inc_account_fetches_found, inc_account_fetches_not_found, inc_account_fetches_success, - set_monitored_accounts_count, + set_monitored_accounts_count, AccountFetchOrigin, }, }; pub use remote_account::{ResolvedAccount, ResolvedAccountSharedData}; @@ -317,7 +317,9 @@ impl RemoteAccountProvider { let updates = me.pubsub_client.take_updates(); me.listen_for_account_updates(updates)?; - let clock_remote_account = me.try_get(clock::ID).await?; + let clock_remote_account = me + .try_get(clock::ID, AccountFetchOrigin::GetAccount) + .await?; match clock_remote_account { RemoteAccount::NotFound(_) => { Err(RemoteAccountProviderError::ClockAccountCouldNotBeResolved( @@ -507,8 +509,9 @@ impl RemoteAccountProvider { pub async fn try_get( &self, pubkey: Pubkey, + fetch_origin: AccountFetchOrigin, ) -> RemoteAccountProviderResult { - self.try_get_multi(&[pubkey], None) + self.try_get_multi(&[pubkey], None, fetch_origin) .await // SAFETY: we are guaranteed to have a single result here as // otherwise we would have gotten an error @@ -519,12 +522,14 @@ impl RemoteAccountProvider { &self, pubkeys: &[Pubkey], config: Option, + fetch_origin: AccountFetchOrigin, ) -> RemoteAccountProviderResult> { use SlotsMatchResult::*; // 1. Fetch the _normal_ way and hope the slots match and if required // the min_context_slot is met - let remote_accounts = self.try_get_multi(pubkeys, None).await?; + let remote_accounts = + self.try_get_multi(pubkeys, None, fetch_origin).await?; if let Match = slots_match_and_meet_min_context( &remote_accounts, config.as_ref().and_then(|c| c.min_context_slot), @@ -547,7 +552,7 @@ impl RemoteAccountProvider { self.chain_slot() ); } - self.fetch(pubkeys.to_vec(), None, self.chain_slot()); + self.fetch(pubkeys.to_vec(), None, self.chain_slot(), fetch_origin); } // 3. Wait for the slots to match @@ -567,7 +572,8 @@ impl RemoteAccountProvider { pubkey_slots ); } - let remote_accounts = self.try_get_multi(pubkeys, None).await?; + let remote_accounts = + self.try_get_multi(pubkeys, None, fetch_origin).await?; let slots_match_result = slots_match_and_meet_min_context( &remote_accounts, config.min_context_slot, @@ -617,6 +623,7 @@ impl RemoteAccountProvider { &self, pubkeys: &[Pubkey], mark_empty_if_not_found: Option<&[Pubkey]>, + fetch_origin: AccountFetchOrigin, ) -> RemoteAccountProviderResult> { if pubkeys.is_empty() { return Ok(vec![]); @@ -651,7 +658,12 @@ impl RemoteAccountProvider { // Start the fetch let min_context_slot = fetch_start_slot; - self.fetch(pubkeys.to_vec(), mark_empty_if_not_found, min_context_slot); + self.fetch( + pubkeys.to_vec(), + mark_empty_if_not_found, + min_context_slot, + fetch_origin, + ); // Wait for all accounts to resolve (either from fetch or subscription override) let mut resolved_accounts = vec![]; @@ -842,6 +854,7 @@ impl RemoteAccountProvider { pubkeys: Vec, mark_empty_if_not_found: Option<&[Pubkey]>, min_context_slot: u64, + fetch_origin: AccountFetchOrigin, ) { const MAX_RETRIES: u64 = 10; @@ -1019,8 +1032,8 @@ impl RemoteAccountProvider { // Update metrics for successful RPC fetch inc_account_fetches_success(pubkeys.len() as u64); - inc_account_fetches_found(found_count); - inc_account_fetches_not_found(not_found_count); + inc_account_fetches_found(fetch_origin, found_count); + inc_account_fetches_not_found(fetch_origin, not_found_count); if log_enabled!(log::Level::Trace) { let pubkeys = pubkeys @@ -1175,8 +1188,10 @@ mod test { }; let pubkey = random_pubkey(); - let remote_account = - remote_account_provider.try_get(pubkey).await.unwrap(); + let remote_account = remote_account_provider + .try_get(pubkey, AccountFetchOrigin::GetAccount) + .await + .unwrap(); assert!(!remote_account.is_found()); } @@ -1228,8 +1243,10 @@ mod test { ) }; - let remote_account = - remote_account_provider.try_get(pubkey).await.unwrap(); + let remote_account = remote_account_provider + .try_get(pubkey, AccountFetchOrigin::GetAccount) + .await + .unwrap(); let AccountAtSlot { account, slot } = rpc_client.get_account_at_slot(&pubkey).unwrap(); assert_eq!( @@ -1330,6 +1347,7 @@ mod test { retry_interval_ms: 50, min_context_slot: None, }), + AccountFetchOrigin::GetAccount, ) .await .unwrap(); @@ -1365,6 +1383,7 @@ mod test { retry_interval_ms: 50, min_context_slot: None, }), + AccountFetchOrigin::GetAccount, ) .await; @@ -1402,6 +1421,7 @@ mod test { retry_interval_ms: 50, min_context_slot: Some(CURRENT_SLOT + 1), }), + AccountFetchOrigin::GetAccount, ) .await; @@ -1443,6 +1463,7 @@ mod test { retry_interval_ms: 50, min_context_slot: Some(CURRENT_SLOT), }), + AccountFetchOrigin::GetAccount, ) .await; @@ -1535,7 +1556,10 @@ mod test { // Add three accounts (up to limit) for pk in pubkeys { - provider.try_get(*pk).await.unwrap(); + provider + .try_get(*pk, AccountFetchOrigin::GetAccount) + .await + .unwrap(); } // No evictions should occur @@ -1562,16 +1586,31 @@ mod test { setup_with_accounts(pubkeys, 3).await; // Fill cache: [1, 2, 3] (1 is least recently used) - provider.try_get(pubkey1).await.unwrap(); - provider.try_get(pubkey2).await.unwrap(); - provider.try_get(pubkey3).await.unwrap(); + provider + .try_get(pubkey1, AccountFetchOrigin::GetAccount) + .await + .unwrap(); + provider + .try_get(pubkey2, AccountFetchOrigin::GetAccount) + .await + .unwrap(); + provider + .try_get(pubkey3, AccountFetchOrigin::GetAccount) + .await + .unwrap(); // Access pubkey1 to make it more recently used: [2, 3, 1] // This should just promote, making order [2, 3, 1] - provider.try_get(pubkey1).await.unwrap(); + provider + .try_get(pubkey1, AccountFetchOrigin::GetAccount) + .await + .unwrap(); // Add pubkey4, should evict pubkey2 (now least recently used) - provider.try_get(pubkey4).await.unwrap(); + provider + .try_get(pubkey4, AccountFetchOrigin::GetAccount) + .await + .unwrap(); // Check channel received the evicted account @@ -1579,7 +1618,10 @@ mod test { assert_eq!(removed_accounts, [pubkey2]); // Add pubkey5, should evict pubkey3 (now least recently used) - provider.try_get(pubkey5).await.unwrap(); + provider + .try_get(pubkey5, AccountFetchOrigin::GetAccount) + .await + .unwrap(); // Check channel received the second evicted account let removed_accounts = drain_removed_account_rx(&mut removed_rx); @@ -1602,12 +1644,18 @@ mod test { // Fill cache to capacity (no evictions) for pk in pubkeys.iter().take(4) { - provider.try_get(*pk).await.unwrap(); + provider + .try_get(*pk, AccountFetchOrigin::GetAccount) + .await + .unwrap(); } // Add more accounts and verify evictions happen in LRU order for i in 4..7 { - provider.try_get(pubkeys[i]).await.unwrap(); + provider + .try_get(pubkeys[i], AccountFetchOrigin::GetAccount) + .await + .unwrap(); let expected_evicted = pubkeys[i - 4]; // Should evict the account added 4 steps ago // Verify the evicted account was sent over the channel diff --git a/magicblock-chainlink/tests/01_ensure-accounts.rs b/magicblock-chainlink/tests/01_ensure-accounts.rs index 62723bac4..e1af349ae 100644 --- a/magicblock-chainlink/tests/01_ensure-accounts.rs +++ b/magicblock-chainlink/tests/01_ensure-accounts.rs @@ -6,7 +6,7 @@ use magicblock_chainlink::{ assert_not_cloned, assert_not_found, assert_not_subscribed, assert_not_undelegating, assert_remain_undelegating, assert_subscribed_without_delegation_record, - testing::deleg::add_delegation_record_for, + testing::deleg::add_delegation_record_for, AccountFetchOrigin, }; use solana_account::{Account, AccountSharedData}; use solana_pubkey::Pubkey; @@ -36,7 +36,14 @@ async fn test_write_non_existing_account() { let pubkey = Pubkey::new_unique(); let pubkeys = [pubkey]; - let res = chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + let res = chainlink + .ensure_accounts( + &pubkeys, + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); debug!("res: {res:?}"); assert_not_found!(res, &pubkeys); @@ -60,7 +67,14 @@ async fn test_existing_account_undelegated() { rpc_client.add_account(pubkey, Account::default()); let pubkeys = [pubkey]; - let res = chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + let res = chainlink + .ensure_accounts( + &pubkeys, + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); debug!("res: {res:?}"); assert_cloned_as_undelegated!(cloner, &pubkeys, CURRENT_SLOT); @@ -89,7 +103,14 @@ async fn test_existing_account_missing_delegation_record() { ); let pubkeys = [pubkey]; - let res = chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + let res = chainlink + .ensure_accounts( + &pubkeys, + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); debug!("res: {res:?}"); assert_cloned_as_undelegated!(cloner, &pubkeys, CURRENT_SLOT); @@ -123,7 +144,14 @@ async fn test_write_existing_account_valid_delegation_record() { add_delegation_record_for(&rpc_client, pubkey, validator_pubkey, owner); let pubkeys = [pubkey]; - let res = chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + let res = chainlink + .ensure_accounts( + &pubkeys, + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); debug!("res: {res:?}"); // The account is cloned into the bank as delegated, the delegation record isn't @@ -161,7 +189,14 @@ async fn test_write_existing_account_other_authority() { add_delegation_record_for(&rpc_client, pubkey, authority, owner); let pubkeys = [pubkey]; - let res = chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + let res = chainlink + .ensure_accounts( + &pubkeys, + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); debug!("res: {res:?}"); // The account is cloned into the bank as undelegated, the delegation record isn't @@ -209,7 +244,14 @@ async fn test_write_undelegating_account_undelegated_to_other_validator() { bank.insert(pubkey, shared_data); let pubkeys = [pubkey]; - let res = chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + let res = chainlink + .ensure_accounts( + &pubkeys, + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); debug!("res: {res:?}"); assert_not_undelegating!(cloner, &pubkeys, CURRENT_SLOT); } @@ -250,7 +292,14 @@ async fn test_write_undelegating_account_still_being_undelegated() { bank.insert(pubkey, shared_data); let pubkeys = [pubkey]; - let res = chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + let res = chainlink + .ensure_accounts( + &pubkeys, + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); debug!("res: {res:?}"); assert_remain_undelegating!(cloner, &pubkeys, CURRENT_SLOT); } @@ -286,7 +335,13 @@ async fn test_write_existing_account_invalid_delegation_record() { }, ); - let res = chainlink.ensure_accounts(&[pubkey], None).await; + let res = chainlink + .ensure_accounts( + &[pubkey], + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await; debug!("res: {res:?}"); assert_matches!(res, Err(_)); diff --git a/magicblock-chainlink/tests/03_deleg_after_sub.rs b/magicblock-chainlink/tests/03_deleg_after_sub.rs index a30ca2eb5..65f028985 100644 --- a/magicblock-chainlink/tests/03_deleg_after_sub.rs +++ b/magicblock-chainlink/tests/03_deleg_after_sub.rs @@ -4,6 +4,7 @@ use magicblock_chainlink::{ assert_not_cloned, assert_not_subscribed, assert_subscribed_without_delegation_record, testing::{deleg::add_delegation_record_for, init_logger}, + AccountFetchOrigin, }; use solana_account::Account; use solana_pubkey::Pubkey; @@ -53,7 +54,14 @@ async fn test_deleg_after_subscribe_case2() { info!("1. Initially the account does not exist"); assert_not_cloned!(cloner, &[pubkey]); - chainlink.ensure_accounts(&[pubkey], None).await.unwrap(); + chainlink + .ensure_accounts( + &[pubkey], + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); assert_not_cloned!(cloner, &[pubkey]); } @@ -75,7 +83,14 @@ async fn test_deleg_after_subscribe_case2() { .await; assert!(!updated); - chainlink.ensure_accounts(&[pubkey], None).await.unwrap(); + chainlink + .ensure_accounts( + &[pubkey], + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); assert_cloned_as_undelegated!(cloner, &[pubkey], slot, program_pubkey); assert_subscribed_without_delegation_record!(&chainlink, &[&pubkey]); } diff --git a/magicblock-chainlink/tests/08_subupdate-ordering.rs b/magicblock-chainlink/tests/08_subupdate-ordering.rs index b552cae03..bc7086030 100644 --- a/magicblock-chainlink/tests/08_subupdate-ordering.rs +++ b/magicblock-chainlink/tests/08_subupdate-ordering.rs @@ -1,5 +1,5 @@ use log::*; -use magicblock_chainlink::testing::init_logger; +use magicblock_chainlink::{testing::init_logger, AccountFetchOrigin}; use solana_account::{Account, ReadableAccount}; use solana_pubkey::Pubkey; use solana_sdk::clock::Slot; @@ -56,7 +56,14 @@ async fn test_subs_receive_out_of_order_updates() { .into(), ); - chainlink.ensure_accounts(&[pubkey], None).await.unwrap(); + chainlink + .ensure_accounts( + &[pubkey], + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); let acc = cloner .get_account(&pubkey) diff --git a/magicblock-chainlink/tests/basics.rs b/magicblock-chainlink/tests/basics.rs index 3d96286ae..7cd3dbacb 100644 --- a/magicblock-chainlink/tests/basics.rs +++ b/magicblock-chainlink/tests/basics.rs @@ -1,6 +1,7 @@ use magicblock_chainlink::{ assert_cloned_as_delegated, assert_cloned_as_undelegated, testing::{deleg::add_delegation_record_for, init_logger}, + AccountFetchOrigin, }; use solana_account::Account; use solana_pubkey::Pubkey; @@ -44,12 +45,26 @@ async fn test_remote_slot_of_accounts_read_from_bank() { assert_eq!(chainlink.fetch_count().unwrap(), 0); // 1. Read account first time which fetches it from chain - chainlink.ensure_accounts(&[pubkey], None).await.unwrap(); + chainlink + .ensure_accounts( + &[pubkey], + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); assert_cloned_as_undelegated!(cloner, &[pubkey], slot, owner); assert_eq!(chainlink.fetch_count().unwrap(), 1); // 2. Read account again which gets it from bank (without fetching again) - chainlink.ensure_accounts(&[pubkey], None).await.unwrap(); + chainlink + .ensure_accounts( + &[pubkey], + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); assert_cloned_as_undelegated!(cloner, &[pubkey], slot, owner); assert_eq!(chainlink.fetch_count().unwrap(), 1); } @@ -85,7 +100,14 @@ async fn test_remote_slot_of_ensure_accounts_from_bank() { assert_eq!(chainlink.fetch_count().unwrap(), 0); // 1. Ensure account first time which fetches it from chain - chainlink.ensure_accounts(&[pubkey], None).await.unwrap(); + chainlink + .ensure_accounts( + &[pubkey], + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); assert_cloned_as_delegated!(cloner, &[pubkey], slot, owner); // We fetch the account once then realize it is owned by the delegation record. @@ -93,7 +115,14 @@ async fn test_remote_slot_of_ensure_accounts_from_bank() { assert_eq!(chainlink.fetch_count().unwrap(), 3); // 2. Ensure account again which gets it from bank (without fetching again) - chainlink.ensure_accounts(&[pubkey], None).await.unwrap(); + chainlink + .ensure_accounts( + &[pubkey], + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await + .unwrap(); assert_cloned_as_delegated!(cloner, &[pubkey], slot, owner); // Since the account is already in the bank, we don't fetch it again assert_eq!(chainlink.fetch_count().unwrap(), 3); diff --git a/magicblock-chainlink/tests/utils/test_context.rs b/magicblock-chainlink/tests/utils/test_context.rs index 3e41702de..04a38ff66 100644 --- a/magicblock-chainlink/tests/utils/test_context.rs +++ b/magicblock-chainlink/tests/utils/test_context.rs @@ -21,7 +21,7 @@ use magicblock_chainlink::{ deleg::add_delegation_record_for, rpc_client_mock::{ChainRpcClientMock, ChainRpcClientMockBuilder}, }, - Chainlink, + AccountFetchOrigin, Chainlink, }; use solana_account::{Account, AccountSharedData}; use solana_pubkey::Pubkey; @@ -198,7 +198,13 @@ impl TestContext { &self, pubkey: &Pubkey, ) -> ChainlinkResult { - self.chainlink.ensure_accounts(&[*pubkey], None).await + self.chainlink + .ensure_accounts( + &[*pubkey], + None, + AccountFetchOrigin::GetMultipleAccounts, + ) + .await } /// Force undelegation of an account in the bank to mark it as such until diff --git a/magicblock-metrics/src/metrics/mod.rs b/magicblock-metrics/src/metrics/mod.rs index d6645da89..4603fe805 100644 --- a/magicblock-metrics/src/metrics/mod.rs +++ b/magicblock-metrics/src/metrics/mod.rs @@ -5,7 +5,9 @@ use prometheus::{ Histogram, HistogramOpts, HistogramVec, IntCounter, IntCounterVec, IntGauge, IntGaugeVec, Opts, Registry, }; -pub use types::{AccountClone, AccountCommit, LabelValue, Outcome}; +pub use types::{ + AccountClone, AccountCommit, AccountFetchOrigin, LabelValue, Outcome, +}; mod types; @@ -192,21 +194,23 @@ lazy_static::lazy_static! { ) .unwrap(); - pub static ref ACCOUNT_FETCHES_FOUND_COUNT: IntCounter = - IntCounter::new( + pub static ref ACCOUNT_FETCHES_FOUND_COUNT: IntCounterVec = IntCounterVec::new( + Opts::new( "account_fetches_found_count", - "Total number of network account fetches that \ - found an account", - ) - .unwrap(); + "Total number of network account fetches that found an account", + ), + &["origin"], + ) + .unwrap(); - pub static ref ACCOUNT_FETCHES_NOT_FOUND_COUNT: IntCounter = - IntCounter::new( + pub static ref ACCOUNT_FETCHES_NOT_FOUND_COUNT: IntCounterVec = IntCounterVec::new( + Opts::new( "account_fetches_not_found_count", - "Total number of network account fetches where \ - account was not found", - ) - .unwrap(); + "Total number of network account fetches where account was not found", + ), + &["origin"], + ) + .unwrap(); pub static ref UNDELEGATION_REQUESTED_COUNT: IntCounter = IntCounter::new( @@ -480,12 +484,19 @@ pub fn inc_account_fetches_failed(count: u64) { ACCOUNT_FETCHES_FAILED_COUNT.inc_by(count); } -pub fn inc_account_fetches_found(count: u64) { - ACCOUNT_FETCHES_FOUND_COUNT.inc_by(count); +pub fn inc_account_fetches_found(fetch_origin: AccountFetchOrigin, count: u64) { + ACCOUNT_FETCHES_FOUND_COUNT + .with_label_values(&[fetch_origin.value()]) + .inc_by(count); } -pub fn inc_account_fetches_not_found(count: u64) { - ACCOUNT_FETCHES_NOT_FOUND_COUNT.inc_by(count); +pub fn inc_account_fetches_not_found( + fetch_origin: AccountFetchOrigin, + count: u64, +) { + ACCOUNT_FETCHES_NOT_FOUND_COUNT + .with_label_values(&[fetch_origin.value()]) + .inc_by(count); } pub fn inc_undelegation_requested() { diff --git a/magicblock-metrics/src/metrics/types.rs b/magicblock-metrics/src/metrics/types.rs index f55252bc6..6ed4ae018 100644 --- a/magicblock-metrics/src/metrics/types.rs +++ b/magicblock-metrics/src/metrics/types.rs @@ -69,6 +69,36 @@ pub enum AccountCommit<'a> { CommitAndUndelegate { pubkey: &'a str, outcome: Outcome }, } +#[derive(Debug, Clone, Copy, PartialEq, Eq)] +pub enum AccountFetchOrigin { + GetMultipleAccounts, + GetAccount, + SendTransaction, +} + +impl AccountFetchOrigin { + pub fn as_str(&self) -> &str { + use AccountFetchOrigin::*; + match self { + GetMultipleAccounts => "get_multiple_accounts", + GetAccount => "get_account", + SendTransaction => "send_transaction", + } + } +} + +impl fmt::Display for AccountFetchOrigin { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", self.as_str()) + } +} + +impl LabelValue for AccountFetchOrigin { + fn value(&self) -> &str { + self.as_str() + } +} + pub trait LabelValue { fn value(&self) -> &str; } diff --git a/test-integration/Cargo.lock b/test-integration/Cargo.lock index 72d363a06..2ed59aef7 100644 --- a/test-integration/Cargo.lock +++ b/test-integration/Cargo.lock @@ -719,7 +719,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "115e54d64eb62cdebad391c19efc9dce4981c690c85a33a12199d99bb9546fee" dependencies = [ "borsh-derive 0.10.4", - "hashbrown 0.12.3", + "hashbrown 0.13.2", ] [[package]] @@ -2268,10 +2268,10 @@ dependencies = [ [[package]] name = "guinea" -version = "0.2.4" +version = "0.3.0" dependencies = [ "bincode", - "magicblock-magic-program-api 0.2.4", + "magicblock-magic-program-api 0.3.0", "serde", "solana-program", ] @@ -3454,7 +3454,7 @@ dependencies = [ [[package]] name = "magicblock-account-cloner" -version = "0.2.4" +version = "0.3.0" dependencies = [ "async-trait", "bincode", @@ -3465,7 +3465,7 @@ dependencies = [ "magicblock-config", "magicblock-core", "magicblock-ledger", - "magicblock-magic-program-api 0.2.4", + "magicblock-magic-program-api 0.3.0", "magicblock-program", "magicblock-rpc-client", "solana-sdk", @@ -3475,7 +3475,7 @@ dependencies = [ [[package]] name = "magicblock-accounts" -version = "0.2.4" +version = "0.3.0" dependencies = [ "async-trait", "futures-util", @@ -3488,7 +3488,7 @@ dependencies = [ "magicblock-core", "magicblock-delegation-program", "magicblock-ledger", - "magicblock-magic-program-api 0.2.4", + "magicblock-magic-program-api 0.3.0", "magicblock-metrics", "magicblock-processor", "magicblock-program", @@ -3503,7 +3503,7 @@ dependencies = [ [[package]] name = "magicblock-accounts-db" -version = "0.2.4" +version = "0.3.0" dependencies = [ "lmdb-rkv", "log", @@ -3520,7 +3520,7 @@ dependencies = [ [[package]] name = "magicblock-aperture" -version = "0.2.4" +version = "0.3.0" dependencies = [ "arc-swap", "base64 0.21.7", @@ -3569,7 +3569,7 @@ dependencies = [ [[package]] name = "magicblock-api" -version = "0.2.4" +version = "0.3.0" dependencies = [ "anyhow", "bincode", @@ -3590,7 +3590,7 @@ dependencies = [ "magicblock-core", "magicblock-delegation-program", "magicblock-ledger", - "magicblock-magic-program-api 0.2.4", + "magicblock-magic-program-api 0.3.0", "magicblock-metrics", "magicblock-processor", "magicblock-program", @@ -3613,7 +3613,7 @@ dependencies = [ [[package]] name = "magicblock-chainlink" -version = "0.2.4" +version = "0.3.0" dependencies = [ "arc-swap", "async-trait", @@ -3624,7 +3624,7 @@ dependencies = [ "lru 0.16.0", "magicblock-core", "magicblock-delegation-program", - "magicblock-magic-program-api 0.2.4", + "magicblock-magic-program-api 0.3.0", "magicblock-metrics", "serde_json", "solana-account", @@ -3648,7 +3648,7 @@ dependencies = [ [[package]] name = "magicblock-committor-program" -version = "0.2.4" +version = "0.3.0" dependencies = [ "borsh 1.5.7", "borsh-derive 1.5.7", @@ -3662,7 +3662,7 @@ dependencies = [ [[package]] name = "magicblock-committor-service" -version = "0.2.4" +version = "0.3.0" dependencies = [ "async-trait", "base64 0.21.7", @@ -3694,7 +3694,7 @@ dependencies = [ [[package]] name = "magicblock-config" -version = "0.2.4" +version = "0.3.0" dependencies = [ "bs58", "clap 4.5.41", @@ -3713,11 +3713,11 @@ dependencies = [ [[package]] name = "magicblock-config-helpers" -version = "0.2.4" +version = "0.3.0" [[package]] name = "magicblock-config-macro" -version = "0.2.4" +version = "0.3.0" dependencies = [ "clap 4.5.41", "convert_case 0.8.0", @@ -3729,11 +3729,11 @@ dependencies = [ [[package]] name = "magicblock-core" -version = "0.2.4" +version = "0.3.0" dependencies = [ "bincode", "flume", - "magicblock-magic-program-api 0.2.4", + "magicblock-magic-program-api 0.3.0", "serde", "solana-account", "solana-account-decoder", @@ -3770,7 +3770,7 @@ dependencies = [ [[package]] name = "magicblock-ledger" -version = "0.2.4" +version = "0.3.0" dependencies = [ "arc-swap", "bincode", @@ -3790,7 +3790,7 @@ dependencies = [ "solana-measure", "solana-metrics", "solana-sdk", - "solana-storage-proto 0.2.4", + "solana-storage-proto 0.3.0", "solana-svm 2.2.1 (git+https://github.com/magicblock-labs/magicblock-svm.git?rev=e480fa2)", "solana-timings", "solana-transaction-status", @@ -3812,7 +3812,7 @@ dependencies = [ [[package]] name = "magicblock-magic-program-api" -version = "0.2.4" +version = "0.3.0" dependencies = [ "bincode", "serde", @@ -3821,7 +3821,7 @@ dependencies = [ [[package]] name = "magicblock-metrics" -version = "0.2.4" +version = "0.3.0" dependencies = [ "http-body-util", "hyper 1.6.0", @@ -3835,7 +3835,7 @@ dependencies = [ [[package]] name = "magicblock-processor" -version = "0.2.4" +version = "0.3.0" dependencies = [ "bincode", "log", @@ -3869,12 +3869,12 @@ dependencies = [ [[package]] name = "magicblock-program" -version = "0.2.4" +version = "0.3.0" dependencies = [ "bincode", "lazy_static", "magicblock-core", - "magicblock-magic-program-api 0.2.4", + "magicblock-magic-program-api 0.3.0", "magicblock-metrics", "num-derive", "num-traits", @@ -3887,7 +3887,7 @@ dependencies = [ [[package]] name = "magicblock-rpc-client" -version = "0.2.4" +version = "0.3.0" dependencies = [ "log", "solana-rpc-client", @@ -3901,7 +3901,7 @@ dependencies = [ [[package]] name = "magicblock-table-mania" -version = "0.2.4" +version = "0.3.0" dependencies = [ "ed25519-dalek", "log", @@ -3919,7 +3919,7 @@ dependencies = [ [[package]] name = "magicblock-task-scheduler" -version = "0.2.4" +version = "0.3.0" dependencies = [ "bincode", "chrono", @@ -3944,7 +3944,7 @@ dependencies = [ [[package]] name = "magicblock-validator-admin" -version = "0.2.4" +version = "0.3.0" dependencies = [ "anyhow", "log", @@ -3962,7 +3962,7 @@ dependencies = [ [[package]] name = "magicblock-version" -version = "0.2.4" +version = "0.3.0" dependencies = [ "git-version", "rustc_version", @@ -4851,7 +4851,7 @@ dependencies = [ "bincode", "borsh 1.5.7", "ephemeral-rollups-sdk", - "magicblock-magic-program-api 0.2.4", + "magicblock-magic-program-api 0.3.0", "serde", "solana-program", ] @@ -5831,7 +5831,7 @@ dependencies = [ "integration-test-tools", "log", "magicblock-core", - "magicblock-magic-program-api 0.2.4", + "magicblock-magic-program-api 0.3.0", "program-schedulecommit", "schedulecommit-client", "solana-program", @@ -5847,7 +5847,7 @@ version = "0.0.0" dependencies = [ "integration-test-tools", "magicblock-core", - "magicblock-magic-program-api 0.2.4", + "magicblock-magic-program-api 0.3.0", "program-schedulecommit", "program-schedulecommit-security", "schedulecommit-client", @@ -8988,7 +8988,7 @@ dependencies = [ [[package]] name = "solana-storage-proto" -version = "0.2.4" +version = "0.3.0" dependencies = [ "bincode", "bs58", @@ -10489,7 +10489,7 @@ dependencies = [ [[package]] name = "test-kit" -version = "0.2.4" +version = "0.3.0" dependencies = [ "env_logger 0.11.8", "guinea", diff --git a/test-integration/test-chainlink/src/test_context.rs b/test-integration/test-chainlink/src/test_context.rs index a90d3d986..498f85b8b 100644 --- a/test-integration/test-chainlink/src/test_context.rs +++ b/test-integration/test-chainlink/src/test_context.rs @@ -202,7 +202,13 @@ impl TestContext { &self, pubkey: &Pubkey, ) -> ChainlinkResult { - self.chainlink.ensure_accounts(&[*pubkey], None).await + self.chainlink + .ensure_accounts( + &[*pubkey], + None, + magicblock_chainlink::AccountFetchOrigin::GetAccount, + ) + .await } /// Force undelegation of an account in the bank to mark it as such until diff --git a/test-integration/test-chainlink/tests/ix_01_ensure-accounts.rs b/test-integration/test-chainlink/tests/ix_01_ensure-accounts.rs index ef58db8fe..e6b9d9e83 100644 --- a/test-integration/test-chainlink/tests/ix_01_ensure-accounts.rs +++ b/test-integration/test-chainlink/tests/ix_01_ensure-accounts.rs @@ -4,6 +4,7 @@ use magicblock_chainlink::{ assert_not_cloned, assert_not_found, assert_not_subscribed, assert_subscribed_without_delegation_record, testing::{init_logger, utils::random_pubkey}, + AccountFetchOrigin, }; use solana_sdk::{signature::Keypair, signer::Signer}; use test_chainlink::ixtest_context::IxtestContext; @@ -16,7 +17,11 @@ async fn ixtest_write_non_existing_account() { let pubkey = random_pubkey(); let pubkeys = [pubkey]; - let res = ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + let res = ctx + .chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); debug!("res: {res:?}"); assert_not_found!(res, &pubkeys); @@ -37,7 +42,11 @@ async fn ixtest_write_existing_account_undelegated() { ctx.init_counter(&counter_auth).await; let pubkeys = [counter_auth.pubkey()]; - let res = ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + let res = ctx + .chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); debug!("res: {res:?}"); assert_cloned_as_undelegated!(ctx.cloner, &pubkeys); @@ -63,7 +72,11 @@ async fn ixtest_write_existing_account_valid_delegation_record() { let deleg_record_pubkey = ctx.delegation_record_pubkey(&counter_pda); let pubkeys = [counter_pda]; - let res = ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + let res = ctx + .chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); debug!("res: {res:?}"); let account = ctx.cloner.get_account(&counter_pda).unwrap(); diff --git a/test-integration/test-chainlink/tests/ix_03_deleg_after_sub.rs b/test-integration/test-chainlink/tests/ix_03_deleg_after_sub.rs index 73577666d..92d3e3e8a 100644 --- a/test-integration/test-chainlink/tests/ix_03_deleg_after_sub.rs +++ b/test-integration/test-chainlink/tests/ix_03_deleg_after_sub.rs @@ -3,6 +3,7 @@ use magicblock_chainlink::{ assert_cloned_as_delegated, assert_cloned_as_undelegated, assert_not_cloned, assert_not_found, assert_not_subscribed, assert_subscribed_without_delegation_record, testing::init_logger, + AccountFetchOrigin, }; use solana_sdk::{signature::Keypair, signer::Signer}; use test_chainlink::ixtest_context::IxtestContext; @@ -20,7 +21,11 @@ async fn ixtest_deleg_after_subscribe_case2() { // 1. Initially the account does not exist { info!("1. Initially the account does not exist"); - let res = ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + let res = ctx + .chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); assert_not_found!(res, &pubkeys); assert_not_cloned!(ctx.cloner, &pubkeys); @@ -32,7 +37,10 @@ async fn ixtest_deleg_after_subscribe_case2() { info!("2. Create account owned by program_flexi_counter"); ctx.init_counter(&counter_auth).await; - ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + ctx.chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); // Assert cloned account state matches the remote account and slot let account = ctx.cloner.get_account(&counter_pda).unwrap(); @@ -53,7 +61,10 @@ async fn ixtest_deleg_after_subscribe_case2() { let deleg_record_pubkey = ctx.delegation_record_pubkey(&counter_pda); - ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + ctx.chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); let account = ctx.cloner.get_account(&counter_pda).unwrap(); assert_cloned_as_delegated!( diff --git a/test-integration/test-chainlink/tests/ix_06_redeleg_us_separate_slots.rs b/test-integration/test-chainlink/tests/ix_06_redeleg_us_separate_slots.rs index f31017dac..2f774db3f 100644 --- a/test-integration/test-chainlink/tests/ix_06_redeleg_us_separate_slots.rs +++ b/test-integration/test-chainlink/tests/ix_06_redeleg_us_separate_slots.rs @@ -7,7 +7,7 @@ use log::*; use magicblock_chainlink::{ assert_cloned_as_delegated_with_retries, assert_cloned_as_undelegated, assert_not_subscribed, assert_subscribed_without_delegation_record, - testing::init_logger, + testing::init_logger, AccountFetchOrigin, }; use solana_sdk::{signature::Keypair, signer::Signer}; use test_chainlink::{ixtest_context::IxtestContext, sleep_ms}; @@ -33,7 +33,10 @@ async fn ixtest_undelegate_redelegate_to_us_in_separate_slots() { { info!("1. Account delegated to us"); - ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + ctx.chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); sleep_ms(1_500).await; // Account should be cloned as delegated diff --git a/test-integration/test-chainlink/tests/ix_07_redeleg_us_same_slot.rs b/test-integration/test-chainlink/tests/ix_07_redeleg_us_same_slot.rs index 984d1c3d1..672c621af 100644 --- a/test-integration/test-chainlink/tests/ix_07_redeleg_us_same_slot.rs +++ b/test-integration/test-chainlink/tests/ix_07_redeleg_us_same_slot.rs @@ -7,6 +7,7 @@ use log::*; use magicblock_chainlink::{ assert_cloned_as_delegated, assert_not_subscribed, testing::{init_logger, utils::sleep_ms}, + AccountFetchOrigin, }; use solana_sdk::{signature::Keypair, signer::Signer}; use test_chainlink::ixtest_context::IxtestContext; @@ -32,7 +33,10 @@ async fn ixtest_undelegate_redelegate_to_us_in_same_slot() { { info!("1. Account delegated to us"); - ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + ctx.chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); sleep_ms(1_500).await; // Account should be cloned as delegated diff --git a/test-integration/test-chainlink/tests/ix_exceed_capacity.rs b/test-integration/test-chainlink/tests/ix_exceed_capacity.rs index cc76a94c4..8c692efbb 100644 --- a/test-integration/test-chainlink/tests/ix_exceed_capacity.rs +++ b/test-integration/test-chainlink/tests/ix_exceed_capacity.rs @@ -3,6 +3,7 @@ use magicblock_chainlink::{ config::{ChainlinkConfig, LifecycleMode}, remote_account_provider::config::RemoteAccountProviderConfig, testing::{init_logger, utils::random_pubkeys}, + AccountFetchOrigin, }; use test_chainlink::ixtest_context::IxtestContext; @@ -41,7 +42,10 @@ async fn ixtest_read_multiple_accounts_not_exceeding_capacity() { let (ctx, pubkeys) = setup(subscribed_accounts_lru_capacity, pubkeys_len).await; - ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + ctx.chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); // Verify all accounts are present in the cache for pubkey in pubkeys { @@ -71,11 +75,11 @@ async fn ixtest_read_multiple_accounts_exceeding_capacity() { // will be removed, but since they haven't been added yet that does nothing and // they get still added later right after. Therefore here we go in steps: ctx.chainlink - .ensure_accounts(&pubkeys[0..4], None) + .ensure_accounts(&pubkeys[0..4], None, AccountFetchOrigin::GetAccount) .await .unwrap(); ctx.chainlink - .ensure_accounts(&pubkeys[4..8], None) + .ensure_accounts(&pubkeys[4..8], None, AccountFetchOrigin::GetAccount) .await .unwrap(); diff --git a/test-integration/test-chainlink/tests/ix_full_scenarios.rs b/test-integration/test-chainlink/tests/ix_full_scenarios.rs index eeb836125..e7dc541c0 100644 --- a/test-integration/test-chainlink/tests/ix_full_scenarios.rs +++ b/test-integration/test-chainlink/tests/ix_full_scenarios.rs @@ -6,6 +6,7 @@ use magicblock_chainlink::{ assert_subscribed_without_loaderv3_program_data_account, remote_account_provider::program_account::RemoteProgramLoader, testing::{init_logger, utils::random_pubkey}, + AccountFetchOrigin, }; use solana_loader_v4_interface::state::LoaderV4Status; use solana_pubkey::Pubkey; @@ -161,8 +162,11 @@ async fn ixtest_accounts_for_tx_2_delegated_3_readonly_3_programs_one_native() { // Initially the new_pubkey does not exist on chain so it will be returned as None { let (fetched_pubkeys, fetched_strs) = { - let fetched_accounts = - ctx.chainlink.fetch_accounts(&all_pubkeys).await.unwrap(); + let fetched_accounts = ctx + .chainlink + .fetch_accounts(&all_pubkeys, AccountFetchOrigin::GetAccount) + .await + .unwrap(); let mut fetched_pubkeys = all_pubkeys .iter() .zip(fetched_accounts.iter()) @@ -206,8 +210,11 @@ async fn ixtest_accounts_for_tx_2_delegated_3_readonly_3_programs_one_native() { sleep_ms(500).await; let (fetched_pubkeys, fetched_strs) = { - let fetched_accounts = - ctx.chainlink.fetch_accounts(&all_pubkeys).await.unwrap(); + let fetched_accounts = ctx + .chainlink + .fetch_accounts(&all_pubkeys, AccountFetchOrigin::GetAccount) + .await + .unwrap(); let mut fetched_pubkeys = all_pubkeys .iter() .zip(fetched_accounts.iter()) diff --git a/test-integration/test-chainlink/tests/ix_programs.rs b/test-integration/test-chainlink/tests/ix_programs.rs index 93c255e65..40032c679 100644 --- a/test-integration/test-chainlink/tests/ix_programs.rs +++ b/test-integration/test-chainlink/tests/ix_programs.rs @@ -8,6 +8,7 @@ use magicblock_chainlink::{ LoadedProgram, ProgramAccountResolver, RemoteProgramLoader, }, testing::init_logger, + AccountFetchOrigin, }; use program_mini::common::IdlType; use solana_loader_v4_interface::state::LoaderV4Status; @@ -435,7 +436,10 @@ async fn ixtest_clone_memo_v1_loader_program() { let pubkeys = [MEMOV1]; - ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + ctx.chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); debug!("{}", ctx.cloner); assert_loaded_program_with_size!( @@ -460,7 +464,10 @@ async fn ixtest_clone_memo_v2_loader_program() { let pubkeys = [MEMOV2]; - ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + ctx.chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); debug!("{}", ctx.cloner); assert_loaded_program_with_size!( @@ -486,7 +493,10 @@ async fn ixtest_clone_mini_v2_loader_program() { let pubkeys = [MINIV2]; - ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + ctx.chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); debug!("{}", ctx.cloner); assert_loaded_program_with_size!( @@ -510,7 +520,10 @@ async fn ixtest_clone_mini_v3_loader_program() { let ctx = IxtestContext::init().await; let pubkeys = [MINIV3]; - ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + ctx.chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); debug!("{}", ctx.cloner); assert_loaded_program_with_size!( @@ -559,7 +572,10 @@ async fn ixtest_clone_mini_v4_loader_program() { let pubkeys = [prog_kp.pubkey()]; - ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + ctx.chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); debug!("{}", ctx.cloner); assert_loaded_program_with_size!( @@ -584,7 +600,10 @@ async fn ixtest_clone_multiple_programs_v1_v2_v3() { let pubkeys = [MEMOV1, MEMOV2, MINIV3]; - ctx.chainlink.ensure_accounts(&pubkeys, None).await.unwrap(); + ctx.chainlink + .ensure_accounts(&pubkeys, None, AccountFetchOrigin::GetAccount) + .await + .unwrap(); debug!("{}", ctx.cloner); diff --git a/test-integration/test-chainlink/tests/ix_remote_account_provider.rs b/test-integration/test-chainlink/tests/ix_remote_account_provider.rs index cdd5e6ff8..55c75e574 100644 --- a/test-integration/test-chainlink/tests/ix_remote_account_provider.rs +++ b/test-integration/test-chainlink/tests/ix_remote_account_provider.rs @@ -15,6 +15,7 @@ use magicblock_chainlink::{ get_remote_account_update_sources, init_logger, random_pubkey, sleep_ms, PUBSUB_URL, RPC_URL, }, + AccountFetchOrigin, }; use solana_rpc_client_api::{ client_error::ErrorKind, config::RpcAccountInfoConfig, request::RpcError, @@ -63,7 +64,10 @@ async fn ixtest_get_non_existing_account() { init_remote_account_provider().await; let pubkey = random_pubkey(); - let remote_account = remote_account_provider.try_get(pubkey).await.unwrap(); + let remote_account = remote_account_provider + .try_get(pubkey, AccountFetchOrigin::GetAccount) + .await + .unwrap(); assert!(!remote_account.is_found()); } @@ -115,8 +119,10 @@ async fn ixtest_get_existing_account_for_valid_slot() { { // Fetching immediately does not return the account yet - let remote_account = - remote_account_provider.try_get(pubkey).await.unwrap(); + let remote_account = remote_account_provider + .try_get(pubkey, AccountFetchOrigin::GetAccount) + .await + .unwrap(); assert!(!remote_account.is_found()); } @@ -132,8 +138,10 @@ async fn ixtest_get_existing_account_for_valid_slot() { { // After waiting for a bit the subscription update came in let cs = current_slot(rpc_client).await; - let remote_account = - remote_account_provider.try_get(pubkey).await.unwrap(); + let remote_account = remote_account_provider + .try_get(pubkey, AccountFetchOrigin::GetAccount) + .await + .unwrap(); assert!(remote_account.is_found()); assert!(remote_account.slot() >= cs); assert_eq!(remote_account.fresh_lamports().unwrap(), 2_000_000); @@ -159,7 +167,7 @@ async fn ixtest_get_multiple_accounts_for_valid_slot() { { let remote_accounts = remote_account_provider - .try_get_multi(&all_pubkeys, None) + .try_get_multi(&all_pubkeys, None, AccountFetchOrigin::GetAccount) .await .unwrap(); @@ -186,7 +194,7 @@ async fn ixtest_get_multiple_accounts_for_valid_slot() { { // Fetching after a bit let remote_accounts = remote_account_provider - .try_get_multi(&all_pubkeys, None) + .try_get_multi(&all_pubkeys, None, AccountFetchOrigin::GetAccount) .await .unwrap(); let remote_lamports = @@ -215,7 +223,7 @@ async fn ixtest_get_multiple_accounts_for_valid_slot() { { // Fetching after a bit let remote_accounts = remote_account_provider - .try_get_multi(&all_pubkeys, None) + .try_get_multi(&all_pubkeys, None, AccountFetchOrigin::GetAccount) .await .unwrap(); let remote_lamports =