Skip to main content
added 59 characters in body
Source Link
sohrab
  • 1.9k
  • 5
  • 17

The best way to see what Anchor is currently doing is to use anchor expandanchor expand to see the expanded macros. Then you can pull that logic inside your own function.

  1. How can we check if a PDA account already exist within a function (not using struct).

I believe Anchor just checks the account balance, e.g. my_account.lamports().

Please note even if the account does exist, Anchor does a few extra things:

  • Ensures the account size matches the requested space, even allocating extra space via CPI if required
  • Ensures there is enough balance for the requested account size, even transferring lamports from payer via CPI, if it is short
  • Ensures the right program is assigned to the account, even assigning owner via CPI if required
  1. How can we create a PDA account within a function (not using struct).

This is how Anchor does it under the hood:

let (__pda_address, __bump) = Pubkey::find_program_address(
    &[<seeds>],
    program_id,
);

let cpi_accounts = anchor_lang::system_program::CreateAccount {
    from: payer.to_account_info(),
    to: my_account.to_account_info(),
};
let cpi_context = anchor_lang::context::CpiContext::new(
    system_program.to_account_info(),
    cpi_accounts,
);
anchor_lang::system_program::create_account(
    cpi_context
        .with_signer(
            &[
                &[
                    <seeds>,
                    &[__bump][..],
                ][..],
            ],
        ),
    lamports,
    space as u64,
    program_id,
)?;
  1. Is there a way to create a PDA account using struct only if doesn't exist already?

You can use init_if_needed in your Accounts struct to instruct Anchor to create an account if only it does not already exist.

This feature is susceptible to re-initialisation attacks so it is not enabled by default. You can enable it in your Cargo.toml by adding init-if-needed feature to anchor-lang.

The best way to see what Anchor is currently doing is to use anchor expand to see the expanded macros. Then you can pull that logic inside your own function.

  1. How can we check if a PDA account already exist within a function (not using struct).

I believe Anchor just checks the account balance, e.g. my_account.lamports().

Please note even if the account does exist, Anchor does a few extra things:

  • Ensures the account size matches the requested space, even allocating extra space via CPI if required
  • Ensures there is enough balance for the requested account size, even transferring lamports from payer via CPI, if it is short
  • Ensures the right program is assigned to the account, even assigning owner via CPI if required
  1. How can we create a PDA account within a function (not using struct).

This is how Anchor does it under the hood:

let (__pda_address, __bump) = Pubkey::find_program_address(
    &[<seeds>],
    program_id,
);

let cpi_accounts = anchor_lang::system_program::CreateAccount {
    from: payer.to_account_info(),
    to: my_account.to_account_info(),
};
let cpi_context = anchor_lang::context::CpiContext::new(
    system_program.to_account_info(),
    cpi_accounts,
);
anchor_lang::system_program::create_account(
    cpi_context
        .with_signer(
            &[
                &[
                    <seeds>,
                    &[__bump][..],
                ][..],
            ],
        ),
    lamports,
    space as u64,
    program_id,
)?;
  1. Is there a way to create a PDA account using struct only if doesn't exist already?

You can use init_if_needed in your Accounts struct to instruct Anchor to create an account if only it does not already exist.

This feature is susceptible to re-initialisation attacks so it is not enabled by default. You can enable it in your Cargo.toml by adding init-if-needed feature to anchor-lang.

The best way to see what Anchor is currently doing is to use anchor expand to see the expanded macros. Then you can pull that logic inside your own function.

  1. How can we check if a PDA account already exist within a function (not using struct).

I believe Anchor just checks the account balance, e.g. my_account.lamports().

Please note even if the account does exist, Anchor does a few extra things:

  • Ensures the account size matches the requested space, even allocating extra space via CPI if required
  • Ensures there is enough balance for the requested account size, even transferring lamports from payer via CPI, if it is short
  • Ensures the right program is assigned to the account, even assigning owner via CPI if required
  1. How can we create a PDA account within a function (not using struct).

This is how Anchor does it under the hood:

let (__pda_address, __bump) = Pubkey::find_program_address(
    &[<seeds>],
    program_id,
);

let cpi_accounts = anchor_lang::system_program::CreateAccount {
    from: payer.to_account_info(),
    to: my_account.to_account_info(),
};
let cpi_context = anchor_lang::context::CpiContext::new(
    system_program.to_account_info(),
    cpi_accounts,
);
anchor_lang::system_program::create_account(
    cpi_context
        .with_signer(
            &[
                &[
                    <seeds>,
                    &[__bump][..],
                ][..],
            ],
        ),
    lamports,
    space as u64,
    program_id,
)?;
  1. Is there a way to create a PDA account using struct only if doesn't exist already?

You can use init_if_needed in your Accounts struct to instruct Anchor to create an account if only it does not already exist.

This feature is susceptible to re-initialisation attacks so it is not enabled by default. You can enable it in your Cargo.toml by adding init-if-needed feature to anchor-lang.

added 328 characters in body
Source Link
sohrab
  • 1.9k
  • 5
  • 17

The best way to see what Anchor is currently doing is to use anchor expand to see the expanded macros. Then you can pull that logic inside your own function.

  1. How can we check if a PDA account already exist within a function (not using struct).

I believe Anchor just checks the account balance, e.g. my_account.lamports().

Please note even if the account does exist, Anchor does a few extra things:

  • Ensures the account size matches the requested space, even allocating extra space via CPI if required
  • Ensures there is enough balance for the requested account size, even transferring lamports from payer via CPI, if it is short
  • Ensures the right program is assigned to the account, even assigning owner via CPI if required
  1. How can we create a PDA account within a function (not using struct).

