1use solana_keypair::Keypair;
2use solana_pubkey::Pubkey;
3
4use crate::rpc::{Rpc, RpcError};
5
6#[derive(Debug, Clone, PartialEq)]
7pub struct FeeConfig {
8 pub state_merkle_tree_rollover: u64,
9 pub address_queue_rollover: u64,
10 pub network_fee: u64,
14 pub address_network_fee: u64,
15 pub solana_network_fee: i64,
16}
17
18impl Default for FeeConfig {
19 fn default() -> Self {
20 Self {
21 state_merkle_tree_rollover: 300,
23 address_queue_rollover: 392,
24 network_fee: 5000,
28 address_network_fee: 5000,
29 solana_network_fee: 5000,
30 }
31 }
32}
33
34impl FeeConfig {
35 pub fn test_batched() -> Self {
36 Self {
37 state_merkle_tree_rollover: 1,
39 address_queue_rollover: 392, network_fee: 5000,
41 address_network_fee: 10000,
42 solana_network_fee: 5000,
43 }
44 }
45}
46
47#[derive(Debug, Clone, PartialEq)]
48pub struct TransactionParams {
49 pub v1_input_compressed_accounts: u8,
50 pub v2_input_compressed_accounts: bool,
51 pub num_output_compressed_accounts: u8,
52 pub num_new_addresses: u8,
53 pub compress: i64,
54 pub fee_config: FeeConfig,
55}
56
57pub async fn assert_transaction_params(
58 rpc: &mut impl Rpc,
59 payer: &Pubkey,
60 signers: &[&Keypair],
61 pre_balance: u64,
62 params: Option<TransactionParams>,
63) -> Result<(), RpcError> {
64 if let Some(transaction_params) = params {
65 let mut deduped_signers = signers.to_vec();
66 deduped_signers.dedup();
67 let post_balance = rpc.get_account(*payer).await?.unwrap().lamports;
68
69 let mut network_fee: i64 = 0;
71
72 if transaction_params.v1_input_compressed_accounts != 0 {
74 network_fee += transaction_params.fee_config.network_fee as i64
75 * transaction_params.v1_input_compressed_accounts as i64;
76 } else if transaction_params.v2_input_compressed_accounts {
77 network_fee += transaction_params.fee_config.network_fee as i64;
78 }
79 if transaction_params.num_new_addresses != 0 {
81 network_fee += transaction_params.fee_config.address_network_fee as i64
82 * transaction_params.num_new_addresses as i64;
83 }
84 let expected_post_balance = pre_balance as i64
85 - i64::from(transaction_params.num_new_addresses)
86 * transaction_params.fee_config.address_queue_rollover as i64
87 - i64::from(transaction_params.num_output_compressed_accounts)
88 * transaction_params.fee_config.state_merkle_tree_rollover as i64
89 - transaction_params.compress
90 - transaction_params.fee_config.solana_network_fee * deduped_signers.len() as i64
91 - network_fee;
92
93 if post_balance as i64 != expected_post_balance {
94 println!("transaction_params: {:?}", transaction_params);
95 println!("pre_balance: {}", pre_balance);
96 println!("post_balance: {}", post_balance);
97 println!("expected post_balance: {}", expected_post_balance);
98 println!(
99 "diff post_balance: {}",
100 post_balance as i64 - expected_post_balance
101 );
102 println!(
103 "rollover fee: {}",
104 transaction_params.fee_config.state_merkle_tree_rollover
105 );
106 println!(
107 "address_network_fee: {}",
108 transaction_params.fee_config.address_network_fee
109 );
110 println!("network_fee: {}", network_fee);
111 println!("num signers {}", deduped_signers.len());
112 println!(
113 "transaction_params.fee_config {:?}",
114 transaction_params.fee_config
115 );
116 return Err(RpcError::CustomError("Transaction fee error.".to_string()));
117 }
118 }
119 Ok(())
120}