关键词:Solana、智能合约、开发网、合约部署、BPF 编译、Rust、Solana CLI
一、准备工作:工具与环境检查
在进入实操之前,先确保你已在本地完整安装 Solana CLI(包含秘钥生成器 solana-keygen 与编译工具集)。执行以下命令快速验证:
solana --version
cargo --version若提示找不到命令,请先回到官方文档完成安装,再继续阅读。——工具 OK,就可以开始实战了。
二、连接 Solana 开发网(Devnet)
主网节点的维护成本高、上链费用大,Solana 官方提供了与主网逻辑一致的 开发网(Devnet) 作为沙盒。你只须一条指令切换:
solana config set --url https://devnet.solana.com执行完毕后会看到:
RPC URL: https://devnet.solana.com
WebSocket URL: wss://devnet.solana.com/网络重置后,默认向开发网发出所有 solana 子命令。👉 还没装好节点环境?这里把安装环境踩坑点一次说清
三、准备账号:支付账号 + 程序账号
每个 Onchain Program 实质也是一个 Account,但标记为 executable: true。要把它写进链,需要先创建:
支付账号:存 SOL 付租金与 gas。
solana-keygen new solana-keygen pubkey ~/.config/solana/id.json示例公钥:
7FqW6xXE4sMmZSeVxFsoTr83He4MhhePvA1vRAv9zgQf给支付账号领测试 SOL:
solana airdrop 10 7FqW6xXE4sMmZSeVxFsoTr83He4MhhePvA1vRAv9zgQf solana balance 7FqW6xXE4sMmZSeVxFsoTr83He4MhhePvA1vRAv9zgQf # 验证程序账号:核心文件发布的地址。
solana-keygen new -o solana_memo_program.json
保存好 solana_memo_program.json,一会用于部署。
四、编译合约:memo 示例实战
官方提供了完整示例仓库:
git clone https://github.com/solana-labs/solana-program-library.git
cd solana-program-library/memo/program
cargo build-bpf第一次编译时若遇到 cannot find Scrt1.o,安装 32 位扩展库即可:
sudo apt install gcc-multilib成功后会提示:
To deploy this program:
$ solana deploy .../spl_memo.so五、部署合约:一行指令上链
获取程序账号的公钥:
solana-keygen pubkey ~/solana_memo_program.json得到示例:D8Cnv1UcThay2WijWP4SQ8G683UuVsKPaZEU7TNVKW1j
正式上链:
solana deploy target/deploy/spl_memo.so ~/solana_memo_program.json日志中出现 { "programId": "D8Cnv1UcThay2WijWP4SQ8G683UuVsKPaZEU7TNVKW1j" } 即部署成功。
打开 Solana Explorer,切换网络至「Devnet」,粘贴上面程序地址即可查看合约详情。👉 把合约部署到主网前,这几个测试陷阱建议先来回避
六、前端调用:用 @solana/web3.js 发交易
初始化 Node 项目
yarn init -y yarn add @solana/web3.js新建
src/index.js:const solanaWeb3 = require('@solana/web3.js'); async function testMemo(connection, payerKeypair) { const ix = new solanaWeb3.TransactionInstruction({ keys: [], programId: new solanaWeb3.PublicKey('D8Cnv1UcThay2WijWP4SQ8G683UuVsKPaZEU7TNVKW1j'), data: Buffer.from('cztest') }); await solanaWeb3.sendAndConfirmTransaction( connection, new solanaWeb3.Transaction().add(ix), [payerKeypair], { skipPreflight: true, commitment: "singleGossip" } ); console.log('done'); } async function main() { const connection = new solanaWeb3.Connection('https://devnet.solana.com', 'singleGossip'); const payerKeypair = new solanaWeb3.Keypair(); await connection.requestAirdrop(payerKeypair.publicKey, 10 * 1e9); testMemo(connection, payerKeypair); } main();
运行后,前端先空投 10 SOL,再向程序发送 cztest;链上记录 hex: 637a74657374,翻译回来正是 cztest,调用成功。
七、手写一个新合约
多次跑示例后,如何从零构建自己的合约?流程几乎与普通 Rust 库无异:
1. 新建项目
cargo new onchain_program2. 修改 Cargo.toml
[package]
name = "onchain_program"
version = "0.1.0"
edition = "2021"
[lib]
crate-type = ["cdylib"]
[dependencies]
solana-program = "1.4"新增 Xargo.toml 指定 BPF 目标:
[target.bpfel-unknown-unknown.dependencies.std]
features = []3. 编写代码
src/lib.rs 定义入口:
use solana_program::{
account_info::AccountInfo, entrypoint, entrypoint::ProgramResult,
program_error::ProgramError, pubkey::Pubkey,
};
entrypoint!(process_instruction);
pub fn process_instruction(
_program_id: &Pubkey,
_accounts: &[AccountInfo],
_instruction_data: &[u8],
) -> ProgramResult {
Ok(())
}至此,「不做事直接返回成功」的最小合约就写好了。
4. 编译
cd onchain_program
cargo build-bpf控制台输出路径后,复制 .so 使用前述 solana deploy 命令即可一键上链。
八、FAQ:开发者最常问的几件事
Q1:开发网 SOL 领完了怎么办?
A:Solana 官方每天提供 2 SOL 的自动水龙头,如需大额可直接换账号或等待下次重置。
Q2:为何一定要 32 位依赖?
A:目前的 BPF 编译工具链仍依赖 32 bit glibc 支持,安装 gcc-multilib 即可解决。
Q3:主网与开发网的 Program 大小限制一致吗?
A:一致,均为 1232 bytes;超出需做压缩或分片,详见 max-retuned-data 字段。
Q4:Rust 特性全部可用吗?
A:不是。标准库部分功能(如 std::thread)在 BPF 运行时被裁剪,完整限制可阅读官方Rust-limitations。
Q5:前端交易确认慢怎么优化?
A:在 @solana/web3.js 中启用 processed 级别的 commitment,可显著缩短确认延迟;正式上线前再切回 confirmed 或 finalized 以保证安全性。
Q6:部署后还能更新合约吗?
A:不可直接更新。Solana Program 是一旦上链即不可修改,需要采用「升级代理合约方案」或重新部署新地址并迁移资产。
总结:从环境、账号、编译到部署再到前端调用,这篇文章帮你走完 Solana 智能合约的最小闭环。掌握工具链核心原理后,无论是写 AMM、NFT 还是游戏链逻辑,都只是换接口、换业务的数据结构而已。祝你在 Solana 生态里代码一路绿灯!