Solana-programma's worden voornamelijk ontwikkeld met de programmeertaal Rust. Deze pagina richt zich op het schrijven van Solana-programma's in Rust zonder gebruik te maken van het Anchor-framework, een aanpak die vaak wordt aangeduid als het schrijven van "native Rust"-programma's.
Native Rust-ontwikkeling geeft ontwikkelaars directe controle over hun Solana-programma's. Deze aanpak vereist echter meer handmatige setup en boilerplate-code in vergelijking met het gebruik van het Anchor-framework. Deze methode wordt aanbevolen voor ontwikkelaars die:
- Gedetailleerde controle over programmalogica en optimalisaties zoeken
- De onderliggende concepten willen leren voordat ze overstappen naar frameworks op hoger niveau
Voor beginners raden we aan om te beginnen met het Anchor-framework. Zie de sectie Anchor voor meer informatie.
Vereisten
Voor gedetailleerde installatie-instructies, bezoek de pagina installatie.
Voordat je begint, zorg ervoor dat je het volgende hebt geïnstalleerd:
- Rust: de programmeertaal voor het bouwen van Solana-programma's.
- Solana CLI: commandoregeltool voor Solana-ontwikkeling.
Aan de slag
Het onderstaande voorbeeld behandelt de basisstappen om je eerste Solana-programma in Rust te maken. We maken een minimaal programma dat "Hello, world!" naar de programmalog schrijft.
Maak een nieuw programma
Maak eerst een nieuw Rust-project aan met het standaard cargo new-commando met
de vlag --lib.
$cargo new hello_world --lib
Navigeer naar de projectmap. Je zou de standaard src/lib.rs- en
Cargo.toml-bestanden moeten zien
$cd hello_world
Werk het edition veld bij in Cargo.toml naar 2021. Anders kun je een
foutmelding krijgen bij het bouwen van het programma.
Voeg de solana-program dependency toe
Voeg vervolgens de solana-program dependency toe. Dit is de minimale
dependency die nodig is om een Solana-programma te bouwen.
$cargo add solana-program@2.2.0
Voeg het crate-type toe
Voeg vervolgens het volgende fragment toe aan Cargo.toml.
[lib]crate-type = ["cdylib", "lib"]
Als je deze configuratie niet toevoegt, wordt de target/deploy directory
niet gegenereerd wanneer je het programma bouwt.
Je Cargo.toml bestand zou er als volgt uit moeten zien:
[package]name = "hello_world"version = "0.1.0"edition = "2021"[lib]crate-type = ["cdylib", "lib"][dependencies]solana-program = "2.2.0"
Voeg de programmacode toe
Vervang vervolgens de inhoud van src/lib.rs met de volgende code. Dit is een
minimaal Solana-programma dat "Hello, world!" naar het programmalogboek schrijft
wanneer het programma wordt aangeroepen.
De msg! macro wordt gebruikt in Solana-programma's om een bericht naar het
programmalogboek te schrijven.
use solana_program::{account_info::AccountInfo, entrypoint, entrypoint::ProgramResult, msg, pubkey::Pubkey,};entrypoint!(process_instruction);pub fn process_instruction(_program_id: &Pubkey,_accounts: &[AccountInfo],_instruction_data: &[u8],) -> ProgramResult {msg!("Hello, world!");Ok(())}
Bouw het programma
Bouw vervolgens het programma met het cargo build-sbf commando.
$cargo build-sbf
Dit commando genereert een target/deploy directory met twee belangrijke
bestanden:
- Een
.sobestand (bijv.hello_world.so): Dit is het gecompileerde Solana-programma dat als "smart contract" naar het netwerk wordt geïmplementeerd. - Een keypair-bestand (bijv.
hello_world-keypair.json): De publieke sleutel van dit keypair wordt gebruikt als programma-ID bij het implementeren van het programma.
Om de programma-ID te bekijken, voer je het volgende commando uit in je terminal. Dit commando print de publieke sleutel van het keypair op het opgegeven bestandspad:
$solana address -k ./target/deploy/hello_world-keypair.json
Voorbeelduitvoer:
4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz
Voeg testafhankelijkheden toe
Test vervolgens het programma met behulp van de litesvm crate. Voeg de
volgende afhankelijkheden toe aan Cargo.toml.
$cargo add litesvm@0.6.1 --dev$cargo add solana-sdk@2.2.0 --dev
Test het programma
Voeg de volgende test toe aan src/lib.rs, onder de programmacode. Dit is een
testmodule die het hello world-programma aanroept.
use solana_program::{account_info::AccountInfo, entrypoint, entrypoint::ProgramResult, msg, pubkey::Pubkey,};entrypoint!(process_instruction);pub fn process_instruction(_program_id: &Pubkey,_accounts: &[AccountInfo],_instruction_data: &[u8],) -> ProgramResult {msg!("Hello, world!");Ok(())}#[cfg(test)]mod test {use litesvm::LiteSVM;use solana_sdk::{instruction::Instruction,message::Message,signature::{Keypair, Signer},transaction::Transaction,};#[test]fn test_hello_world() {// Create a new LiteSVM instancelet mut svm = LiteSVM::new();// Create a keypair for the transaction payerlet payer = Keypair::new();// Airdrop some lamports to the payersvm.airdrop(&payer.pubkey(), 1_000_000_000).unwrap();// Load our programlet program_keypair = Keypair::new();let program_id = program_keypair.pubkey();svm.add_program_from_file(program_id, "target/deploy/hello_world.so").unwrap();// Create instruction with no accounts and no datalet instruction = Instruction {program_id,accounts: vec![],data: vec![],};// Create transactionlet message = Message::new(&[instruction], Some(&payer.pubkey()));let transaction = Transaction::new(&[&payer], message, svm.latest_blockhash());// Send transaction and verify it succeedslet result = svm.send_transaction(transaction);assert!(result.is_ok(), "Transaction should succeed");let logs = result.unwrap().logs;println!("Logs: {logs:#?}");}}
Voer de test uit met het cargo test commando. Het programmalogboek zal "Hello,
world!" weergeven.
$cargo test -- --no-capture
Voorbeelduitvoer:
running 1 testLogs: ["Program 9528phXNvdWp5kkR4rgpoeZvR8ZWT5THVywK95YRprkk invoke [1]","Program log: Hello, world!","Program 9528phXNvdWp5kkR4rgpoeZvR8ZWT5THVywK95YRprkk consumed 211 of 200000 compute units","Program 9528phXNvdWp5kkR4rgpoeZvR8ZWT5THVywK95YRprkk success",]test test::test_hello_world ... oktest result: ok. 1 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out; finished in 0.05s
Deploy het programma
Deploy vervolgens het programma. Bij lokale ontwikkeling kunnen we de
solana-test-validator gebruiken.
Configureer eerst de Solana CLI om het lokale Solana-cluster te gebruiken.
$solana config set -ul
Voorbeelduitvoer:
Config File: /.config/solana/cli/config.ymlRPC URL: http://localhost:8899WebSocket URL: ws://localhost:8900/ (computed)Keypair Path: /.config/solana/id.jsonCommitment: confirmed
Open een nieuwe terminal en voer het solana-test-validators commando uit om de
lokale validator te starten.
$solana-test-validator
Terwijl de testvalidator draait, voer je het solana program deploy commando
uit in een aparte terminal om het programma te deployen naar de lokale
validator.
$solana program deploy ./target/deploy/hello_world.so
Voorbeelduitvoer:
Program Id: 4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMzSignature:5osMiNMiDZGM7L1e2tPHxU8wdB8gwG8fDnXLg5G7SbhwFz4dHshYgAijk4wSQL5cXiu8z1MMou5kLadAQuHp7ybH
Je kunt de programma-ID en transactiehandtekening inspecteren op Solana Explorer.
Let op dat de cluster op Solana Explorer ook localhost moet zijn. De "Custom
RPC URL" optie op Solana Explorer staat standaard op http://localhost:8899.
Maak een voorbeeldclient
Vervolgens laten we zien hoe je het programma aanroept met een Rust-client.
Maak eerst een examples map en een client.rs bestand.
$mkdir -p examples && touch examples/client.rs
Voeg het volgende toe aan Cargo.toml.
[[example]]name = "client"path = "examples/client.rs"
Voeg solana-client en tokio dependencies toe.
$cargo add solana-client@2.2.0 --dev$cargo add tokio --dev
Voeg de client toe
Voeg de volgende code toe aan examples/client.rs. Dit is een Rust-clientscript
dat een nieuw keypair financiert om transactiekosten te betalen en vervolgens
het hello world-programma aanroept.
use solana_client::rpc_client::RpcClient;use solana_sdk::{commitment_config::CommitmentConfig,instruction::Instruction,pubkey::Pubkey,signature::{Keypair, Signer},transaction::Transaction,};use std::str::FromStr;#[tokio::main]async fn main() {// Program ID (replace with your actual program ID)let program_id = Pubkey::from_str("4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz").unwrap();// Connect to the Solana devnetlet rpc_url = String::from("http://localhost:8899");let client = RpcClient::new_with_commitment(rpc_url, CommitmentConfig::confirmed());// Generate a new keypair for the payerlet payer = Keypair::new();// Request airdroplet airdrop_amount = 1_000_000_000; // 1 SOLlet signature = client.request_airdrop(&payer.pubkey(), airdrop_amount).expect("Failed to request airdrop");// Wait for airdrop confirmationloop {let confirmed = client.confirm_transaction(&signature).unwrap();if confirmed {break;}}// Create the instructionlet instruction = Instruction::new_with_borsh(program_id,&(), // Empty instruction datavec![], // No accounts needed);// Add the instruction to new transactionlet mut transaction = Transaction::new_with_payer(&[instruction], Some(&payer.pubkey()));transaction.sign(&[&payer], client.get_latest_blockhash().unwrap());// Send and confirm the transactionmatch client.send_and_confirm_transaction(&transaction) {Ok(signature) => println!("Transaction Signature: {}", signature),Err(err) => eprintln!("Error sending transaction: {}", err),}}
Vervang de programma-ID
Voordat je de clientcode uitvoert, vervang je de programma-ID in het codefragment met die van jouw programma.
Je kunt je programma-ID verkrijgen door het volgende commando uit te voeren.
$solana address -k ./target/deploy/hello_world-keypair.json
Roep het programma aan
Voer het clientscript uit met het volgende commando.
$cargo run --example client
Voorbeelduitvoer:
Transaction Signature: 54TWxKi3Jsi3UTeZbhLGUFX6JQH7TspRJjRRFZ8NFnwG5BXM9udxiX77bAACjKAS9fGnVeEazrXL4SfKrW7xZFYV
Je kunt de transactiehandtekening bekijken op Solana Explorer (lokale cluster) om "Hello, world!" in het programmalogboek te zien.
Update het programma
Solana-programma's kunnen worden bijgewerkt door opnieuw te implementeren naar
dezelfde programma-ID. Update het programma in src/lib.rs om "Hello, Solana!"
af te drukken in plaats van "Hello, world!".
pub fn process_instruction(_program_id: &Pubkey,_accounts: &[AccountInfo],_instruction_data: &[u8],) -> ProgramResult {-msg!("Hello, world!");+msg!("Hello, Solana!");Ok(())}
Voer het cargo build-sbf commando uit om een bijgewerkt .so bestand te
genereren.
$cargo build-sbf
Test het bijgewerkte programma door het cargo test commando uit te voeren.
$cargo test -- --no-capture
Je zou "Hello, Solana!" moeten zien in het programmalogboek.
running 1 testLogs: ["Program 5y8bHrnwfq2dLDgLn3WoTHb9dDuyorj9gyapW6aeyrpV invoke [1]","Program log: Hello, Solana!","Program 5y8bHrnwfq2dLDgLn3WoTHb9dDuyorj9gyapW6aeyrpV consumed 211 of 200000 compute units","Program 5y8bHrnwfq2dLDgLn3WoTHb9dDuyorj9gyapW6aeyrpV success",]test test::test_hello_world ... oktest result: ok. 1 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out; finished in 0.08s
Implementeer het programma opnieuw
Implementeer het programma opnieuw met hetzelfde solana program deploy
commando.
$solana program deploy ./target/deploy/hello_world.so
Voer de clientcode opnieuw uit en bekijk de transactiehandtekening op Solana Explorer om "Hello, Solana!" in het programmalogboek te zien.
$cargo run --example client
Sluit het programma
Je kunt je Solana-programma sluiten om de SOL die aan het account is toegewezen terug te vorderen. Het sluiten van een programma is onomkeerbaar, dus dit moet met voorzichtigheid worden gedaan.
Om een programma te sluiten, gebruik je het solana program close <PROGRAM_ID>
commando. Bijvoorbeeld:
$solana program close 4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz --bypass-warning
Voorbeelduitvoer:
Closed Program Id 4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz, 0.1350588 SOLreclaimed
Merk op dat zodra een programma is gesloten, de programma-ID niet opnieuw kan worden gebruikt. Een poging om een programma te implementeren met een eerder gesloten programma-ID zal resulteren in een foutmelding.
Error: Program 4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz has been closed, usea new Program Id
Een gesloten programma opnieuw implementeren
Als je een programma met dezelfde broncode opnieuw moet implementeren na het sluiten van een programma, moet je een nieuwe programma-ID genereren. Om een nieuw keypair voor het programma te genereren, voer je het volgende commando uit:
$solana-keygen new -o ./target/deploy/hello_world-keypair.json --force
Als alternatief kun je het bestaande keypair-bestand (bijv.
./target/deploy/hello_world-keypair.json) verwijderen en cargo build-sbf
opnieuw uitvoeren, wat een nieuw keypair-bestand zal genereren.
Is this page helpful?