Architecture du stockage
Le réseau Savitri utilise RocksDB comme moteur de stockage principal, avec des familles de colonnes pour l'isolation des données et des schémas d'accès efficaces.
Familles de colonnes
| Famille de colonnes | Clé | Valeur | Objectif |
|---|---|---|---|
CF_BLOCKS | hauteur (u64 LE) | Bloc (bincode) | Stockage des blocs |
CF_TRANSACTIONS | tx_hash (32 octets) | Transaction (bincode) | Recherche de transactions |
CF_ACCOUNTS | adresse (32 octets) | Compte (24 octets) | Solde + nonce |
CF_METADATA | clé texte | variable | Tête de chaîne, configuration |
CF_RECEIPTS | tx_hash | Reçu (bincode) | Reçus de transactions |
CF_CONTRACTS | adresse | ContractInfo | État des contrats intelligents |
CF_GOVERNANCE | proposal_id | Proposition (bincode) | Propositions de gouvernance |
CF_ORACLE | feed_id | OracleData | Flux d'oracles |
CF_BONDS | adresse | Montant du cautionnement | Cautionnements des validateurs |
CF_VOTE_TOKENS | adresse | Solde VoteToken | Tokens de vote de gouvernance |
CF_TREASURY | clé | État du trésor | Trésor du réseau |
CF_VESTING | schedule_id | VestingSchedule | Acquisition progressive de tokens |
CF_REWARD_COINS | adresse | Solde de récompenses | Récompenses des nœuds |
CF_FEE_METRICS | clé | Données de frais | Suivi des frais |
CF_SUPPLY_METRICS | clé | Données d'offre | Offre de tokens |
CF_ACTIVE_NODES | node_id | Activité | Disponibilité des nœuds |
CF_MONOLITHS | monolith_id | Monolithe | Compression de blocs |
CF_FL | clé | Données FL | Apprentissage fédéré |
CF_POU | node_id | Score PoU | Scores de consensus |
Encodage des comptes
Les comptes utilisent un encodage compact en format fixe de 24 octets :
Octets 0-15 : solde (u128, little-endian)
Octets 16-23 : nonce (u64, little-endian)
Rétrocompatible : l'ancien format de 16 octets (solde uniquement, nonce=0) est toujours pris en charge.
Les comptes vides (solde=0, nonce=0) ne sont jamais persistés pour économiser de l'espace de stockage.
Racine d'état
La racine d'état est calculée via un instantané lexicographique de la base de données :
seed = H("STATEv1-LE")
leaf = H("STATE" || key || value) pour chaque paire clé-valeur
root = rolling_accumulate(seed, leaf_1, leaf_2, ..., leaf_n)
Les clés sont itérées dans l'ordre lexicographique pour assurer le déterminisme.
Trait de stockage
Tous les backends de stockage implémentent le StorageTrait :
pub trait StorageTrait: Send + Sync {
fn get_cf(&self, cf: &str, key: &[u8]) -> Result<Option<Vec<u8>>>;
fn put_cf(&self, cf: &str, key: &[u8], value: &[u8]) -> Result<()>;
fn delete_cf(&self, cf: &str, key: &[u8]) -> Result<()>;
fn get_cf_prefix(&self, cf: &str, prefix: &[u8]) -> Result<Vec<(Vec<u8>, Vec<u8>)>>;
// ... opérations par lot, itération, etc.
}
Désérialisation sécurisée
Toute désérialisation bincode utilise une limite de taille maximale pour prévenir l'épuisement de la mémoire :
const MAX_BINCODE_SIZE: u64 = 16 * 1024 * 1024; // 16 Mo
Mise en cache
Couche de cache LRU pour les données fréquemment consultées :
- Cache des comptes : réduit les lectures RocksDB pour les vérifications de solde/nonce
- Cache de stockage de contrats : met en cache les résultats SLOAD dans l'exécution de contrats
- Cache de scores : cache LRU pour la notation des transactions du mempool (évite les recalculs)
Configuration RocksDB
| Paramètre | Développement | Production |
|---|---|---|
| Taille du cache | 256 Mo | 1024 Mo |
| Tampon d'écriture | 16 Mo | 64 Mo |
| Nombre max. de fichiers ouverts | 100 | 1000 |
| Intervalle de synchronisation | 5s | 30s |
| Compression | Désactivée | Activée |
Opérations par lot
Les écritures atomiques par lot assurent la cohérence :
let mut batch = storage.batch();
batch.put_cf(CF_ACCOUNTS, &addr, &account.encode());
batch.put_cf(CF_TRANSACTIONS, &tx_hash, &tx_bytes);
batch.put_cf(CF_BLOCKS, &height_key, &block_bytes);
batch.commit()?;
Système d'acquisition progressive
Les calendriers d'acquisition progressive de tokens prennent en charge trois types :
| Type | Comportement |
|---|---|
Linear | Tokens libérés linéairement sur la durée |
Cliff | Aucun token avant la période de blocage, puis linéaire |
Staged | Mode de compatibilité genèse |
Indicateurs de fonctionnalité
| Indicateur | Description |
|---|---|
rocksdb | Backend RocksDB (par défaut) |
memory | Backend en mémoire (tests) |
prometheus | Export de métriques Prometheus |
tempfile | Stockage temporaire pour les tests |