intro
anchor macros
declare_id!():declares the onchain address of the program#[program]contains instructions which defins the business logic#[dervice(Accounts)]lists the accounts with predefined constraints#[error_code]define custom, human-redable error types to make debugging possible
program structure
→ import library
→ declare_id
→ prigram (#[program])
→ accounts (#derive(Accounts))
→ error codes
structure
src
├── instructions
│ ├── instruction1.rs
│ ├── mod.rs
│ ├── instruction2.rs
│ └── instruction3.rs
├── errors.rs
├── lib.rs
└── state.rs
→ accounts (#derive(Accounts)):
all the data holder and other are termed as accounts in solana infra.
hence in event of account related tasks we uses this macros like
- account featching
- ownership checks
- PDA seeds verifications
- rent - exampt checks
- mutability enfiorcement
on higerlevel we can say “generate account validation and boiler plate code for serilization and de-serilization, so your dumbass can focus on business logic!“
account types
https://arc.net/l/quote/wlgwfhzx example:
making a vault: think of it as a locker you want ur sol to be in a vault and only your account can withdraws or add sols to it no one else!
#[derive(Accounts)]
pub struct VaultAction<'info> {
#[account(mut)]
pub signer: Signer<'info>,
#[account(
mut,
seeds = [b"vault", signer.key().as_ref()],
bump,
)]
pub vault: SystemAccount<'info>,
pub system_program: Program<'info, System>,
}- Signer<‘info>: Verifies the account signed the transaction; essential for security and for CPIs that demand a signature
#[account(mut)]
pub signer: Signer<'info>,
means the signer’s account is mustable account(mut) and the transaction must be signed Signer<'info>.
example x sends some sol to y, hence for this instruction we need x’s and y’s account to be mutable and the transaction must be signed!
#[account(
mut,
seeds = [b"vault", signer.key().as_ref()],
bump,
)]
pub vault: SystemAccount<'info>,
in this example we are using PDA, this pda is ur valut.
mut as this valut must be mutable so you can add and withdraw sol or x.
when signer transfer sol → valut balance changes.
pda = an address deterministically genertated from seeds + program id.
seeds =
b"valut(string namespace)signer.key().as_ref()signer’s public key in bytes.
bump generated by anchor when validating
why are we using SystemAccount not Account ? coz we are only storing sols data in this case [block]
Can anyone “access” (withdraw from) your vault?
No, not unless your program logic allows it. PDA accounts don’t have private keys. They can only be modified by the owning program (your Anchor program). So even if someone knows your vault PDA address, they cannot sign transactions as that PDA. Only your program (with correct seeds + bump check) can authorize changes to it
pub system_program: Program<'info, System>
- this instruction expacts the system program account, so we can all it for creating accounts, transfering shit or space allocation we never modify it we just invoke it.
as modifincation by default is only alloweb by system programs!
#[error_code]
The #[error_code] macro lets you define clear, custom errors inside the program.
#[error_code]
pub enum VaultError {
#[msg("Vault already exists")]
VaultAlreadyExists,
#[msg("Invalid amount")]
InvalidAmount,
}Each enum variant can carry a #[msg(…)] attribute that logs a descriptive string whenever the error occurs; far more helpful than a raw numeric code during debugging.