From 225c5f08c43c15ea7319d64dd1b1ea8580a838a5 Mon Sep 17 00:00:00 2001 From: Michael Vines Date: Mon, 10 Jun 2024 08:53:32 -0700 Subject: [PATCH] sys-lend: add priority fees metric --- src/bin/sys-lend.rs | 59 ++++++++++++++++++++++++++++++------------- src/lib.rs | 23 +++++++++-------- src/main.rs | 40 +++++++++++++++++++++-------- src/priority_fee.rs | 4 +-- src/stake_spreader.rs | 8 ++++-- 5 files changed, 92 insertions(+), 42 deletions(-) diff --git a/src/bin/sys-lend.rs b/src/bin/sys-lend.rs index 939fb07..69619c0 100644 --- a/src/bin/sys-lend.rs +++ b/src/bin/sys-lend.rs @@ -16,7 +16,7 @@ use { commitment_config::CommitmentConfig, instruction::{AccountMeta, Instruction}, message::{self, Message, VersionedMessage}, - native_token::sol_to_lamports, + native_token::{lamports_to_sol, sol_to_lamports}, program_pack::Pack, pubkey, pubkey::Pubkey, @@ -93,7 +93,7 @@ mod dp { pub fn supply_balance( pool: &str, address: &Pubkey, - maybe_token: Token, + maybe_token: MaybeToken, ui_amount: f64, ) -> metrics::Point { metrics::Point::new("sys_lend::supply_balance") @@ -103,7 +103,7 @@ mod dp { .field("amount", ui_amount) } - pub fn supply_apy(pool: &str, maybe_token: Token, apy_bps: u64) -> metrics::Point { + pub fn supply_apy(pool: &str, maybe_token: MaybeToken, apy_bps: u64) -> metrics::Point { metrics::Point::new("sys_lend::supply_apy") .tag("pool", pool) .tag("token", maybe_token.name()) @@ -113,7 +113,7 @@ mod dp { pub fn principal_balance_change( pool: &str, address: &Pubkey, - maybe_token: Token, + maybe_token: MaybeToken, ui_amount: f64, ) -> metrics::Point { metrics::Point::new("sys_lend::principal_balance_change") @@ -122,6 +122,19 @@ mod dp { .tag("token", maybe_token.name()) .field("amount", ui_amount) } + + pub fn priority_fee( + command: &str, + address: &Pubkey, + maybe_token: MaybeToken, + priority_fee: f64, + ) -> metrics::Point { + metrics::Point::new("sys_lend::priority_fee") + .tag("command", command) + .tag("address", metrics::dp::pubkey_to_value(address)) + .tag("token", maybe_token.name()) + .field("priority_fee", priority_fee) + } } fn is_token_supported(token: &Token, pools: &[String]) -> Result<(), Box> { @@ -742,7 +755,7 @@ async fn main() -> Result<(), Box> { if !raw { notifier.send(&msg).await; } - metrics::push(dp::supply_apy(&pool, token, apy_as_bps)).await; + metrics::push(dp::supply_apy(&pool, maybe_token, apy_as_bps)).await; println!("{msg}"); } } @@ -793,7 +806,7 @@ async fn main() -> Result<(), Box> { metrics::push(dp::supply_balance( pool, &address, - token, + maybe_token, token.ui_amount(amount), )) .await; @@ -1426,10 +1439,10 @@ async fn main() -> Result<(), Box> { let (recent_blockhash, last_valid_block_height) = rpc_client.get_latest_blockhash_with_commitment(rpc_client.commitment())?; - let transaction = { + let (transaction, priority_fee) = { let mut instructions = instructions; - apply_priority_fee( + let priority_fee = apply_priority_fee( rpc_client, &mut instructions, required_compute_units, @@ -1442,25 +1455,37 @@ async fn main() -> Result<(), Box> { &address_lookup_table_accounts, recent_blockhash, )?; - VersionedTransaction::try_new(VersionedMessage::V0(message), &vec![signer])? + ( + VersionedTransaction::try_new(VersionedMessage::V0(message), &vec![signer])?, + priority_fee, + ) }; let signature = transaction.signatures[0]; - if !send_transaction_until_expired(&rpc_clients, &transaction, last_valid_block_height) - { + let transaction_confirmed = + send_transaction_until_expired(&rpc_clients, &transaction, last_valid_block_height); + if transaction_confirmed.is_some() { + metrics::push(dp::priority_fee( + &format!("{cmd:?}").to_lowercase(), + &address, + maybe_token, + lamports_to_sol(priority_fee), + )) + .await; + } + if !transaction_confirmed.unwrap_or_default() { let msg = format!("Transaction failed: {signature}"); notifier.send(&msg).await; return Err(msg.into()); - } else { - println!("Transaction confirmed: {signature}"); } + println!("Transaction confirmed: {signature}"); match cmd { Command::Deposit => { metrics::push(dp::principal_balance_change( deposit_pool, &address, - token, + maybe_token, token.ui_amount(amount), )) .await; @@ -1469,7 +1494,7 @@ async fn main() -> Result<(), Box> { metrics::push(dp::principal_balance_change( withdraw_pool, &address, - token, + maybe_token, -token.ui_amount(amount), )) .await; @@ -1478,14 +1503,14 @@ async fn main() -> Result<(), Box> { metrics::push(dp::principal_balance_change( withdraw_pool, &address, - token, + maybe_token, -token.ui_amount(amount), )) .await; metrics::push(dp::principal_balance_change( deposit_pool, &address, - token, + maybe_token, token.ui_amount(amount), )) .await; diff --git a/src/lib.rs b/src/lib.rs index efd1ea4..4f15732 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -82,9 +82,9 @@ pub fn send_transaction_until_expired( rpc_clients: &RpcClients, transaction: &impl SerializableTransaction, last_valid_block_height: u64, -) -> bool { +) -> Option { send_transaction_until_expired_with_slot(rpc_clients, transaction, last_valid_block_height) - .is_some() + .map(|(_context_slot, success)| success) } // Same as `send_transaction_until_expired` but on success returns a `Slot` that the transaction @@ -93,7 +93,7 @@ fn send_transaction_until_expired_with_slot( rpc_clients: &RpcClients, transaction: &impl SerializableTransaction, last_valid_block_height: u64, -) -> Option { +) -> Option<(Slot, bool)> { let mut last_send_attempt = None; let config = RpcSendTransactionConfig { @@ -130,13 +130,16 @@ fn send_transaction_until_expired_with_slot( Ok(rpc_response::Response { context, value }) => { let confirmation_context_slot = context.slot; if let Some(ref transaction_status) = value[0] { - match transaction_status.err { - None => return Some(confirmation_context_slot), - Some(ref err) => { - println!("Transaction failed: {err}"); - return None; - } - } + return Some(( + confirmation_context_slot, + match transaction_status.err { + None => true, + Some(ref err) => { + println!("Transaction failed: {err}"); + false + } + }, + )); } else { match rpc_clients.default().get_epoch_info() { Ok(epoch_info) => { diff --git a/src/main.rs b/src/main.rs index 96998f8..359db91 100644 --- a/src/main.rs +++ b/src/main.rs @@ -657,7 +657,9 @@ async fn process_exchange_deposit( lot_selection_method, lot_numbers, )?; - if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) { + if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) + .unwrap_or_default() + { return Err("Deposit failed".into()); } Ok(()) @@ -1233,7 +1235,9 @@ async fn process_jup_swap( lot_selection_method, )?; - if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) { + if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) + .unwrap_or_default() + { db.cancel_swap(signature)?; return Err("Swap failed".into()); } @@ -1364,7 +1368,7 @@ async fn process_tulip_deposit( lot_selection_method, )?; - if !send_transaction_until_expired(rpc_client, &transaction, last_valid_block_height) { + if !send_transaction_until_expired(rpc_client, &transaction, last_valid_block_height).unwrap_or_default() { db.cancel_swap(signature).expect("cancel_swap"); return Err("Swap failed".into()); } @@ -1460,7 +1464,7 @@ async fn process_tulip_withdraw( lot_selection_method, )?; - if !send_transaction_until_expired(rpc_client, &transaction, last_valid_block_height) { + if !send_transaction_until_expired(rpc_client, &transaction, last_valid_block_height).unwrap_or_default() { db.cancel_swap(signature).expect("cancel_swap"); return Err("Swap failed".into()); } @@ -3058,7 +3062,9 @@ async fn process_account_merge( None, )?; - if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) { + if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) + .unwrap_or_default() + { db.cancel_transfer(signature)?; return Err("Merge failed".into()); } @@ -3404,7 +3410,9 @@ async fn process_account_sweep( )?; if let Some(transaction) = maybe_transaction { - if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) { + if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) + .unwrap_or_default() + { db.cancel_transfer(signature)?; if let Some((transitory_stake_account, ..)) = via_transitory_stake.as_ref() { db.remove_transitory_sweep_stake_address(transitory_stake_account.pubkey())?; @@ -3544,7 +3552,9 @@ async fn process_account_split( lot_numbers, )?; - if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) { + if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) + .unwrap_or_default() + { db.cancel_transfer(signature)?; db.remove_account(into_keypair.pubkey(), MaybeToken::SOL())?; return Err("Split failed".into()); @@ -3658,7 +3668,9 @@ async fn process_account_redelegate( None, )?; - if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) { + if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) + .unwrap_or_default() + { db.cancel_transfer(signature)?; db.remove_account(into_keypair.pubkey(), MaybeToken::SOL())?; return Err("Redelegate failed".into()); @@ -3997,7 +4009,9 @@ async fn process_account_wrap( lot_numbers, )?; - if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) { + if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) + .unwrap_or_default() + { db.cancel_transfer(signature)?; return Err("Wrap failed".into()); } @@ -4096,7 +4110,9 @@ async fn process_account_unwrap( lot_numbers, )?; - if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) { + if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) + .unwrap_or_default() + { db.cancel_transfer(signature)?; return Err("Wrap failed".into()); } @@ -4295,7 +4311,9 @@ async fn process_account_sync_sweep( None, )?; - if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) { + if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) + .unwrap_or_default() + { db.cancel_transfer(signature)?; return Err("Merge failed".into()); } diff --git a/src/priority_fee.rs b/src/priority_fee.rs index 26635cb..5ca4b65 100644 --- a/src/priority_fee.rs +++ b/src/priority_fee.rs @@ -103,7 +103,7 @@ pub fn apply_priority_fee( instructions: &mut Vec, compute_unit_limit: u32, priority_fee: PriorityFee, -) -> Result<(), Box> { +) -> Result> { let compute_budget = match priority_fee { PriorityFee::Exact { lamports } => ComputeBudget::new(compute_unit_limit, lamports), PriorityFee::Auto { @@ -187,5 +187,5 @@ pub fn apply_priority_fee( ), ); - Ok(()) + Ok(compute_budget.priority_fee_lamports()) } diff --git a/src/stake_spreader.rs b/src/stake_spreader.rs index 5c7ccf4..c356fdd 100644 --- a/src/stake_spreader.rs +++ b/src/stake_spreader.rs @@ -395,7 +395,9 @@ pub async fn run( None, )?; - if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) { + if !send_transaction_until_expired(rpc_clients, &transaction, last_valid_block_height) + .unwrap_or_default() + { db.cancel_transfer(signature)?; eprintln!("Merge failed"); } else { @@ -598,7 +600,9 @@ pub async fn run( rpc_clients, &transaction, last_valid_block_height, - ) { + ) + .unwrap_or_default() + { eprintln!("Delegation failed"); transaction_failures += 1; }