typhoon_token/traits/
create_mint.rs

1use {
2    crate::{Mint, TokenProgram},
3    pinocchio::{
4        account_info::AccountInfo, instruction::Signer as CpiSigner, pubkey::Pubkey,
5        sysvars::rent::Rent,
6    },
7    pinocchio_token::instructions::InitializeMint2,
8    typhoon_accounts::{
9        Account, FromAccountInfo, InterfaceAccount, Mut, ProgramId, ReadableAccount, Signer,
10        SignerCheck, SystemAccount, UncheckedAccount, WritableAccount,
11    },
12    typhoon_errors::Error,
13    typhoon_utility::create_or_assign,
14};
15
16pub trait SplCreateMint<'a, T: ReadableAccount>
17where
18    Self: Sized + Into<&'a AccountInfo>,
19    T: ReadableAccount + FromAccountInfo<'a>,
20{
21    #[inline]
22    fn create_mint(
23        self,
24        rent: &Rent,
25        payer: &impl WritableAccount,
26        mint_authority: &Pubkey,
27        decimals: u8,
28        freeze_authority: Option<&Pubkey>,
29        seeds: Option<&[CpiSigner]>,
30    ) -> Result<Mut<T>, Error> {
31        let info = self.into();
32        create_or_assign(info, rent, payer, &TokenProgram::ID, Mint::LEN, seeds)?;
33
34        InitializeMint2 {
35            mint: info,
36            mint_authority,
37            decimals,
38            freeze_authority,
39        }
40        .invoke_signed(seeds.unwrap_or_default())?;
41
42        Mut::try_from_info(info)
43    }
44}
45
46macro_rules! impl_trait {
47    ($origin: ty) => {
48        impl<'a> SplCreateMint<'a, Account<'a, Mint>> for $origin {}
49        impl<'a, C> SplCreateMint<'a, Signer<'a, Account<'a, Mint>, C>> for $origin where
50            C: SignerCheck
51        {
52        }
53        impl<'a> SplCreateMint<'a, InterfaceAccount<'a, Mint>> for $origin {}
54        impl<'a, C> SplCreateMint<'a, Signer<'a, InterfaceAccount<'a, Mint>, C>> for $origin where
55            C: SignerCheck
56        {
57        }
58    };
59}
60
61impl_trait!(&'a AccountInfo);
62impl_trait!(SystemAccount<'a>);
63impl_trait!(UncheckedAccount<'a>);