carbon_system_program_decoder/instructions/
mod.rs

1use super::SystemProgramDecoder;
2pub mod advance_nonce_account;
3pub mod allocate;
4pub mod allocate_with_seed;
5pub mod assign;
6pub mod assign_with_seed;
7pub mod authorize_nonce_account;
8pub mod create_account;
9pub mod create_account_with_seed;
10pub mod initialize_nonce_account;
11pub mod transfer_sol;
12pub mod transfer_sol_with_seed;
13pub mod upgrade_nonce_account;
14pub mod withdraw_nonce_account;
15
16#[derive(
17    carbon_core::InstructionType, serde::Serialize, serde::Deserialize, PartialEq, Debug, Clone,
18)]
19pub enum SystemProgramInstruction {
20    CreateAccount(create_account::CreateAccount),
21    Assign(assign::Assign),
22    TransferSol(transfer_sol::TransferSol),
23    CreateAccountWithSeed(create_account_with_seed::CreateAccountWithSeed),
24    AdvanceNonceAccount(advance_nonce_account::AdvanceNonceAccount),
25    WithdrawNonceAccount(withdraw_nonce_account::WithdrawNonceAccount),
26    InitializeNonceAccount(initialize_nonce_account::InitializeNonceAccount),
27    AuthorizeNonceAccount(authorize_nonce_account::AuthorizeNonceAccount),
28    Allocate(allocate::Allocate),
29    AllocateWithSeed(allocate_with_seed::AllocateWithSeed),
30    AssignWithSeed(assign_with_seed::AssignWithSeed),
31    TransferSolWithSeed(transfer_sol_with_seed::TransferSolWithSeed),
32    UpgradeNonceAccount(upgrade_nonce_account::UpgradeNonceAccount),
33}
34
35impl carbon_core::instruction::InstructionDecoder<'_> for SystemProgramDecoder {
36    type InstructionType = SystemProgramInstruction;
37
38    fn decode_instruction(
39        &self,
40        instruction: &solana_sdk::instruction::Instruction,
41    ) -> Option<carbon_core::instruction::DecodedInstruction<Self::InstructionType>> {
42        if !instruction.program_id.eq(&solana_sdk::system_program::id()) {
43            return None;
44        }
45
46        carbon_core::try_decode_instructions!(instruction,
47            SystemProgramInstruction::CreateAccount => create_account::CreateAccount,
48            SystemProgramInstruction::Assign => assign::Assign,
49            SystemProgramInstruction::TransferSol => transfer_sol::TransferSol,
50            SystemProgramInstruction::CreateAccountWithSeed => create_account_with_seed::CreateAccountWithSeed,
51            SystemProgramInstruction::AdvanceNonceAccount => advance_nonce_account::AdvanceNonceAccount,
52            SystemProgramInstruction::WithdrawNonceAccount => withdraw_nonce_account::WithdrawNonceAccount,
53            SystemProgramInstruction::InitializeNonceAccount => initialize_nonce_account::InitializeNonceAccount,
54            SystemProgramInstruction::AuthorizeNonceAccount => authorize_nonce_account::AuthorizeNonceAccount,
55            SystemProgramInstruction::Allocate => allocate::Allocate,
56            SystemProgramInstruction::AllocateWithSeed => allocate_with_seed::AllocateWithSeed,
57            SystemProgramInstruction::AssignWithSeed => assign_with_seed::AssignWithSeed,
58            SystemProgramInstruction::TransferSolWithSeed => transfer_sol_with_seed::TransferSolWithSeed,
59            SystemProgramInstruction::UpgradeNonceAccount => upgrade_nonce_account::UpgradeNonceAccount,
60        )
61    }
62}
63
64#[cfg(test)]
65mod tests {
66    use carbon_core::{
67        deserialize::{ArrangeAccounts, U64PrefixString},
68        instruction::InstructionDecoder,
69    };
70    use solana_sdk::{instruction::AccountMeta, pubkey};
71
72    use super::*;
73
74    #[test]
75    fn test_decode_create_with_seed() {
76        // Arrange
77        let expected_ix = SystemProgramInstruction::CreateAccountWithSeed(
78            create_account_with_seed::CreateAccountWithSeed {
79                base: pubkey!("6bBmDxYqXeFbXN8SmtjTpiA3SrEDKsxK8RG6yhPGpa9G"),
80                seed: U64PrefixString("CF9nRGJcFhH57xgcPxaamBs5pHxHexP9".to_string()),
81                space: 165,
82                amount: 1283531083,
83                program_address: pubkey!("TokenkegQfeZyiNwAJbNbGKPFXCWuBvf9Ss623VQ5DA"),
84            },
85        );
86        let expected_accounts = vec![
87            AccountMeta::new(
88                pubkey!("6bBmDxYqXeFbXN8SmtjTpiA3SrEDKsxK8RG6yhPGpa9G"),
89                true,
90            ),
91            AccountMeta::new(
92                pubkey!("3MoeLKJVQHNUtTAXEurLAQtCSXpLGAvairYEHpkqW6CC"),
93                false,
94            ),
95        ];
96        let expected_arranged_accounts =
97            create_account_with_seed::CreateAccountWithSeedInstructionAccounts {
98                payer: pubkey!("6bBmDxYqXeFbXN8SmtjTpiA3SrEDKsxK8RG6yhPGpa9G"),
99                new_account: pubkey!("3MoeLKJVQHNUtTAXEurLAQtCSXpLGAvairYEHpkqW6CC"),
100                base_account: pubkey!("6bBmDxYqXeFbXN8SmtjTpiA3SrEDKsxK8RG6yhPGpa9G"),
101            };
102
103        // Act
104        let decoder = SystemProgramDecoder;
105        let instruction =
106            carbon_test_utils::read_instruction("tests/fixtures/create_with_seed_ix.json")
107                .expect("read fixture");
108        let decoded = decoder
109            .decode_instruction(&instruction)
110            .expect("decode instruction");
111        let decoded_arranged_accounts =
112            create_account_with_seed::CreateAccountWithSeed::arrange_accounts(
113                &instruction.accounts,
114            )
115            .expect("aranage accounts");
116
117        // Assert
118        assert_eq!(decoded.data, expected_ix);
119        assert_eq!(decoded.accounts, expected_accounts);
120        assert_eq!(decoded.program_id, solana_sdk::system_program::id());
121        assert_eq!(decoded_arranged_accounts, expected_arranged_accounts);
122    }
123}