Skip to content

refactor: to light sdk v2 cargo #3

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Draft
wants to merge 3 commits into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 9 additions & 14 deletions cargo-generate.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
[template]
cargo_generate_version = ">=0.18.2"
ignore = [ "circuits/program_name/cargo-generate.toml", "programs_psp/program_name/cargo-generate.toml" ]
ignore = [
"circuits/program_name/cargo-generate.toml",
"programs_psp/program_name/cargo-generate.toml",
]


[placeholders.rust-name]
Expand Down Expand Up @@ -32,21 +35,13 @@ prompt = "Borsh version"
type = "string"
prompt = "light hasher version"

[placeholders.light-macros-version]
type = "string"
prompt = "light macros version"

[placeholders.light-sdk-version]
type = "string"
prompt = "light sdk version"

[placeholders.light-sdk-macros-version]
type = "string"
prompt = "light sdk macros version"

[placeholders.light-utils-version]
[placeholders.light-compressed-account-version]
type = "string"
prompt = "Light utils version"
prompt = "light compressed account version"

[placeholders.light-verifier-version]
type = "string"
Expand All @@ -60,14 +55,14 @@ prompt = "solana sdk version"
type = "string"
prompt = "light client version"

[placeholders.light-test-utils-version]
[placeholders.light-program-test-version]
type = "string"
prompt = "light test utils version"
prompt = "light program test version"

[placeholders.solana-program-test-version]
type = "string"
prompt = "solana program test version"

[placeholders.tokio-version]
type = "string"
prompt = "tokio version"
prompt = "tokio version"
16 changes: 5 additions & 11 deletions programs/{{rust-name}}/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ name = "{{rust-name}}"
version = "0.1.0"
description = "Created with Anchor"
edition = "2021"
rust-version = "1.75.0"

[lib]
crate-type = ["cdylib", "lib"]
Expand All @@ -15,23 +16,16 @@ no-log-ix-name = []
cpi = ["no-entrypoint"]
default = ["idl-build"]
test-sbf = []
bench-sbf = []
idl-build = ["anchor-lang/idl-build", "light-sdk/idl-build"]

[dependencies]
anchor-lang = "{{anchor-version}}"
light-hasher = {version="{{light-hasher-version}}", features = ["solana"] }
light-macros = "{{light-macros-version}}"
light-hasher = { version = "{{light-hasher-version}}", features = ["solana"] }
light-sdk = "{{light-sdk-version}}"
light-sdk-macros = "{{light-sdk-macros-version}}"
light-utils = "{{light-utils-version}}"
light-verifier = "{{light-verifier-version}}"

[target.'cfg(not(target_os = "solana"))'.dependencies]
solana-sdk = "{{solana-sdk-version}}"

[dev-dependencies]
light-client ="{{light-client-version}}"
light-test-utils = "{{light-test-utils-version}}"
solana-program-test = "{{solana-program-test-version}}"
light-client = "{{light-client-version}}"
light-program-test = "{{light-program-test-version}}"
tokio = "{{tokio-version}}"
solana-sdk = "{{solana-sdk-version}}"
201 changes: 134 additions & 67 deletions programs/{{rust-name}}/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,103 +1,170 @@
use anchor_lang::prelude::*;
use light_sdk::{
compressed_account::LightAccount, light_account, light_accounts, light_program,
merkle_context::PackedAddressMerkleContext,
account::LightAccount,
cpi::verify::verify_compressed_account_infos,
error::LightSdkError,
instruction::{account_meta::CompressedAccountMeta, instruction_data::LightInstructionData},
Discriminator, LightDiscriminator, LightHasher,
};

declare_id!("{{program-id}}");

#[light_program]
#[program]
pub mod {{rust-name-snake-case}} {
use light_sdk::{
address::v1::derive_address,
cpi::accounts::CompressionCpiAccounts,
NewAddressParamsPacked,
};

use super::*;

pub fn create<'info>(
ctx: LightContext<'_, '_, '_, 'info, Create<'info>>,
ctx: Context<'_, '_, '_, 'info, GenericAnchorAccounts<'info>>,
light_ix_data: LightInstructionData,
output_merkle_tree_index: u8,
) -> Result<()> {
ctx.light_accounts.counter.owner = ctx.accounts.signer.key();
ctx.light_accounts.counter.counter = 0;
let program_id = crate::ID.into();
let light_cpi_accounts = CompressionCpiAccounts::new(
ctx.accounts.signer.as_ref(),
ctx.remaining_accounts,
crate::ID,
)
.map_err(ProgramError::from)?;

let address_merkle_context = light_ix_data
.new_addresses
.ok_or(LightSdkError::ExpectedAddressMerkleContext)
.map_err(ProgramError::from)?[0];

let (address, address_seed) = derive_address(
&[b"counter", ctx.accounts.signer.key().as_ref()],
&light_cpi_accounts.tree_accounts()[address_merkle_context.address_merkle_tree_pubkey_index as
usize].key(),
&crate::ID,
);

let new_address_params = NewAddressParamsPacked {
seed: address_seed,
address_queue_account_index: address_merkle_context.address_queue_pubkey_index,
address_merkle_tree_root_index: address_merkle_context.root_index,
address_merkle_tree_account_index: address_merkle_context.address_merkle_tree_pubkey_index,
};

let mut counter = LightAccount::<'_, CounterCompressedAccount>::new_init(
&program_id,
Some(address),
output_merkle_tree_index,
);

