Создание токенового минта
Что такое аккаунт минта?
Аккаунт минта уникально представляет токен в Solana и хранит его глобальные метаданные.
Mint Account Type
/// Mint data.#[repr(C)]#[derive(Clone, Copy, Debug, Default, PartialEq)]pub struct Mint {/// Optional authority used to mint new tokens. The mint authority may only/// be provided during mint creation. If no mint authority is present/// then the mint has a fixed supply and no further tokens may be/// minted.pub mint_authority: COption<Pubkey>,/// Total supply of tokens.pub supply: u64,/// Number of base 10 digits to the right of the decimal place.pub decimals: u8,/// Is `true` if this structure has been initializedpub is_initialized: bool,/// Optional authority to freeze token accounts.pub freeze_authority: COption<Pubkey>,}
Обратите внимание, что как Token Program, так и Token Extension Program используют одну и ту же базовую реализацию для аккаунта минта.
Каждый токен в Solana имеет аккаунт минта, а адрес минта служит уникальным идентификатором токена.
Например, USD Coin (USDC) имеет адрес минта
EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v
. Этот адрес уникально
идентифицирует USDC во всей экосистеме Solana. Вы можете просмотреть этот минт
на
Solana Explorer.
Как создать аккаунт минта
Создание аккаунта минта требует использования инструкции
InitializeMint
.
Подробнее см. в
деталях реализации.
Для создания аккаунта минта необходимо выполнить две инструкции:
- System Program: Создать аккаунт с выделенным пространством для аккаунта минта и передать права собственности Token Program.
- Token Program: Инициализировать данные аккаунта минта.
Typescript
import {airdropFactory,appendTransactionMessageInstructions,createSolanaRpc,createSolanaRpcSubscriptions,createTransactionMessage,generateKeyPairSigner,getSignatureFromTransaction,lamports,pipe,sendAndConfirmTransactionFactory,setTransactionMessageFeePayerSigner,setTransactionMessageLifetimeUsingBlockhash,signTransactionMessageWithSigners} from "@solana/kit";import { getCreateAccountInstruction } from "@solana-program/system";import {getInitializeMintInstruction,getMintSize,TOKEN_PROGRAM_ADDRESS} from "@solana-program/token";// Create Connection, local validator in this exampleconst rpc = createSolanaRpc("http://localhost:8899");const rpcSubscriptions = createSolanaRpcSubscriptions("ws://localhost:8900");// Generate keypairs for fee payerconst feePayer = await generateKeyPairSigner();// Fund fee payerawait airdropFactory({ rpc, rpcSubscriptions })({recipientAddress: feePayer.address,lamports: lamports(1_000_000_000n),commitment: "confirmed"});// Generate keypair to use as address of mintconst mint = await generateKeyPairSigner();// Get default mint account size (in bytes), no extensions enabledconst space = BigInt(getMintSize());// Get minimum balance for rent exemptionconst rent = await rpc.getMinimumBalanceForRentExemption(space).send();// Instruction to create new account for mint (token program)// Invokes the system programconst createAccountInstruction = getCreateAccountInstruction({payer: feePayer,newAccount: mint,lamports: rent,space,programAddress: TOKEN_PROGRAM_ADDRESS});// Instruction to initialize mint account data// Invokes the token programconst initializeMintInstruction = getInitializeMintInstruction({mint: mint.address,decimals: 9,mintAuthority: feePayer.address});const instructions = [createAccountInstruction, initializeMintInstruction];// Get latest blockhash to include in transactionconst { value: latestBlockhash } = await rpc.getLatestBlockhash().send();// Create transaction messageconst transactionMessage = pipe(createTransactionMessage({ version: 0 }), // Create transaction message(tx) => setTransactionMessageFeePayerSigner(feePayer, tx), // Set fee payer(tx) => setTransactionMessageLifetimeUsingBlockhash(latestBlockhash, tx), // Set transaction blockhash(tx) => appendTransactionMessageInstructions(instructions, tx) // Append instructions);// Sign transaction message with required signers (fee payer and mint keypair)const signedTransaction =await signTransactionMessageWithSigners(transactionMessage);// Send and confirm transactionawait sendAndConfirmTransactionFactory({ rpc, rpcSubscriptions })(signedTransaction,{ commitment: "confirmed" });// Get transaction signatureconst transactionSignature = getSignatureFromTransaction(signedTransaction);console.log("Mint Address:", mint.address);console.log("\nTransaction Signature:", transactionSignature);
Console
Click to execute the code.
Rust
use anyhow::Result;use solana_client::nonblocking::rpc_client::RpcClient;use solana_sdk::{commitment_config::CommitmentConfig,program_pack::Pack,signature::{Keypair, Signer},system_instruction::create_account,transaction::Transaction,};use spl_token::{id as token_program_id, instruction::initialize_mint, state::Mint};#[tokio::main]async fn main() -> Result<()> {// Create connection to local validatorlet client = RpcClient::new_with_commitment(String::from("http://localhost:8899"),CommitmentConfig::confirmed(),);let latestBlockhash = client.get_latest_blockhash().await?;// Generate a new keypair for the fee payerlet fee_payer = Keypair::new();// Airdrop 1 SOL to fee payerlet airdrop_signature = client.request_airdrop(&fee_payer.pubkey(), 1_000_000_000).await?;client.confirm_transaction(&airdrop_signature).await?;loop {let confirmed = client.confirm_transaction(&airdrop_signature).await?;if confirmed {break;}}// Generate keypair to use as address of mintlet mint = Keypair::new();let space = Mint::LEN;let rent = client.get_minimum_balance_for_rent_exemption(space).await?;// Create account instructionlet create_account_instruction = create_account(&fee_payer.pubkey(),&mint.pubkey(),rent,space as u64,&token_program_id(),);// Initialize mint instructionlet initialize_mint_instruction = initialize_mint(&token_program_id(),&mint.pubkey(), // mint address&fee_payer.pubkey(), // mint authoritySome(&fee_payer.pubkey()), // freeze authority9, // decimals)?;// Create transaction and add instructionslet transaction = Transaction::new_signed_with_payer(&[create_account_instruction, initialize_mint_instruction],Some(&fee_payer.pubkey()),&[&fee_payer, &mint],latestBlockhash,);// Send and confirm transactionlet transaction_signature = client.send_and_confirm_transaction(&transaction).await?;println!("Mint Address: {}", mint.pubkey());println!("\nTransaction Signature: {}", transaction_signature);Ok(())}
Console
Click to execute the code.
Python
Python
#!/usr/bin/env python3import asynciofrom solana.rpc.async_api import AsyncClientfrom solders.keypair import Keypairfrom solders.transaction import VersionedTransactionfrom solders.message import MessageV0from solders.system_program import create_account, CreateAccountParamsfrom spl.token.instructions import initialize_mint, InitializeMintParamsfrom spl.token.constants import TOKEN_PROGRAM_ID# ConstantsDECIMALS = 9async def create_mint(rpc, mint_authority):"""Creates and initializes a new mint account"""mint = Keypair()space = 82 # getMintSize() equivalent for SPL Token# Get minimum balance for rent exemptionrent = await rpc.get_minimum_balance_for_rent_exemption(space)# Create & initialize mint accountcreate_account_instruction = create_account(CreateAccountParams(from_pubkey=mint_authority.pubkey(),to_pubkey=mint.pubkey(),lamports=rent.value,space=space,owner=TOKEN_PROGRAM_ID))initialize_mint_instruction = initialize_mint(InitializeMintParams(program_id=TOKEN_PROGRAM_ID,mint=mint.pubkey(),decimals=DECIMALS,mint_authority=mint_authority.pubkey(),freeze_authority=None))instructions = [create_account_instruction,initialize_mint_instruction]# Get latest blockhashlatest_blockhash = await rpc.get_latest_blockhash()# Create messagetransaction_message = MessageV0.try_compile(payer=mint_authority.pubkey(),instructions=instructions,address_lookup_table_accounts=[],recent_blockhash=latest_blockhash.value.blockhash)# Create and sign transactionsigned_transaction = VersionedTransaction(transaction_message, [mint_authority, mint])print("Mint account created successfully")print(f"Mint: {mint.pubkey()}")print(f"Mint Authority: {mint_authority.pubkey()}")print(f"Decimals: {DECIMALS}")return mint.pubkey()async def main():rpc = AsyncClient("http://localhost:8899")# Constantsmint_authority = Keypair()async with rpc:# Create mint accountawait create_mint(rpc, mint_authority)if __name__ == "__main__":asyncio.run(main())
Console
Click to execute the code.
Is this page helpful?