mpl_candy_guard/guards/
token_burn.rs1use super::*;
2
3use crate::{state::GuardType, utils::*};
4
5#[derive(AnchorSerialize, AnchorDeserialize, Clone, Debug)]
13pub struct TokenBurn {
14 pub amount: u64,
15 pub mint: Pubkey,
16}
17
18impl Guard for TokenBurn {
19 fn size() -> usize {
20 8 + 32 }
23
24 fn mask() -> u64 {
25 GuardType::as_mask(GuardType::TokenBurn)
26 }
27}
28
29impl Condition for TokenBurn {
30 fn validate<'info>(
31 &self,
32 ctx: &mut EvaluationContext,
33 _guard_set: &GuardSet,
34 _mint_args: &[u8],
35 ) -> Result<()> {
36 let token_gate_index = ctx.account_cursor;
38 let token_gate_account = try_get_account_info(ctx.accounts.remaining, token_gate_index)?;
39 ctx.account_cursor += 1;
41
42 let account = assert_is_ata(token_gate_account, &ctx.accounts.minter.key(), &self.mint)?;
43
44 if account.amount >= self.amount {
45 let token_gate_mint =
46 try_get_account_info(ctx.accounts.remaining, token_gate_index + 1)?;
47 ctx.account_cursor += 1;
49
50 assert_keys_equal(&token_gate_mint.key(), &self.mint)?;
52 } else {
53 return err!(CandyGuardError::NotEnoughTokens);
54 }
55
56 ctx.indices.insert("token_burn_index", token_gate_index);
57
58 Ok(())
59 }
60
61 fn pre_actions<'info>(
62 &self,
63 ctx: &mut EvaluationContext,
64 _guard_set: &GuardSet,
65 _mint_args: &[u8],
66 ) -> Result<()> {
67 let token_gate_index = ctx.indices["token_burn_index"];
68 let token_gate_account = try_get_account_info(ctx.accounts.remaining, token_gate_index)?;
70 let token_gate_mint = try_get_account_info(ctx.accounts.remaining, token_gate_index + 1)?;
71
72 spl_token_burn(TokenBurnParams {
73 mint: token_gate_mint.to_account_info(),
74 source: token_gate_account.to_account_info(),
75 amount: self.amount,
76 authority: ctx.accounts.minter.to_account_info(),
77 authority_signer_seeds: None,
78 token_program: ctx.accounts.spl_token_program.to_account_info(),
79 })?;
80
81 Ok(())
82 }
83}