1use crate::{TestRewarder, quarry_mine, quarry_mint_wrapper};
18use anyhow::Result;
19use solana_sdk::pubkey::Pubkey;
20use solana_sdk::signature::{Keypair, Signer};
21use std::fmt;
22use testsvm::prelude::*;
23
24#[derive(Debug)]
26pub struct TestQuarry {
27 pub label: String,
28 pub quarry: AccountRef<quarry_mine::accounts::Quarry>,
29 pub rewarder: Pubkey,
30 pub staked_token_mint: AccountRef<anchor_spl::token::Mint>,
31}
32
33impl TestQuarry {
34 pub fn fetch_quarry(&self, env: &TestSVM) -> Result<quarry_mine::accounts::Quarry> {
36 self.quarry.load(env)
37 }
38
39 pub fn create_miner(
41 &self,
42 env: &mut TestSVM,
43 label: &str,
44 user: &Keypair,
45 ) -> Result<(
46 AccountRef<quarry_mine::accounts::Miner>,
47 AccountRef<anchor_spl::token::TokenAccount>,
48 )> {
49 let miner = env.get_pda(
50 &format!("miner_{label}"),
51 &[b"Miner", self.quarry.key.as_ref(), user.pubkey().as_ref()],
52 quarry_mine::ID,
53 )?;
54
55 let (create_vault_ix, miner_vault) = env.create_ata_ix(
57 &format!("miner_vault_{label}"),
58 &miner.key,
59 &self.staked_token_mint.key,
60 )?;
61 env.execute_ixs(&[create_vault_ix])?;
62
63 let create_miner_ix = anchor_instruction(
64 quarry_mine::ID,
65 quarry_mine::client::accounts::CreateMinerV2 {
66 quarry: self.quarry.key,
67 rewarder: self.rewarder,
68 miner: miner.key,
69 authority: user.pubkey(),
70 payer: env.default_fee_payer(),
71 token_mint: self.staked_token_mint.key,
72 miner_vault: miner_vault.key,
73 system_program: solana_sdk::system_program::ID,
74 token_program: anchor_spl::token::ID,
75 },
76 quarry_mine::client::args::CreateMinerV2 {},
77 );
78
79 env.execute_ixs_with_signers(&[create_miner_ix], &[user])?;
80
81 Ok((miner, miner_vault))
82 }
83
84 pub fn stake_tokens(
86 &self,
87 env: &mut TestSVM,
88 miner: &AccountRef<quarry_mine::accounts::Miner>,
89 miner_vault: &AccountRef<anchor_spl::token::TokenAccount>,
90 user_token_account: &AccountRef<anchor_spl::token::TokenAccount>,
91 amount: u64,
92 user: &Keypair,
93 ) -> Result<()> {
94 let stake_ix = anchor_instruction(
95 quarry_mine::ID,
96 quarry_mine::client::accounts::StakeTokens {
97 authority: user.pubkey(),
98 miner: miner.key,
99 quarry: self.quarry.key,
100 rewarder: self.rewarder,
101 token_account: user_token_account.key,
102 miner_vault: miner_vault.key,
103 token_program: anchor_spl::token::ID,
104 },
105 quarry_mine::client::args::StakeTokens { amount },
106 );
107
108 env.execute_ixs_with_signers(&[stake_ix], &[user])?;
109
110 Ok(())
111 }
112
113 pub fn update_quarry_rewards(&self, env: &mut TestSVM) -> Result<()> {
115 let update_ix = anchor_instruction(
116 quarry_mine::ID,
117 quarry_mine::client::accounts::UpdateQuarryRewards {
118 quarry: self.quarry.key,
119 rewarder: self.rewarder,
120 },
121 quarry_mine::client::args::UpdateQuarryRewards {},
122 );
123
124 env.execute_ixs(&[update_ix])?;
125
126 Ok(())
127 }
128
129 pub fn withdraw_tokens(
131 &self,
132 env: &mut TestSVM,
133 miner: &AccountRef<quarry_mine::accounts::Miner>,
134 miner_vault: &AccountRef<anchor_spl::token::TokenAccount>,
135 user_token_account: &AccountRef<anchor_spl::token::TokenAccount>,
136 amount: u64,
137 user: &Keypair,
138 ) -> Result<()> {
139 let withdraw_ix = anchor_instruction(
140 quarry_mine::ID,
141 quarry_mine::client::accounts::WithdrawTokens {
142 authority: user.pubkey(),
143 miner: miner.key,
144 quarry: self.quarry.key,
145 rewarder: self.rewarder,
146 token_account: user_token_account.key,
147 miner_vault: miner_vault.key,
148 token_program: anchor_spl::token::ID,
149 },
150 quarry_mine::client::args::WithdrawTokens { amount },
151 );
152
153 env.execute_ixs_with_signers(&[withdraw_ix], &[user])?;
154
155 Ok(())
156 }
157
158 pub fn claim_rewards(
160 &self,
161 env: &mut TestSVM,
162 rewarder: &TestRewarder,
163 miner: &AccountRef<quarry_mine::accounts::Miner>,
164 _miner_vault: &AccountRef<anchor_spl::token::TokenAccount>,
165 user_rewards_account: &AccountRef<anchor_spl::token::TokenAccount>,
166 user: &Keypair,
167 ) -> Result<()> {
168 let (minter, _) = Pubkey::find_program_address(
170 &[
171 b"MintWrapperMinter",
172 rewarder.mint_wrapper.mint_wrapper.key.as_ref(),
173 rewarder.rewarder.key.as_ref(),
174 ],
175 &quarry_mint_wrapper::ID,
176 );
177
178 let claim_ix = anchor_instruction(
179 quarry_mine::ID,
180 quarry_mine::client::accounts::ClaimRewardsV2 {
181 mint_wrapper: rewarder.mint_wrapper.mint_wrapper.key,
182 mint_wrapper_program: quarry_mint_wrapper::ID,
183 minter,
184 rewards_token_mint: rewarder.mint_wrapper.reward_token_mint.key,
185 rewards_token_account: user_rewards_account.key,
186 claim_fee_token_account: rewarder.claim_fee_token_account.key,
187 claim: quarry_mine::client::accounts::Claim {
188 authority: user.pubkey(),
189 miner: miner.key,
190 quarry: self.quarry.key,
191 token_program: anchor_spl::token::ID,
192 rewarder: self.rewarder,
193 },
194 },
195 quarry_mine::client::args::ClaimRewardsV2 {},
196 );
197
198 env.execute_ixs_with_signers(&[claim_ix], &[user])?;
199
200 Ok(())
201 }
202}
203
204impl fmt::Display for TestQuarry {
205 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
206 write!(f, "{}", self.quarry.key)
207 }
208}
209
210impl AsRef<[u8]> for TestQuarry {
211 fn as_ref(&self) -> &[u8] {
212 self.quarry.key.as_ref()
213 }
214}