counter.owner = ctx.accounts.signer.key();

verify_compressed_account_infos(
&light_cpi_accounts,
light_ix_data.proof,
&[counter.to_account_info().unwrap()],
Some(vec![new_address_params]),
None,
false,
None,
)
.map_err(ProgramError::from)?;

Ok(())
}

pub fn increment<'info>(
ctx: LightContext<'_, '_, '_, 'info, Increment<'info>>,
ctx: Context<'_, '_, '_, 'info, GenericAnchorAccounts<'info>>,
light_ix_data: LightInstructionData,
counter_value: u64,
account_meta: CompressedAccountMeta,
) -> Result<()> {
ctx.light_accounts.counter.counter += 1;
let program_id = crate::ID.into();
let mut counter = LightAccount::<'_, CounterCompressedAccount>::new_mut(
&program_id,
&account_meta,
CounterCompressedAccount {
owner: ctx.accounts.signer.key(),
counter: counter_value,
},
)
.map_err(ProgramError::from)?;

counter.counter += 1;

let light_cpi_accounts = CompressionCpiAccounts::new(
ctx.accounts.signer.as_ref(),
ctx.remaining_accounts,
crate::ID,
)
.map_err(ProgramError::from)?;

verify_compressed_account_infos(
&light_cpi_accounts,
light_ix_data.proof,
&[counter.to_account_info().unwrap()],
None,
None,
false,
None,
)
.map_err(ProgramError::from)?;

Ok(())
}

pub fn delete<'info>(
ctx: LightContext<'_, '_, '_, 'info, Delete<'info>>,
ctx: Context<'_, '_, '_, 'info, GenericAnchorAccounts<'info>>,
light_ix_data: LightInstructionData,
counter_value: u64,
account_meta: CompressedAccountMeta,
) -> Result<()> {
let program_id = crate::ID.into();

let counter = LightAccount::<'_, CounterCompressedAccount>::new_close(
&program_id,
&account_meta,
CounterCompressedAccount {
owner: ctx.accounts.signer.key(),
counter: counter_value,
},
)
.map_err(ProgramError::from)?;

let light_cpi_accounts = CompressionCpiAccounts::new(
ctx.accounts.signer.as_ref(),
ctx.remaining_accounts,
crate::ID,
)
.map_err(ProgramError::from)?;

// The true parameter indicates that accounts should be closed
verify_compressed_account_infos(
&light_cpi_accounts,
light_ix_data.proof,
&[counter.to_account_info().unwrap()],
None,
None,
true,
None,
)
.map_err(ProgramError::from)?;

Ok(())
}
}


#[light_account]
#[derive(Clone, Debug, Default)]
#[derive(
Clone, Debug, Default, AnchorDeserialize, AnchorSerialize, LightDiscriminator, LightHasher,
)]
pub struct CounterCompressedAccount {
#[truncate]
#[hash]
pub owner: Pubkey,
pub counter: u64,
}

#[error_code]
pub enum CustomError {
#[msg("No authority to perform this action")]
Unauthorized,
}

#[light_accounts]
pub struct Create<'info> {
#[account(mut)]
#[fee_payer]
pub signer: Signer<'info>,
#[self_program]
pub self_program: Program<'info, crate::program::{{rust-name-camel-case}}>,
/// CHECK: Checked in light-system-program.
#[authority]
pub cpi_signer: AccountInfo<'info>,
#[light_account(init, seeds = [b"counter", signer.key().as_ref()])]
pub counter: LightAccount<CounterCompressedAccount>,
}

#[light_accounts]
pub struct Increment<'info> {
#[account(mut)]
#[fee_payer]
pub signer: Signer<'info>,
#[self_program]
pub self_program: Program<'info, crate::program::{{rust-name-camel-case}}>,
/// CHECK: Checked in light-system-program.
#[authority]
pub cpi_signer: AccountInfo<'info>,

#[light_account(
mut,
seeds = [b"counter", signer.key().as_ref()],
constraint = counter.owner == signer.key() @ CustomError::Unauthorized
)]
pub counter: LightAccount<CounterCompressedAccount>,
}

#[light_accounts]
pub struct Delete<'info> {
#[derive(Accounts)]
pub struct GenericAnchorAccounts<'info> {
#[account(mut)]
#[fee_payer]
pub signer: Signer<'info>,
#[self_program]
pub self_program: Program<'info, crate::program::{{rust-name-camel-case}}>,
/// CHECK: Checked in light-system-program.
#[authority]
pub cpi_signer: AccountInfo<'info>,

#[light_account(
close,
seeds = [b"counter", signer.key().as_ref()],
constraint = counter.owner == signer.key() @ CustomError::Unauthorized
)]
pub counter: LightAccount<CounterCompressedAccount>,
}
Loading