Документація SolanaРозробка програм

Розробка програм на Rust

Програми Solana переважно розробляються за допомогою мови програмування Rust. Ця сторінка зосереджена на написанні програм Solana на Rust без використання фреймворку Anchor, підхід, який часто називають написанням програм на "нативному Rust".

Розробка на нативному Rust надає розробникам прямий контроль над їхніми програмами Solana. Однак цей підхід вимагає більше ручного налаштування та шаблонного коду порівняно з використанням фреймворку Anchor. Цей метод рекомендується для розробників, які:

  • Прагнуть детального контролю над логікою програми та оптимізаціями
  • Хочуть вивчити основні концепції перед переходом до фреймворків вищого рівня

Для початківців ми рекомендуємо почати з фреймворку Anchor. Дивіться розділ Anchor для отримання додаткової інформації.

Передумови

Для детальних інструкцій з встановлення відвідайте сторінку встановлення.

Перш ніж почати, переконайтеся, що у вас встановлено наступне:

  • Rust: Мова програмування для створення програм Solana.
  • Solana CLI: Інструмент командного рядка для розробки на Solana.

Початок роботи

Приклад нижче охоплює основні кроки для створення вашої першої програми Solana, написаної на Rust. Ми створимо мінімальну програму, яка виводить "Hello, world!" у журнал програми.

Створення нової програми

Спочатку створіть новий Rust-проєкт, використовуючи стандартну команду cargo new з прапорцем --lib.

Terminal
$
cargo new hello_world --lib

Перейдіть до директорії проєкту. Ви побачите стандартні файли src/lib.rs та Cargo.toml

Terminal
$
cd hello_world

Оновіть поле edition у файлі Cargo.toml на 2021. Інакше ви можете зіткнутися з помилкою під час збірки програми.

Додайте залежність solana-program

Далі додайте залежність solana-program. Це мінімальна залежність, необхідна для збірки програми Solana.

Terminal
$
cargo add solana-program@2.2.0

Додайте crate-type

Далі додайте наступний фрагмент до Cargo.toml.

Cargo.toml
[lib]
crate-type = ["cdylib", "lib"]

Якщо ви не включите цю конфігурацію, директорія target/deploy не буде згенерована під час збірки програми.

Ваш файл Cargo.toml повинен виглядати наступним чином:

Cargo.toml
[package]
name = "hello_world"
version = "0.1.0"
edition = "2021"
[lib]
crate-type = ["cdylib", "lib"]
[dependencies]
solana-program = "2.2.0"

Додайте код програми

Далі замініть вміст файлу src/lib.rs наступним кодом. Це мінімальна програма Solana, яка виводить "Hello, world!" у лог програми, коли програма викликається.

Макрос msg! використовується в програмах Solana для виведення повідомлення в лог програми.

src/lib.rs
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(())
}

Зберіть програму

Далі зберіть програму, використовуючи команду cargo build-sbf.

Terminal
$
cargo build-sbf

Ця команда генерує директорію target/deploy, що містить два важливі файли:

  1. Файл .so (наприклад, hello_world.so): це скомпільована програма Solana, яка буде розгорнута в мережі як "смарт-контракт".
  2. Файл keypair (наприклад, hello_world-keypair.json): публічний ключ цього keypair використовується як ідентифікатор програми під час її розгортання.

Щоб переглянути ідентифікатор програми, виконайте наступну команду в терміналі. Ця команда виводить публічний ключ keypair за вказаним шляхом до файлу:

Terminal
$
solana address -k ./target/deploy/hello_world-keypair.json

Приклад виводу:

4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz

Додайте тестові залежності

Далі протестуйте програму за допомогою крейту litesvm. Додайте наступні залежності до Cargo.toml.

Terminal
$
cargo add litesvm@0.6.1 --dev
$
cargo add solana-sdk@2.2.0 --dev

Протестуйте програму

Додайте наступний тест до src/lib.rs, нижче коду програми. Це тестовий модуль, який викликає програму hello world.

src/lib.rs
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 instance
let mut svm = LiteSVM::new();
// Create a keypair for the transaction payer
let payer = Keypair::new();
// Airdrop some lamports to the payer
svm.airdrop(&payer.pubkey(), 1_000_000_000).unwrap();
// Load our program
let 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 data
let instruction = Instruction {
program_id,
accounts: vec![],
data: vec![],
};
// Create transaction
let message = Message::new(&[instruction], Some(&payer.pubkey()));
let transaction = Transaction::new(&[&payer], message, svm.latest_blockhash());
// Send transaction and verify it succeeds
let result = svm.send_transaction(transaction);
assert!(result.is_ok(), "Transaction should succeed");
let logs = result.unwrap().logs;
println!("Logs: {logs:#?}");
}
}