This is how Anchor does it under the hood:

let (__pda_address, __bump) = Pubkey::find_program_address(
    &[<seeds>],
    program_id,
);

let cpi_accounts = anchor_lang::system_program::CreateAccount {
    from: payer.to_account_info(),
    to: my_account.to_account_info(),
};
let cpi_context = anchor_lang::context::CpiContext::new(
    system_program.to_account_info(),
    cpi_accounts,
);
anchor_lang::system_program::create_account(
    cpi_context
        .with_signer(
            &[
                &[
                    <seeds>,
                    &[__bump][..],
                ][..],
            ],
        ),
    lamports,
    space as u64,
    program_id,
)?;
  1. Is there a way to create a PDA account using struct only if doesn't exist already?

I doYou can use init_if_needed in your Accounts struct to instruct Anchor to create an account if only it does not believealready exist.

This feature is susceptible to re-initialisation attacks so it is not enabled by default. You either havecan enable it in your Cargo.toml by adding init-if-needed or you don't. There is no in-betweenfeature to anchor-lang.

The best way to see what Anchor is currently doing is to use anchor expand to see the expanded macros. Then you can pull that logic inside your own function.

  1. How can we check if a PDA account already exist within a function (not using struct).

I believe Anchor just checks the account balance, e.g. my_account.lamports().

Please note even if the account does exist, Anchor does a few extra things:

  • Ensures the account size matches the requested space, even allocating extra space via CPI if required
  • Ensures there is enough balance for the requested account size, even transferring lamports from payer via CPI, if it is short
  • Ensures the right program is assigned to the account, even assigning owner via CPI if required
  1. How can we create a PDA account within a function (not using struct).

This is how Anchor does it under the hood:

let (__pda_address, __bump) = Pubkey::find_program_address(
    &[<seeds>],
    program_id,
);

let cpi_accounts = anchor_lang::system_program::CreateAccount {
    from: payer.to_account_info(),
    to: my_account.to_account_info(),
};
let cpi_context = anchor_lang::context::CpiContext::new(
    system_program.to_account_info(),
    cpi_accounts,
);
anchor_lang::system_program::create_account(
    cpi_context
        .with_signer(
            &[
                &[
                    <seeds>,
                    &[__bump][..],
                ][..],
            ],
        ),
    lamports,
    space as u64,
    program_id,
)?;
  1. Is there a way to create a PDA account using struct only if doesn't exist already?

I do not believe so. You either have init or you don't. There is no in-between.

The best way to see what Anchor is currently doing is to use anchor expand to see the expanded macros. Then you can pull that logic inside your own function.

  1. How can we check if a PDA account already exist within a function (not using struct).

I believe Anchor just checks the account balance, e.g. my_account.lamports().

Please note even if the account does exist, Anchor does a few extra things:

  • Ensures the account size matches the requested space, even allocating extra space via CPI if required
  • Ensures there is enough balance for the requested account size, even transferring lamports from payer via CPI, if it is short
  • Ensures the right program is assigned to the account, even assigning owner via CPI if required
  1. How can we create a PDA account within a function (not using struct).

This is how Anchor does it under the hood:

let (__pda_address, __bump) = Pubkey::find_program_address(
    &[<seeds>],
    program_id,
);

let cpi_accounts = anchor_lang::system_program::CreateAccount {
    from: payer.to_account_info(),
    to: my_account.to_account_info(),
};
let cpi_context = anchor_lang::context::CpiContext::new(
    system_program.to_account_info(),
    cpi_accounts,
);
anchor_lang::system_program::create_account(
    cpi_context
        .with_signer(
            &[
                &[
                    <seeds>,
                    &[__bump][..],
                ][..],
            ],
        ),
    lamports,
    space as u64,
    program_id,
)?;
  1. Is there a way to create a PDA account using struct only if doesn't exist already?

You can use init_if_needed in your Accounts struct to instruct Anchor to create an account if only it does not already exist.

This feature is susceptible to re-initialisation attacks so it is not enabled by default. You can enable it in your Cargo.toml by adding init-if-needed feature to anchor-lang.

Source Link
sohrab
  • 1.9k
  • 5
  • 17

The best way to see what Anchor is currently doing is to use anchor expand to see the expanded macros. Then you can pull that logic inside your own function.

  1. How can we check if a PDA account already exist within a function (not using struct).

I believe Anchor just checks the account balance, e.g. my_account.lamports().

Please note even if the account does exist, Anchor does a few extra things:

  • Ensures the account size matches the requested space, even allocating extra space via CPI if required
  • Ensures there is enough balance for the requested account size, even transferring lamports from payer via CPI, if it is short
  • Ensures the right program is assigned to the account, even assigning owner via CPI if required
  1. How can we create a PDA account within a function (not using struct).

This is how Anchor does it under the hood:

let (__pda_address, __bump) = Pubkey::find_program_address(
    &[<seeds>],
    program_id,
);

let cpi_accounts = anchor_lang::system_program::CreateAccount {
    from: payer.to_account_info(),
    to: my_account.to_account_info(),
};
let cpi_context = anchor_lang::context::CpiContext::new(
    system_program.to_account_info(),
    cpi_accounts,
);
anchor_lang::system_program::create_account(
    cpi_context
        .with_signer(
            &[
                &[
                    <seeds>,
                    &[__bump][..],
                ][..],
            ],
        ),
    lamports,
    space as u64,
    program_id,
)?;
  1. Is there a way to create a PDA account using struct only if doesn't exist already?

I do not believe so. You either have init or you don't. There is no in-between.