anchor_lang/accounts/
unchecked_account.rs1use crate::error::ErrorCode;
5use crate::{Accounts, AccountsExit, Key, Result, ToAccountInfos, ToAccountMetas};
6use solana_program::account_info::AccountInfo;
7use solana_program::instruction::AccountMeta;
8use solana_program::pubkey::Pubkey;
9use std::collections::BTreeSet;
10use std::ops::Deref;
11
12#[derive(Debug, Clone)]
15pub struct UncheckedAccount<'info>(&'info AccountInfo<'info>);
16
17impl<'info> UncheckedAccount<'info> {
18 pub fn try_from(acc_info: &'info AccountInfo<'info>) -> Self {
19 Self(acc_info)
20 }
21}
22
23impl<'info, B> Accounts<'info, B> for UncheckedAccount<'info> {
24 fn try_accounts(
25 _program_id: &Pubkey,
26 accounts: &mut &'info [AccountInfo<'info>],
27 _ix_data: &[u8],
28 _bumps: &mut B,
29 _reallocs: &mut BTreeSet<Pubkey>,
30 ) -> Result<Self> {
31 if accounts.is_empty() {
32 return Err(ErrorCode::AccountNotEnoughKeys.into());
33 }
34 let account = &accounts[0];
35 *accounts = &accounts[1..];
36 Ok(UncheckedAccount(account))
37 }
38}
39
40impl ToAccountMetas for UncheckedAccount<'_> {
41 fn to_account_metas(&self, is_signer: Option<bool>) -> Vec<AccountMeta> {
42 let is_signer = is_signer.unwrap_or(self.is_signer);
43 let meta = match self.is_writable {
44 false => AccountMeta::new_readonly(*self.key, is_signer),
45 true => AccountMeta::new(*self.key, is_signer),
46 };
47 vec![meta]
48 }
49}
50
51impl<'info> ToAccountInfos<'info> for UncheckedAccount<'info> {
52 fn to_account_infos(&self) -> Vec<AccountInfo<'info>> {
53 vec![self.0.clone()]
54 }
55}
56
57impl<'info> AccountsExit<'info> for UncheckedAccount<'info> {}
58
59impl<'info> AsRef<AccountInfo<'info>> for UncheckedAccount<'info> {
60 fn as_ref(&self) -> &AccountInfo<'info> {
61 self.0
62 }
63}
64
65impl<'info> Deref for UncheckedAccount<'info> {
66 type Target = AccountInfo<'info>;
67
68 fn deref(&self) -> &Self::Target {
69 self.0
70 }
71}
72
73impl Key for UncheckedAccount<'_> {
74 fn key(&self) -> Pubkey {
75 *self.0.key
76 }
77}