Запустіть тест за допомогою команди cargo test. Лог програми відобразить "Hello, world!".

Terminal
$
cargo test -- --no-capture

Приклад виводу:

Terminal
running 1 test
Logs: [
"Program 9528phXNvdWp5kkR4rgpoeZvR8ZWT5THVywK95YRprkk invoke [1]",
"Program log: Hello, world!",
"Program 9528phXNvdWp5kkR4rgpoeZvR8ZWT5THVywK95YRprkk consumed 211 of 200000 compute units",
"Program 9528phXNvdWp5kkR4rgpoeZvR8ZWT5THVywK95YRprkk success",
]
test test::test_hello_world ... ok
test result: ok. 1 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out; finished in 0.05s

Розгорніть програму

Далі розгорніть програму. Під час локальної розробки ми можемо використовувати solana-test-validator.

Спочатку налаштуйте Solana CLI для використання локального кластера Solana.

Terminal
$
solana config set -ul

Приклад виводу:

Config File: /.config/solana/cli/config.yml
RPC URL: http://localhost:8899
WebSocket URL: ws://localhost:8900/ (computed)
Keypair Path: /.config/solana/id.json
Commitment: confirmed

Відкрийте новий термінал і виконайте команду solana-test-validators, щоб запустити локальний validator.

Terminal
$
solana-test-validator

Поки тестовий validator працює, виконайте команду solana program deploy в окремому терміналі, щоб розгорнути програму на локальному validator.

Terminal
$
solana program deploy ./target/deploy/hello_world.so

Приклад виводу:

Program Id: 4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz
Signature:
5osMiNMiDZGM7L1e2tPHxU8wdB8gwG8fDnXLg5G7SbhwFz4dHshYgAijk4wSQL5cXiu8z1MMou5kLadAQuHp7ybH

Ви можете переглянути ідентифікатор програми та підпис транзакції в Solana Explorer.

Зверніть увагу, що кластер у Solana Explorer також має бути localhost. Опція "Custom RPC URL" у Solana Explorer за замовчуванням встановлена на http://localhost:8899.

Створення прикладу клієнта

Далі ми продемонструємо, як викликати програму за допомогою клієнта на Rust.

Спочатку створіть директорію examples та файл client.rs.

Terminal
$
mkdir -p examples && touch examples/client.rs

Додайте наступне до Cargo.toml.

Cargo.toml
[[example]]
name = "client"
path = "examples/client.rs"

Додайте залежності solana-client та tokio.

Terminal
$
cargo add solana-client@2.2.0 --dev
$
cargo add tokio --dev

Додавання клієнта

Додайте наступний код до examples/client.rs. Це клієнтський скрипт на Rust, який фінансує новий keypair для оплати комісій за транзакції, а потім викликає програму hello world.

examples/client.rs
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 devnet
let rpc_url = String::from("http://localhost:8899");
let client = RpcClient::new_with_commitment(rpc_url, CommitmentConfig::confirmed());
// Generate a new keypair for the payer
let payer = Keypair::new();
// Request airdrop
let airdrop_amount = 1_000_000_000; // 1 SOL
let signature = client
.request_airdrop(&payer.pubkey(), airdrop_amount)
.expect("Failed to request airdrop");
// Wait for airdrop confirmation
loop {
let confirmed = client.confirm_transaction(&signature).unwrap();
if confirmed {
break;
}
}
// Create the instruction
let instruction = Instruction::new_with_borsh(
program_id,
&(), // Empty instruction data
vec![], // No accounts needed
);
// Add the instruction to new transaction
let mut transaction = Transaction::new_with_payer(&[instruction], Some(&payer.pubkey()));
transaction.sign(&[&payer], client.get_latest_blockhash().unwrap());
// Send and confirm the transaction
match client.send_and_confirm_transaction(&transaction) {
Ok(signature) => println!("Transaction Signature: {}", signature),
Err(err) => eprintln!("Error sending transaction: {}", err),
}
}

Заміна ідентифікатора програми

