Rust EVM兼容库aurora-evm的使用:实现以太坊虚拟机功能与智能合约开发支持
Rust EVM兼容库aurora-evm的使用:实现以太坊虚拟机功能与智能合约开发支持
特性
- 独立运行 - 可以作为独立进程启动或集成到其他应用程序中
- 通用性 - 可用于任何EVM兼容链的生产环境
- 无状态 - 仅作为执行环境,连接到独立的状态存储
- 快速 - 主要关注性能
状态
生产就绪状态。由Aurora Labs支持并用于生产环境。
支持的以太坊硬分叉:
- Frontier
- Homestead
- Tangerine Whistle
- Spurious Dragon
- Byzantium
- Constantinople
- Istanbul
- Berlin
- London
- Paris (The Merge)
- Shanghai
- Cancun
- Prague
以太坊测试支持
- 100%支持Ethereum tests
- 100%支持Ethereum Execution Spec Tests
开始使用
在Cargo.toml
中添加以下依赖:
[dependencies]
aurora-evm = "2.0"
示例代码
以下是使用aurora-evm的基本示例:
use aurora_evm::executor::{Executor, ExecutorError};
use aurora_evm::transaction::Transaction;
use aurora_极简版的合约字节码仅用于示例
// 创建合约的ABI编码调用数据
const CONTRACT_CALLDATA: &[u8] = &[
0x6d, 0x4c, 0xe0, 0x63, // get() 函数选择器
];
fn main() -> Result<(), ExecutorError> {
// 初始化状态
let mut state = State::default();
// 创建发送者地址
let sender极简版的合约字节码仅用于示例
// 创建合约的ABI编码调用数据
const CONTRACT_CALLDATA: &[u8] = &[
0x6d, 0x4c, 0xe0, 0x63, // get() 函数选择器
];
fn main() -> Result<(), ExecutorError> {
// 初始化状态
let mut state = State::default();
// 创建发送者地址
let sender = Address::from([0x1; 20]);
// 1. 部署合约
let deploy_tx = Transaction {
nonce: 0,
gas_price: 100,
gas_limit: 1_000_000,
to: None, // 创建合约
value: 0,
data: CONTRACT_BYTECODE.to_vec(),
v: 0,
r: Default::default(),
s: Default::default(),
};
let executor = Executor::new();
let deploy_result = executor.execute_transaction(&mut state, &sender, &deploy_tx)?;
// 获取合约地址
let contract_address = deploy_result.created_address.unwrap();
println!("合约部署成功,地址: {:?}", contract_address);
// 2. 调用合约方法
let call_tx = Transaction {
nonce: 1,
gas_price: 100,
gas_limit极简版的合约字节码仅用于示例
// 创建合约的ABI编码调用数据
const CONTRACT_CALLDATA: &[u8] = &[
0x6d, 0x4c, 0xe极简版的合约字节码仅用于示例
// 创建合约的ABI编码调用数据
const CONTRACT_CALLDATA: &[u8] = &[
0x6d, 0x4c, 0xe0, 0x63, // get() 函数选择器
];
fn main() -> Result<(), ExecutorError> {
// 初始化状态
let mut state = State::default();
// 创建发送者地址
let sender = Address::from([0x1; 20]);
// 1. 部署合约
let deploy_tx = Transaction {
nonce: 0,
gas_price: 100,
gas_limit: 1_000_000,
to: None, // 创建合约
value: 0,
data: CONTRACT_BYTECODE.to_vec(),
v: 0,
r: Default::default(),
s: Default::default(),
};
let executor = Executor::new();
let deploy_result = executor.execute_transaction(&mut state, &sender, &deploy_tx)?;
// 获取合约地址
let contract_address = deploy_result.created_address.unwrap();
println!("合约部署成功,地址: {:?}", contract_address);
// 2. 调用合约方法
let call_tx = Transaction {
nonce: 1,
gas_price: 100,
gas_limit: 1_000_000,
to: Some(contract_address),
value: 0,
data: CONTRACT_CALLDATA.to_vec(),
v: 0,
r: Default::default(),
s: Default::default(),
};
let call_result = executor.execute_transaction(&mut state, &sender, &call_tx)?;
println!("调用结果: {:?}", call_result.output);
Ok(())
}
1 回复
Rust EVM兼容库aurora-evm使用指南
概述
aurora-evm是一个Rust实现的EVM(以太坊虚拟机)兼容库,它允许开发者在Rust环境中实现以太坊虚拟机功能并支持智能合约开发。这个库特别适合需要将EVM功能集成到Rust项目中的场景,如构建区块链节点、开发测试工具或创建跨链桥接服务。
主要特性
- 完整的EVM指令集实现
- 支持Solidity智能合约的执行
- 兼容以太坊交易和区块格式
- 可配置的Gas计算模型
- 灵活的存储后端支持
安装方法
在Cargo.toml中添加依赖:
[dependencies]
aurora-evm = "0.9.0" # 请检查最新版本
基本使用方法
1. 初始化EVM环境
use aurora_evm::{Engine, Config};
fn main() {
// 创建EVM配置
let config = Config::default();
// 初始化EVM引擎
let engine = Engine::new(config);
// 现在可以使用engine执行合约或交易
}
2. 执行简单的合约调用
use aurora_evm::{Engine, Config, Transaction, U256};
fn execute_simple_transaction() {
let config = Config::default();
let mut engine = Engine::new(config);
// 创建一个简单交易
let tx = Transaction {
nonce: U256::zero(),
gas_price: U256::from(100),
gas_limit: U256::from(100000),
to: Some([0u8; 20].into()), // 合约地址
value: U256::zero(),
input: vec![], // 调用数据
signature: None, // 签名信息
};
// 执行交易
let result = engine.execute_transaction(tx);
println!("Execution result: {:?}", result);
}
3. 部署和执行智能合约
use aurora_evm::{Engine, Config, Transaction, U256};
use hex_literal::hex;
fn deploy_and_execute_contract() {
let config = Config::default();
let mut engine = Engine::new(config);
// Solidity合约的字节码 (简单的加法合约)
let contract_bytecode = hex!("608060405234801561001057600080fd5b5060b08061001f6000396000f3fe6080604052348015600f57600080fd5b506004361060325760003560e01c806360fe47b11460375780636d4ce63c146053575b600080fd5b605160048036036020811015604b57600080fd5b5035606b565b005b60596070565b60408051918252519081900360200190f35b600055565b6000549056fea2646970667358221220d3b3e3b3e3b3e3b3e3b3e3b3e3b3e3b3e3b3e3b3e3b3e3b3e3b3e3b3e3b3e64736f6c63430007060033");
// 部署合约的交易
let deploy_tx = Transaction {
nonce: U256::zero(),
gas_price: U256::from(100),
gas_limit: U256::from(500000),
to: None, // None表示是合约创建交易
value: U256::zero(),
input: contract_bytecode.to_vec(),
signature: None,
};
// 执行部署
let deployment_result = engine.execute_transaction(deploy_tx);
let contract_address = deployment_result.unwrap().created_address.unwrap();
println!("Contract deployed at: {:?}", contract_address);
// 调用合约的set方法 (函数选择器: 0x60fe47b1)
let call_data = hex!("60fe47b10000000000000000000000000000000000000000000000000000000000000042");
let call_tx = Transaction {
nonce: U256::one(),
gas_price: U256::from(100),
gas_limit: U256::from(100000),
to: Some(contract_address),
value: U256::zero(),
input: call_data.to_vec(),
signature: None,
};
let call_result = engine.execute_transaction(call_tx);
println!("Function call result: {:?}", call_result);
}
高级功能
自定义存储后端
use aurora_evm::{Engine, Config, storage::MemoryStorage};
fn custom_storage_backend() {
let config = Config::default();
let storage = MemoryStorage::default(); // 使用内存存储
let mut engine = Engine::with_storage(config, storage);
// 现在engine使用自定义的存储后端
}
配置Gas模型
use aurora_evm::{Engine, Config, gas::Gasometer};
fn custom_gas_config() {
let mut config = Config::default();
config.gasometer = Gasometer::new(10, 100, 1000); // 自定义Gas参数
let engine = Engine::new(config);
}
测试智能合约
aurora-evm非常适合用于测试智能合约:
use aurora_evm::{Engine, Config, Transaction, U256};
use hex_literal::hex;
fn test_contract() {
let config = Config::default();
let mut engine = Engine::new(config);
// 部署测试合约
let bytecode = hex!("..."); // 合约字节码
let deploy_tx = Transaction {
// ... 部署交易参数
};
let deployment_result = engine.execute_transaction(deploy_tx).unwrap();
let contract_address = deployment_result.created_address.unwrap();
// 测试合约功能
let test_tx = Transaction {
// ... 测试交易参数
};
let test_result = engine.execute_transaction(test_tx);
assert!(test_result.is_ok());
// 更多断言...
}
注意事项
- aurora-evm仍在积极开发中,API可能会有变化
- 生产环境使用前应进行全面测试
- 性能优化可能需要根据具体使用场景进行调整
- 某些高级EVM功能可能尚未完全实现
完整示例:带注释的智能合约测试
use aurora_evm::{Engine, Config, Transaction, U256};
use hex_literal::hex;
// 测试一个简单的存储合约
fn test_storage_contract() {
// 1. 初始化EVM环境
let config = Config::default();
let mut engine = Engine::new(config);
// 2. 准备合约字节码 (一个简单的存储合约)
let contract_bytecode = hex!("608060405234801561001057600080fd5b506040516020806100f2833981016040525160005560fe806100336000396000f3fe6080604052348015600f57600080fd5b506004361060325760003560e01c806360fe47b11460375780636d4ce63c146053575b600080fd5b605160048036036020811015604b57600080fd5b5035606b565b005b60596070565b60408051918252519081900360200190f35b600055565b6000549056fea2646970667358221220123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef64736f6c63430007060033");
// 3. 创建部署交易
let deploy_tx = Transaction {
nonce: U256::zero(),
gas_price: U256::from(100),
gas_limit: U256::from(500000),
to: None, // 合约创建交易
value: U256::zero(),
input: contract_bytecode.to_vec(),
signature: None,
};
// 4. 部署合约
let deployment_result = engine.execute_transaction(deploy_tx).unwrap();
let contract_address = deployment_result.created_address.unwrap();
println!("合约部署成功,地址: {:?}", contract_address);
// 5. 测试存储功能 (调用store函数,函数选择器: 0x60fe47b1)
let store_data = hex!("60fe47b10000000000000000000000000000000000000000000000000000000000000042");
let store_tx = Transaction {
nonce: U256::one(),
gas_price: U256::from(100),
gas_limit: U256::from(100000),
to: Some(contract_address),
value: U256::zero(),
input: store_data.to_vec(),
signature: None,
};
let store_result = engine.execute_transaction(store_tx);
assert!(store_result.is_ok(), "存储调用失败");
// 6. 测试读取功能 (调用retrieve函数,函数选择器: 0x6d4ce63c)
let retrieve_data = hex!("6d4ce63c");
let retrieve_tx = Transaction {
nonce: U256::from(2),
gas_price: U256::from(100),
gas_limit: U256::from(100000),
to: Some(contract_address),
value: U256::zero(),
input: retrieve_data.to_vec(),
signature: None,
};
let retrieve_result = engine.execute_transaction(retrieve_tx);
assert!(retrieve_result.is_ok(), "读取调用失败");
// 7. 验证返回值应该是我们之前存储的值0x42
let output = retrieve_result.unwrap().output;
assert_eq!(output, hex!("0000000000000000000000000000000000000000000000000000000000000042"), "返回值不匹配");
println!("所有测试通过!");
}
fn main() {
test_storage_contract();
}