소각이란 무엇인가요?
토큰 소각은 토큰 계정 잔액을 영구적으로 감소시키고 민트의 총 공급량을 동일한 양만큼 줄입니다.
토큰 소각 방법
토큰 소각은 Token Program의 Burn 또는 BurnChecked 명령어를
사용합니다.
아래 예제는 BurnChecked 를 사용하며, 호출자가 민트의 소수점 자릿수를
제공하여 명령어가 소각 전에 예상되는 토큰 정밀도를 확인할 수 있도록 합니다.
네이티브 민트는 소각을 지원하지 않습니다.
대신 CloseAccount 를 사용하세요.
토큰 계정 소유자 또는 승인된 위임자가 트랜잭션에 서명합니다. Token Extension Program에서는 민트에 영구 위임자 확장이 활성화되어 있는 경우 민트 영구 위임자도 소각을 승인할 수 있습니다.
소스 참조
| 항목 | 설명 | Token Program | Token Extension Program |
|---|---|---|---|
Mint | 민트 상태는 총 토큰 공급량을 저장합니다. | 소스 | 소스 |
Account | 토큰 계정 상태는 소각으로 인해 감소된 토큰 잔액을 저장합니다. | 소스 | 소스 |
Burn | 호출자가 민트의 소수점 자릿수를 제공하지 않고도 토큰 계정 잔액과 민트 공급량을 감소시키는 소각 명령어입니다. | 소스 | 소스 |
BurnChecked | 호출자가 민트의 소수점 자릿수를 제공하도록 요구하고 토큰 계정 잔액과 민트 공급량을 감소시키기 전에 해당 값을 확인하는 소각 명령어입니다. | 소스 | 소스 |
process_burn | 토큰 소각을 위한 공유 프로세서 로직입니다. | 소스 | 소스 |
Typescript
아래 Kit 예제는 @solana/kit를 사용하는 권장 접근 방식을 보여줍니다.
@solana/web3.js를 사용하는 레거시 예제는 참고용으로 포함되어 있습니다.
Kit
import { generateKeyPairSigner } from "@solana/kit";import { createLocalClient } from "@solana/kit-client-rpc";import {findAssociatedTokenPda,tokenProgram,TOKEN_PROGRAM_ADDRESS} from "@solana-program/token";const client = await createLocalClient().use(tokenProgram());const mint = await generateKeyPairSigner();const [tokenAccount] = await findAssociatedTokenPda({mint: mint.address,owner: client.payer.address,tokenProgram: TOKEN_PROGRAM_ADDRESS});const result = await client.token.instructions.burnChecked({account: tokenAccount, // Token account holding the tokens to burn.mint: mint.address, // Mint for the token being burned.authority: client.payer, // Owner or delegate approving the burn.amount: 25n, // Token amount in base units.decimals: 2 // Decimals defined on the mint account.}).sendTransaction();const mintAccount = await client.token.accounts.mint.fetch(mint.address);const tokenAccountData = await client.token.accounts.token.fetch(tokenAccount);console.log("Mint Address:", mint.address);console.log("Mint Account:", mintAccount.data);console.log("\nToken Account Address:", tokenAccount);console.log("Token Account:", tokenAccountData.data);console.log("\nTransaction Signature:", result.context.signature);
Console
Click to execute the code.
Web3.js
import { Connection, Keypair, LAMPORTS_PER_SOL } from "@solana/web3.js";import {createAssociatedTokenAccount,burnChecked,createMint,getAccount,getMint,mintToChecked,TOKEN_PROGRAM_ID} from "@solana/spl-token";const result = await burnChecked(connection, // Connection to the local validator.feePayer, // Account paying transaction fees.associatedTokenAccount, // Token account holding the tokens to burn.mintPubkey, // Mint for the token being burned.feePayer, // Owner or delegate approving the burn.25, // Token amount in base units.2, // Decimals defined on the mint account.[], // Additional multisig signers.{commitment: "confirmed" // Confirmation options for the transaction.},TOKEN_PROGRAM_ID // Token program to invoke.);const mintAccount = await getMint(connection,mintPubkey,"confirmed",TOKEN_PROGRAM_ID);const tokenAccountData = await getAccount(connection,associatedTokenAccount,"confirmed",TOKEN_PROGRAM_ID);console.log("Mint Address:", mintPubkey.toBase58());console.log("Mint Account:", mintAccount);console.log("\nAssociated Token Account Address:",associatedTokenAccount.toBase58());console.log("Associated Token Account:", tokenAccountData);console.log("\nTransaction Signature:", result);
Console
Click to execute the code.
Rust
Rust
use anyhow::Result;use solana_client::nonblocking::rpc_client::RpcClient;use solana_commitment_config::CommitmentConfig;use solana_sdk::{program_pack::Pack,signature::{Keypair, Signer},transaction::Transaction,};use solana_system_interface::instruction::create_account;use spl_associated_token_account_interface::{address::get_associated_token_address, instruction::create_associated_token_account,};use spl_token_interface::{id as token_program_id,instruction::{burn_checked, initialize_mint, mint_to_checked},state::{Account, Mint},};#[tokio::main]async fn main() -> Result<()> {let client = RpcClient::new_with_commitment(String::from("http://localhost:8899"),CommitmentConfig::confirmed(),);let burn_amount = 25;let transaction = Transaction::new_signed_with_payer(&[burn_checked(&token_program_id(), // Token program to invoke.&associated_token_address, // Token account holding the tokens to burn.&mint.pubkey(), // Mint for the token being burned.&fee_payer.pubkey(), // Owner or delegate approving the burn.&[], // Additional multisig signers.burn_amount, // Token amount in base units.decimals, // Decimals defined on the mint account.)?,],Some(&fee_payer.pubkey()),&[&fee_payer],latest_blockhash,);let transaction_signature = client.send_and_confirm_transaction(&transaction).await?;let mint_account = client.get_account(&mint.pubkey()).await?;let mint_data = Mint::unpack(&mint_account.data)?;let token_account = client.get_account(&associated_token_address).await?;let token_data = Account::unpack(&token_account.data)?;println!("Mint Address: {}", mint.pubkey());println!("Mint Account: {:#?}", mint_data);println!("\nAssociated Token Account Address: {}",associated_token_address);println!("Associated Token Account: {:#?}", token_data);println!("\nTransaction Signature: {}", transaction_signature);Ok(())}
Console
Click to execute the code.
Python
Python
#!/usr/bin/env python3import asyncioimport jsonfrom solana.rpc.async_api import AsyncClientfrom solders.keypair import Keypairfrom solders.message import Messagefrom solders.pubkey import Pubkeyfrom solders.system_program import create_account, CreateAccountParamsfrom solders.transaction import Transactionfrom spl.token.async_client import AsyncTokenfrom spl.token.instructions import (burn_checked,BurnCheckedParams,create_associated_token_account,get_associated_token_address,initialize_mint,InitializeMintParams,mint_to_checked,MintToCheckedParams,)from spl.token.constants import MINT_LEN, TOKEN_PROGRAM_IDDECIMALS = 2AMOUNT_TO_MINT = 100AMOUNT_TO_BURN = 25async def main():rpc = AsyncClient("http://localhost:8899")async with rpc:burn_tokens_instruction = burn_checked(BurnCheckedParams(program_id=TOKEN_PROGRAM_ID, # Token program to invoke.mint=mint.pubkey(), # Mint for the token being burned.account=token_account_address, # Token account whose balance decreases.owner=fee_payer.pubkey(), # Account that owns the token account and signs the transaction.amount=AMOUNT_TO_BURN, # Token amount in base units.decimals=DECIMALS, # Decimals defined on the mint account.))latest_blockhash = await rpc.get_latest_blockhash()transaction = Transaction([fee_payer],Message([burn_tokens_instruction], fee_payer.pubkey()),latest_blockhash.value.blockhash,)result = await rpc.send_transaction(transaction)mint_info = await token.get_mint_info()token_account_info = await token.get_account_info(token_account_address)mint_account = {key: str(value) if isinstance(value, Pubkey) else valuefor key, value in mint_info._asdict().items()}token_account = {key: str(value) if isinstance(value, Pubkey) else valuefor key, value in token_account_info._asdict().items()}print("Mint Address:", mint.pubkey())print("Mint Account:")print(json.dumps(mint_account, indent=2))print("\nToken Account Address:", token_account_address)print("Token Account:")print(json.dumps(token_account, indent=2))print("\nTransaction Signature:", result.value)if __name__ == "__main__":asyncio.run(main())
Console
Click to execute the code.
Is this page helpful?