Перед запуском клієнтського коду замініть ідентифікатор програми у фрагменті коду на той, що відповідає вашій програмі.

Ви можете отримати ідентифікатор вашої програми, виконавши наступну команду.

Terminal
$
solana address -k ./target/deploy/hello_world-keypair.json

Виклик програми

Запустіть клієнтський скрипт за допомогою наступної команди.

Terminal
$
cargo run --example client

Приклад виводу:

Transaction Signature: 54TWxKi3Jsi3UTeZbhLGUFX6JQH7TspRJjRRFZ8NFnwG5BXM9udxiX77bAACjKAS9fGnVeEazrXL4SfKrW7xZFYV

Ви можете перевірити підпис транзакції в Solana Explorer (локальний кластер), щоб побачити "Hello, world!" у журналі програми.

Оновлення програми

Програми Solana можна оновлювати, повторно розгортаючи їх за тим самим ідентифікатором програми. Оновіть програму в src/lib.rs, щоб вона виводила "Hello, Solana!" замість "Hello, world!".

lib.rs
pub fn process_instruction(
_program_id: &Pubkey,
_accounts: &[AccountInfo],
_instruction_data: &[u8],
) -> ProgramResult {
-
msg!("Hello, world!");
+
msg!("Hello, Solana!");
Ok(())
}

Виконайте команду cargo build-sbf, щоб згенерувати оновлений файл .so.

Terminal
$
cargo build-sbf

Протестуйте оновлену програму, виконавши команду cargo test.

Terminal
$
cargo test -- --no-capture

Ви повинні побачити "Hello, Solana!" у журналі програми.

Terminal
running 1 test
Logs: [
"Program 5y8bHrnwfq2dLDgLn3WoTHb9dDuyorj9gyapW6aeyrpV invoke [1]",
"Program log: Hello, Solana!",
"Program 5y8bHrnwfq2dLDgLn3WoTHb9dDuyorj9gyapW6aeyrpV consumed 211 of 200000 compute units",
"Program 5y8bHrnwfq2dLDgLn3WoTHb9dDuyorj9gyapW6aeyrpV success",
]
test test::test_hello_world ... ok
test result: ok. 1 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out; finished in 0.08s

Повторне розгортання програми

Повторно розгорніть програму, використовуючи ту саму команду solana program deploy.

Terminal
$
solana program deploy ./target/deploy/hello_world.so

Запустіть клієнтський код знову та перевірте підпис транзакції в Solana Explorer, щоб побачити "Hello, Solana!" у журналі програми.

Terminal
$
cargo run --example client

Закриття програми

Ви можете закрити свою програму Solana, щоб повернути SOL, виділений для облікового запису. Закриття програми є незворотним, тому це слід робити з обережністю.

Щоб закрити програму, використовуйте команду solana program close <PROGRAM_ID>. Наприклад:

Terminal
$
solana program close 4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz --bypass-warning

Приклад виводу:

Closed Program Id 4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz, 0.1350588 SOL
reclaimed

Зверніть увагу, що після закриття програми її ідентифікатор програми не може бути використаний повторно. Спроба розгорнути програму з раніше закритим ідентифікатором програми призведе до помилки.

Error: Program 4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz has been closed, use
a new Program Id

Повторне розгортання закритої програми

Якщо вам потрібно повторно розгорнути програму з тим самим вихідним кодом після закриття програми, ви повинні згенерувати новий ідентифікатор програми. Щоб згенерувати нову keypair для програми, виконайте таку команду:

Terminal
$
solana-keygen new -o ./target/deploy/hello_world-keypair.json --force

Як альтернатива, ви можете видалити існуючий файл keypair (наприклад, ./target/deploy/hello_world-keypair.json) і запустити cargo build-sbf знову, що згенерує новий файл keypair.

Створення нової програми

Спочатку створіть новий Rust-проєкт, використовуючи стандартну команду cargo new з прапорцем --lib.

Terminal
$
cargo new hello_world --lib

Перейдіть до директорії проєкту. Ви побачите стандартні файли src/lib.rs та Cargo.toml

Terminal
$
cd hello_world

Оновіть поле edition у файлі Cargo.toml на 2021. Інакше ви можете зіткнутися з помилкою під час збірки програми.

Додайте залежність solana-program

Далі додайте залежність solana-program. Це мінімальна залежність, необхідна для збірки програми Solana.

