anchor counter
lib.rs
lib.rs
use anchor_lang::prelude::*;
declare_id!("E1GF68JGGqduqQMpEPS1F85GxoDGxvu2K5er23F3MD2v");
#[program]
// Smart contract functions
pub mod counter {
use super::*;
pub fn create_counter(ctx: Context<CreateCounter>) -> Result<()> {
msg!("Creating a Counter!!");
// The creation of the counter must be here
let counter = &mut ctx.accounts.counter;
counter.authority = ctx.accounts.authority.key();
counter.count = 0;
msg!("Current count is {}", counter.count);
msg!("The Admin PubKey is: {} ", counter.authority);
Ok(())
}
pub fn update_counter(ctx: Context<UpdateCounter>) -> Result<()> {
msg!("Adding 1 to the counter!!");
// Updating the counter must be here
let counter = &mut ctx.accounts.counter;
counter.count += 1;
msg!("Current count is {}", counter.count);
msg!("{} remaining to reach 1000 ", 1000 - counter.count);
Ok(())
}
}
// Data validators
#[derive(Accounts)]
pub struct CreateCounter<'info> {
#[account(mut)]
authority: Signer<'info>,
#[account(
init,
seeds = [authority.key().as_ref()],
bump,
payer = authority,
space = 100
)]
counter: Account<'info, Counter>,
system_program: Program<'info, System>,
}
#[derive(Accounts)]
pub struct UpdateCounter<'info> {
authority: Signer<'info>,
#[account(mut, has_one = authority)]
counter: Account<'info, Counter>,
}
// Data structures
#[account]
pub struct Counter {
authority: Pubkey,
count: u64,
}
clinet.ts
clinet.ts
// Client
// console.log("My address:", pg.wallet.publicKey.toString());
// const balance = await pg.connection.getBalance(pg.wallet.publicKey);
// console.log(`My balance: ${balance / web3.LAMPORTS_PER_SOL} SOL`);
import * as anchor from "@coral-xyz/anchor";
import { SystemProgram, PublicKey } from "@solana/web3.js";
// Initialize the provider
const provider = anchor.AnchorProvider.local();
anchor.setProvider(provider);
// Define the program
// const program = anchor.workspace.Counter; // Replace with your program name
const programId = new PublicKey("E1GF68JGGqduqQMpEPS1F85GxoDGxvu2K5er23F3MD2v");
const idl = {
version: "0.1.0",
name: "counter",
instructions: [
{
name: "createCounter",
accounts: [
{
name: "authority",
isMut: true,
isSigner: true,
},
{
name: "counter",
isMut: true,
isSigner: false,
},
{
name: "systemProgram",
isMut: false,
isSigner: false,
},
],
args: [],
},
{
name: "updateCounter",
accounts: [
{
name: "authority",
isMut: false,
isSigner: true,
},
{
name: "counter",
isMut: true,
isSigner: false,
},
],
args: [],
},
],
accounts: [
{
name: "Counter",
type: {
kind: "struct",
fields: [
{
name: "authority",
type: "publicKey",
},
{
name: "count",
type: "u64",
},
],
},
},
],
};
const program = new anchor.Program(idl, programId, provider);
console.log("program.programId: ", program.programId);
async function createCounter() {
// 检测没有的时候再创建
const [counter, _counterBump] =
await anchor.web3.PublicKey.findProgramAddress(
[provider.wallet.publicKey.toBytes()],
program.programId
);
console.log("Your counter address", counter.toString());
// 检查账户是否已经存在
try {
const counterAccount = await program.account.counter.fetch(counter);
console.log("Counter already exists with data:", counterAccount);
return; // 如果账户已经存在,直接返回
} catch (err) {
// 如果账户不存在,继续创建
console.log("Counter does not exist, creating a new one...");
}
// 发送创建计数器的交易
const tx = await program.methods
.createCounter()
.accounts({
authority: provider.wallet.publicKey,
counter: counter,
systemProgram: SystemProgram.programId,
})
.rpc();
console.log("Your transaction signature", tx);
}
async function fetchCounter() {
// Derive the counter's public key
const [counterPubkey, _] = await anchor.web3.PublicKey.findProgramAddress(
[provider.wallet.publicKey.toBytes()],
program.programId
);
console.log("Your counter address", counterPubkey.toString());
// Fetch the counter account data
const counter = await program.account.counter.fetch(counterPubkey);
console.log("Your counter", counter);
}
async function updateCounter() {
// Derive the counter's public key
const [counterPubkey, _] = await anchor.web3.PublicKey.findProgramAddress(
[provider.wallet.publicKey.toBytes()],
program.programId
);
console.log("Your counter address", counterPubkey.toString());
// Fetch the current counter value
const counter = await program.account.counter.fetch(counterPubkey);
console.log("Your counter", counter);
// Send a transaction to update the counter
const tx = await program.methods
.updateCounter()
.accounts({
counter: counterPubkey,
})
.rpc();
console.log("Your transaction signature", tx);
// Fetch the updated counter value
const counterUpdated = await program.account.counter.fetch(counterPubkey);
console.log("Your counter count is: ", counterUpdated.count.toNumber());
}
async function main() {
console.log("Starting client...");
// Create the counter
await createCounter();
// Fetch the counter
await fetchCounter();
// Update the counter
await updateCounter();
}
main().catch((err) => {
console.error(err);
});
test
index.test.ts
describe("counter", () => {
// Configure the client to use the local cluster.
const systemProgram = anchor.web3.SystemProgram;
console.log("pg.program.programId", pg.program.programId);
console.log(JSON.stringify(pg.program.idl, null, 2));
it("Create Counter!", async () => {
// Keypair = account
const [counter, _counterBump] =
await anchor.web3.PublicKey.findProgramAddress(
[pg.wallet.publicKey.toBytes()],
pg.program.programId
);
console.log("Your counter address", counter.toString());
const tx = await pg.program.methods
.createCounter()
.accounts({
authority: pg.wallet.publicKey,
counter: counter,
systemProgram: systemProgram.programId,
})
.rpc();
console.log("Your transaction signature", tx);
});
it("Fetch a counter!", async () => {
// Keypair = account
const [counterPubkey, _] = await anchor.web3.PublicKey.findProgramAddress(
[pg.wallet.publicKey.toBytes()],
pg.program.programId
);
console.log("Your counter address", counterPubkey.toString());
const counter = await pg.program.account.counter.fetch(counterPubkey);
console.log("Your counter", counter);
});
it("Update a counter!", async () => {
// Keypair = account
const [counterPubkey, _] = await anchor.web3.PublicKey.findProgramAddress(
[pg.wallet.publicKey.toBytes()],
pg.program.programId
);
console.log("Your counter address", counterPubkey.toString());
const counter = await pg.program.account.counter.fetch(counterPubkey);
console.log("Your counter", counter);
const tx = await pg.program.methods
.updateCounter()
.accounts({
counter: counterPubkey,
})
.rpc();
console.log("Your transaction signature", tx);
const counterUpdated = await pg.program.account.counter.fetch(
counterPubkey
);
console.log("Your counter count is: ", counterUpdated.count.toNumber());
});
});
