简体   繁体   中英

Anchor test Transaction simulation failed: An account required by the instruction is missing

I am trying to create a simple program that lets users donates. This program is bootstrapped by Anchor. Unfortunately, It failed on very first step creating a PDA account by CPI. Please see the detailed info below:

Anchor test fails with:

    PublicKey {
  _bn: <BN: 265af4367675fa484c7148bf59dd7392a0a290cee149a6912c35a01495da14df>
} PublicKey {
  _bn: <BN: ee4f6de6f56f9606ca2af702908a5655ede672356998a6139802e3cdde9325f3>
}
Transaction simulation failed: Error processing Instruction 0: An account required by the instruction is missing 
    Program Fg6PaFpoGXkYsidMpWTK6W2BeZ7FEfcYkg476zPFsLnS invoke [1]
    Program log: Instruction: SendDonation
    Instruction references an unknown account 11111111111111111111111111111111
    Program Fg6PaFpoGXkYsidMpWTK6W2BeZ7FEfcYkg476zPFsLnS consumed 5599 of 1400000 compute units
    Program Fg6PaFpoGXkYsidMpWTK6W2BeZ7FEfcYkg476zPFsLnS failed: An account required by the instruction is missing
    1) Should send donation

Here the lib.rs

use anchor_lang::prelude::*;

declare_id!("Fg6PaFpoGXkYsidMpWTK6W2BeZ7FEfcYkg476zPFsLnS");

#[program]
pub mod crypto_donut {
    use super::*;
    use anchor_lang::solana_program::entrypoint::ProgramResult;
    use anchor_lang::solana_program::program::invoke;
    use anchor_lang::solana_program::system_instruction::transfer;

    pub fn initialize(ctx: Context<Initialize>) -> ProgramResult {
        let base_account = &mut ctx.accounts.base_account;
        base_account.owner = ctx.accounts.user.to_account_info().key();
        Ok(())
    }

    pub fn send_donation(ctx: Context<Donation>, amount: u64) -> ProgramResult {
        let base_account = &mut ctx.accounts.base_account;
        base_account.donators.push(ctx.accounts.user.key());

        let instruction = transfer(ctx.accounts.user.key, &base_account.key(), amount);

        invoke(
            &instruction,
            &[
                ctx.accounts.user.to_account_info(),
                base_account.to_account_info(),
            ],
        )
        .unwrap();

        Ok(())
    }
}

#[derive(Accounts)]
pub struct Initialize<'info> {
    #[account(init, payer = user, space = 64 + 1024)]
    pub base_account: Account<'info, BaseAccount>,

    #[account(mut)]
    pub user: Signer<'info>,
    pub system_program: Program<'info, System>,
}

#[account]
pub struct BaseAccount {
    pub donators: Vec<Pubkey>,
    pub owner: Pubkey,
}

#[derive(Accounts)]
pub struct Donation<'info> {
    #[account(mut)]
    pub base_account: Account<'info, BaseAccount>,
    pub user: Signer<'info>,
}

Here the test which failed:

  it("Should send donation", async () => {
      const donator = anchor.web3.Keypair.generate();

      console.log(donator.publicKey, baseAccount.publicKey);

      await provider.connection.confirmTransaction(
          await provider.connection.requestAirdrop(donator.publicKey, 10000000000),
          "confirmed"
        );

        const tx = await program.rpc.sendDonation(new anchor.BN(100), {
          accounts: {
              baseAccount: baseAccount.publicKey,
              user: donator.publicKey,
          },
          signers: [donator],
        });

        const balance = await program.account.baseAccount.getAccountInfo(donator.publicKey);
      console.log(balance);
        expect(balance.lamports.toString()).equal("100");
      });
});

What am I doing wrong?

Lol, i forget #[account(mut)] before pub user: Signer<'info> :))

#[derive(Accounts)]
pub struct Donation<'info> {
    #[account(mut)]
    pub base_account: Account<'info, BaseAccount>,
    #[account(mut)]
    pub user: Signer<'info>,
    pub system_program: Program<'info, System>,
}

and system_program too. Thanks for Stepan comment

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM