3

I'm new to Solana development, and I'm stuck with testing my initialize instruction. My initialize instruction is not complicated.

I'm getting this error.

thread 'test_initialize' panicked at /Users/user/.cargo/registry/src/index.crates.io-6f17d22bba15001f/solana-program-test-1.18.17/src/lib.rs:713:17:
Program processor not available for myProgram (<program id>)

initialize instruction looks like below.

#[derive(Accounts)]
pub struct Initialize<'info> {
    #[account(mut)]
    pub admin: Signer<'info>,

    #[account(
        init,
        payer = admin,
        seeds = [b"fund"],
        bump,
        space = 1024,
    )]
    pub fund: Account<'info, Fund>,

    pub system_program: Program<'info, System>,
}

#[program]
pub mod myProgram {
    use super::*;

    pub fn initialize(
        ctx: Context<Initialize>,
        default_protocol_fee_rate: u16,
        whitelisted_tokens: Vec<Pubkey>,
        lst_caps: Vec<u64>,
    ) -> Result<()> {
        let fund = &mut ctx.accounts.fund;

        Ok((fund.initialize( // this just stores values
            ctx.accounts.admin.key(),
            default_protocol_fee_rate,
            whitelisted_tokens,
            lst_caps,
        ))?)
    }
}

And the test code is here.

use anchor_lang::{prelude::*, solana_program::instruction::Instruction, system_program};
use myProgram;
use solana_program_test::{processor, tokio, ProgramTest, ProgramTestContext};
use solana_sdk::{account::Account, signature::Keypair, signer::Signer, transaction::Transaction};

#[tokio::test]
async fn test_initialize() {
    let SetUpTest { validator, admin, fund } = SetUpTest::new();

    let mut context = validator.start_with_context().await;
    let amount: u64 = 1_000;

    let initialize_ix = Instruction {
        program_id: myProgram::ID,
        accounts: myProgram::accounts::Initialize {
            admin: admin.pubkey(),
            fund,
            system_program: system_program::ID,
        }.to_account_metas(None),
        data: myProgram::instruction::Initialize {
            default_protocol_fee_rate: 10,
            whitelisted_tokens: [
                Pubkey::new_unique(),
                Pubkey::new_unique(),
            ].to_vec(),
            lst_caps: [
                1000,
                2000
            ].to_vec(),
        }.try_to_vec().unwrap(),
    };

    let initialize_tx = Transaction::new_signed_with_payer(
        &[initialize_ix],
        Some(&admin.pubkey()),
        &[&admin],
        context.last_blockhash,
    );

    context
        .banks_client
        .process_transaction(initialize_tx)
        .await
        .unwrap();
}

pub struct SetUpTest {
    pub validator: ProgramTest,
    pub admin: Keypair,
    pub fund: Pubkey,
}

impl SetUpTest {
    pub fn new() -> Self {
        let mut validator = ProgramTest::new("myProgram", myProgram::ID, None);

        let admin = Keypair::new();
        validator.add_account(
            admin.pubkey(),
            Account {
                lamports: 1_000_000_000,
                ..Account::default()
            },
        );

        let (fund_pda, _) = Pubkey::find_program_address(&[b"fund"], &myProgram::ID);

        msg!("fund_pda: {}", fund_pda);

        Self {
            validator,
            admin,
            fund: fund_pda,
        }
    }
}

The error is ocurring at let mut validator = ProgramTest::new("myProgram", myProgram::ID, None); at the test code. Some other reference used processor!(process_instruction) at None argument, but at my case, I don't know what to put at there.

Edit

For more information, I've tried let mut validator = ProgramTest::new("myProgram", myProgram::ID, processor!(myProgram::entry));, but here's a compile issue occurs.

mismatched types
expected fn pointer `for<'a, 'b, 'c, 'd> fn(&'a anchor_lang::prelude::Pubkey, &'b [AccountInfo<'c>], &'d _) -> Result<_, _>`
      found fn item `for<'info, 'a, 'b> fn(&'a anchor_lang::prelude::Pubkey, &'info [AccountInfo<'info>], &'b _) -> Result<_, _> {entry}`
4
  • Are you calling your instruction in a mod with the #[program] macro? If not, that's what your issue is.
    – McBain
    Commented Jul 10 at 11:42
  • @Ahri Ah yes, I'm calling with #[program] macro. I missed it moving over here.
    – Jung Chun
    Commented Jul 11 at 1:33
  • Could you update your code to include this? I'm pretty sure the problem is related to that but it's hard to tell if we don't have the code
    – McBain
    Commented Jul 11 at 8:24
  • @Ahri Yeah, I updated the initialize instruction code! Thanks
    – Jung Chun
    Commented Jul 11 at 9:55

1 Answer 1

4

This is a known issue between anchor and solana-test. At the moment, the recommended workaround is to use cargo test-sbf instead of cargo test (more info on why this works here.) Depending on your exact project structure (e.g. if you have more than one program) you might have to set some env variables, check this answer for this.

If this doesn't work, here's a fork someone made to of solana-test to have it work with anchor: https://github.com/dankelleher/solana/commit/3c285b5574722bd8e7ec4c7f659ec769b9aba5ce

2
  • Side note: The anchor issue states: > If more people start reporting about it, we might PR to solana-program-test crate to include an anchor feature with Anchor's expected lifetimes So if this bothers you, open an issue in anchor to discuss this.
    – McBain
    Commented Jul 11 at 10:36
  • 1
    Thanks! Now I get the different error. I'll mark this accepted and come back with new question.
    – Jung Chun
    Commented Jul 12 at 9:39

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.