Terminal
$
cargo add solana-program@2.2.0

Додайте crate-type

Далі додайте наступний фрагмент до Cargo.toml.

Cargo.toml
[lib]
crate-type = ["cdylib", "lib"]

Якщо ви не включите цю конфігурацію, директорія target/deploy не буде згенерована під час збірки програми.

Додайте код програми

Далі замініть вміст файлу src/lib.rs наступним кодом. Це мінімальна програма Solana, яка виводить "Hello, world!" у лог програми, коли програма викликається.

Макрос msg! використовується в програмах Solana для виведення повідомлення в лог програми.

Зберіть програму

Далі зберіть програму, використовуючи команду cargo build-sbf.

Terminal
$
cargo build-sbf

Ця команда генерує директорію target/deploy, що містить два важливі файли:

  1. Файл .so (наприклад, hello_world.so): це скомпільована програма Solana, яка буде розгорнута в мережі як "смарт-контракт".
  2. Файл keypair (наприклад, hello_world-keypair.json): публічний ключ цього keypair використовується як ідентифікатор програми під час її розгортання.

Щоб переглянути ідентифікатор програми, виконайте наступну команду в терміналі. Ця команда виводить публічний ключ keypair за вказаним шляхом до файлу:

Terminal
$
solana address -k ./target/deploy/hello_world-keypair.json

Приклад виводу:

4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz

Додайте тестові залежності

Далі протестуйте програму за допомогою крейту litesvm. Додайте наступні залежності до Cargo.toml.

Terminal
$
cargo add litesvm@0.6.1 --dev
$
cargo add solana-sdk@2.2.0 --dev

Протестуйте програму

Додайте наступний тест до src/lib.rs, нижче коду програми. Це тестовий модуль, який викликає програму hello world.

Запустіть тест за допомогою команди cargo test. Лог програми відобразить "Hello, world!".

Terminal
$
cargo test -- --no-capture

Приклад виводу:

Terminal
running 1 test
Logs: [
"Program 9528phXNvdWp5kkR4rgpoeZvR8ZWT5THVywK95YRprkk invoke [1]",
"Program log: Hello, world!",
"Program 9528phXNvdWp5kkR4rgpoeZvR8ZWT5THVywK95YRprkk consumed 211 of 200000 compute units",
"Program 9528phXNvdWp5kkR4rgpoeZvR8ZWT5THVywK95YRprkk success",
]
test test::test_hello_world ... ok
test result: ok. 1 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out; finished in 0.05s

Розгорніть програму

Далі розгорніть програму. Під час локальної розробки ми можемо використовувати solana-test-validator.

Спочатку налаштуйте Solana CLI для використання локального кластера Solana.

Terminal
$
solana config set -ul

Приклад виводу:

Config File: /.config/solana/cli/config.yml
RPC URL: http://localhost:8899
WebSocket URL: ws://localhost:8900/ (computed)
Keypair Path: /.config/solana/id.json
Commitment: confirmed

Відкрийте новий термінал і виконайте команду solana-test-validators, щоб запустити локальний validator.

Terminal
$
solana-test-validator

Поки тестовий validator працює, виконайте команду solana program deploy в окремому терміналі, щоб розгорнути програму на локальному validator.

Terminal
$
solana program deploy ./target/deploy/hello_world.so

Приклад виводу:

Program Id: 4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz
Signature:
5osMiNMiDZGM7L1e2tPHxU8wdB8gwG8fDnXLg5G7SbhwFz4dHshYgAijk4wSQL5cXiu8z1MMou5kLadAQuHp7ybH

Ви можете переглянути ідентифікатор програми та підпис транзакції в Solana Explorer.

Зверніть увагу, що кластер у Solana Explorer також має бути localhost. Опція "Custom RPC URL" у Solana Explorer за замовчуванням встановлена на http://localhost:8899.

Створення прикладу клієнта

Далі ми продемонструємо, як викликати програму за допомогою клієнта на Rust.

Спочатку створіть директорію examples та файл client.rs.

Terminal
$
mkdir -p examples && touch examples/client.rs

Додайте наступне до Cargo.toml.

Cargo.toml
[[example]]
name = "client"
path = "examples/client.rs"

Додайте залежності solana-client та tokio.

Terminal
$
cargo add solana-client@2.2.0 --dev
$
cargo add tokio --dev

Додавання клієнта

