sal/src/hero_vault/ethereum/README.md

6.6 KiB

Hero Vault Ethereum Module

The Ethereum module provides functionality for creating and managing Ethereum wallets and interacting with smart contracts on EVM-based blockchains.

Module Structure

The Ethereum module is organized into several components:

  • wallet.rs - Core Ethereum wallet implementation
  • networks.rs - Network registry and configuration
  • provider.rs - Provider creation and management
  • transaction.rs - Transaction-related functionality
  • storage.rs - Wallet storage functionality
  • contract.rs - Smart contract interaction functionality
  • contract_utils.rs - Utilities for contract interactions

Key Features

Wallet Management

The module provides functionality for creating and managing Ethereum wallets:

// Create a network-independent Ethereum wallet
let wallet = create_ethereum_wallet()?;

// Create a wallet with a specific name
let named_wallet = create_ethereum_wallet_from_name("my_wallet")?;

// Create a wallet from a private key
let imported_wallet = create_ethereum_wallet_from_private_key("0x...")?;

// Get the current wallet
let current_wallet = get_current_ethereum_wallet()?;

// Clear wallets
clear_ethereum_wallets()?;

// Legacy functions for backward compatibility
let wallet = create_ethereum_wallet_for_network(network)?;
let peaq_wallet = create_peaq_wallet()?;
let agung_wallet = create_agung_wallet()?;

Network Management

The module supports multiple Ethereum networks and provides functionality for managing network configurations:

// Register a new network
register_network("Arbitrum", 42161, "https://arb1.arbitrum.io/rpc", "https://arbiscan.io", "ETH", 18);

// Remove a network
remove_network("Arbitrum");

// Get a network configuration by name
let network = get_network_by_name("Ethereum")?;

// Get the proper network name (normalized)
let name = get_proper_network_name("eth")?; // Returns "Ethereum"

// List all available network names
let networks = list_network_names()?;

// Get all network configurations
let all_networks = get_all_networks()?;

Provider Management

The module provides functionality for creating and managing Ethereum providers:

// Create a provider for a specific network
let provider = create_provider("Ethereum")?;

// Create a provider from a network configuration
let provider = create_provider_from_config(&network)?;

// Legacy functions for backward compatibility
let gnosis_provider = create_gnosis_provider()?;
let peaq_provider = create_peaq_provider()?;
let agung_provider = create_agung_provider()?;

Transaction Management

The module provides functionality for managing Ethereum transactions:

// Get the balance of an address on a specific network
let balance = get_balance("Ethereum", address).await?;

// Get the balance using a provider
let balance = get_balance_with_provider(&provider, address).await?;

// Send ETH to an address on a specific network
let tx_hash = send_eth(&wallet, "Ethereum", to_address, amount).await?;

// Legacy function for backward compatibility
let tx_hash = send_eth_with_provider(&wallet, &provider, to_address, amount).await?;

// Format a balance for display
let formatted = format_balance(balance, &network);

Smart Contract Interactions

The module provides functionality for interacting with smart contracts:

// Load a contract ABI from JSON
let abi = load_abi_from_json(json_string)?;

// Create a contract instance
let contract = Contract::new(address, abi, network);

// Call a read-only function
let result = call_read_function(&contract, &provider, "balanceOf", tokens).await?;

// Call a write function
let tx_hash = call_write_function(&contract, &wallet, &provider, "transfer", tokens).await?;

// Estimate gas for a function call
let gas = estimate_gas(&contract, &provider, "transfer", tokens).await?;

Contract Utilities

The module provides utilities for working with contract function arguments and return values:

// Convert Rhai values to Ethereum tokens
let token = convert_rhai_to_token(value)?;

// Prepare function arguments
let args = prepare_function_arguments(&abi, function_name, &args)?;

// Convert Ethereum tokens to Rhai values
let rhai_value = convert_token_to_rhai(&token)?;

// Convert a token to a dynamic value
let dynamic = token_to_dynamic(&token)?;

Network Registry

The module now includes a centralized network registry that allows for dynamic management of EVM-compatible networks:

// Built-in networks
- Gnosis Chain (chain_id: 100, token: xDAI)
- Peaq Network (chain_id: 3338, token: PEAQ)
- Agung Network (chain_id: 9990, token: AGNG)

// Register a custom network at runtime
register_network(
    "Polygon", 
    137, 
    "https://polygon-rpc.com", 
    "https://polygonscan.com", 
    "MATIC", 
    18
);

Wallet Address Consistency

In the new design, Ethereum wallet addresses are consistent across all EVM-compatible networks. This reflects how Ethereum addresses work in reality - the same private key generates the same address on all EVM chains.

// Create a wallet once
let wallet = create_ethereum_wallet()?;

// Use the same wallet address on any network
let eth_balance = get_balance("Ethereum", wallet.address).await?;
let polygon_balance = get_balance("Polygon", wallet.address).await?;
let gnosis_balance = get_balance("Gnosis", wallet.address).await?;

Error Handling

The module uses the CryptoError type for handling errors that can occur during Ethereum operations:

  • InvalidAddress - Invalid Ethereum address format
  • ContractError - Smart contract interaction error
  • NoKeypairSelected - No keypair selected for wallet creation
  • InvalidKeyLength - Invalid private key length

Examples

For examples of how to use the Ethereum module, see the examples/hero_vault directory, particularly:

  • contract_example.rhai - Demonstrates loading a contract ABI and interacting with smart contracts
  • agung_simple_transfer.rhai - Shows how to perform a simple ETH transfer on the Agung network
  • agung_send_transaction.rhai - Demonstrates sending transactions on the Agung network
  • agung_contract_with_args.rhai - Shows how to interact with contracts with arguments on Agung

Adding a New Network

With the new design, adding a new network is as simple as registering it with the network registry:

// In Rust
ethereum::register_network(
    "Optimism", 
    10, 
    "https://mainnet.optimism.io", 
    "https://optimistic.etherscan.io", 
    "ETH", 
    18
);

// In Rhai
register_network(
    "Optimism", 
    10, 
    "https://mainnet.optimism.io", 
    "https://optimistic.etherscan.io", 
    "ETH", 
    18
);

No code changes are required to add support for new networks!