Додайте наступний код до examples/client.rs. Це клієнтський скрипт на Rust, який фінансує новий keypair для оплати комісій за транзакції, а потім викликає програму hello world.

Заміна ідентифікатора програми

Перед запуском клієнтського коду замініть ідентифікатор програми у фрагменті коду на той, що відповідає вашій програмі.

Ви можете отримати ідентифікатор вашої програми, виконавши наступну команду.

Terminal
$
solana address -k ./target/deploy/hello_world-keypair.json

Виклик програми

Запустіть клієнтський скрипт за допомогою наступної команди.

Terminal
$
cargo run --example client

Приклад виводу:

Transaction Signature: 54TWxKi3Jsi3UTeZbhLGUFX6JQH7TspRJjRRFZ8NFnwG5BXM9udxiX77bAACjKAS9fGnVeEazrXL4SfKrW7xZFYV

Ви можете перевірити підпис транзакції в Solana Explorer (локальний кластер), щоб побачити "Hello, world!" у журналі програми.

Оновлення програми

Програми Solana можна оновлювати, повторно розгортаючи їх за тим самим ідентифікатором програми. Оновіть програму в src/lib.rs, щоб вона виводила "Hello, Solana!" замість "Hello, world!".

lib.rs
pub fn process_instruction(
_program_id: &Pubkey,
_accounts: &[AccountInfo],
_instruction_data: &[u8],
) -> ProgramResult {
-
msg!("Hello, world!");
+
msg!("Hello, Solana!");
Ok(())
}

Виконайте команду cargo build-sbf, щоб згенерувати оновлений файл .so.

Terminal
$
cargo build-sbf

Протестуйте оновлену програму, виконавши команду cargo test.

Terminal
$
cargo test -- --no-capture

Ви повинні побачити "Hello, Solana!" у журналі програми.

Terminal
running 1 test
Logs: [
"Program 5y8bHrnwfq2dLDgLn3WoTHb9dDuyorj9gyapW6aeyrpV invoke [1]",
"Program log: Hello, Solana!",
"Program 5y8bHrnwfq2dLDgLn3WoTHb9dDuyorj9gyapW6aeyrpV consumed 211 of 200000 compute units",
"Program 5y8bHrnwfq2dLDgLn3WoTHb9dDuyorj9gyapW6aeyrpV success",
]
test test::test_hello_world ... ok
test result: ok. 1 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out; finished in 0.08s

Повторне розгортання програми

Повторно розгорніть програму, використовуючи ту саму команду solana program deploy.

Terminal
$
solana program deploy ./target/deploy/hello_world.so

Запустіть клієнтський код знову та перевірте підпис транзакції в Solana Explorer, щоб побачити "Hello, Solana!" у журналі програми.

Terminal
$
cargo run --example client

Закриття програми

Ви можете закрити свою програму Solana, щоб повернути SOL, виділений для облікового запису. Закриття програми є незворотним, тому це слід робити з обережністю.

Щоб закрити програму, використовуйте команду solana program close <PROGRAM_ID>. Наприклад:

Terminal
$
solana program close 4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz --bypass-warning

Приклад виводу:

Closed Program Id 4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz, 0.1350588 SOL
reclaimed

Зверніть увагу, що після закриття програми її ідентифікатор програми не може бути використаний повторно. Спроба розгорнути програму з раніше закритим ідентифікатором програми призведе до помилки.

Error: Program 4Ujf5fXfLx2PAwRqcECCLtgDxHKPznoJpa43jUBxFfMz has been closed, use
a new Program Id

Повторне розгортання закритої програми

Якщо вам потрібно повторно розгорнути програму з тим самим вихідним кодом після закриття програми, ви повинні згенерувати новий ідентифікатор програми. Щоб згенерувати нову keypair для програми, виконайте таку команду:

Terminal
$
solana-keygen new -o ./target/deploy/hello_world-keypair.json --force

Як альтернатива, ви можете видалити існуючий файл keypair (наприклад, ./target/deploy/hello_world-keypair.json) і запустити cargo build-sbf знову, що згенерує новий файл keypair.

lib.rs
Cargo.toml
[package]
name = "hello_world"
version = "0.1.0"
edition = "2021"
[dependencies]

Is this page helpful?

Зміст

Редагувати сторінку

Керується

© 2026 Фонд Solana.
Всі права захищені.
Залишайтеся на зв'язку