From 413554977b3a2dacee27c3f51cacb8962d1076b1 Mon Sep 17 00:00:00 2001 From: Dr Maxim Orlovsky Date: Tue, 9 Jul 2024 13:58:50 +0200 Subject: [PATCH] persistance: do save data on store transaction commit --- src/persistence/index.rs | 6 ++++ src/persistence/memory.rs | 59 ++++++++++++++++++++++----------------- 2 files changed, 40 insertions(+), 25 deletions(-) diff --git a/src/persistence/index.rs b/src/persistence/index.rs index 0ad897f2..c0014850 100644 --- a/src/persistence/index.rs +++ b/src/persistence/index.rs @@ -23,11 +23,13 @@ use std::collections::BTreeSet; use std::error::Error; use std::fmt::Debug; +use amplify::confinement; use rgb::{ Assign, AssignmentType, BundleId, ContractId, ExposedState, Extension, Genesis, GenesisSeal, GraphSeal, OpId, Operation, Opout, TransitionBundle, TypedAssigns, XChain, XOutputSeal, XWitnessId, }; +use strict_encoding::SerializeError; use crate::containers::{BundledWitness, Consignment, ToWitnessId}; use crate::persistence::StoreTransaction; @@ -83,6 +85,10 @@ impl From::Error>> f } } +impl From for IndexWriteError { + fn from(err: confinement::Error) -> Self { IndexWriteError::Connectivity(err.into()) } +} + #[derive(Clone, PartialEq, Eq, Debug, Display, Error, From)] #[display(doc_comments)] pub enum IndexInconsistency { diff --git a/src/persistence/memory.rs b/src/persistence/memory.rs index 6f4d267e..7c689f5f 100644 --- a/src/persistence/memory.rs +++ b/src/persistence/memory.rs @@ -36,7 +36,7 @@ use rgb::{ Extension, Genesis, GenesisSeal, GraphSeal, Identity, OpId, Operation, Opout, Schema, SchemaId, SecretSeal, TransitionBundle, XChain, XOutputSeal, XWitnessId, }; -use strict_encoding::{StrictDeserialize, StrictSerialize}; +use strict_encoding::{SerializeError, StrictDeserialize, StrictSerialize}; use strict_types::TypeSystem; use super::{ @@ -49,6 +49,7 @@ use crate::containers::{ AnchorSet, ContentId, ContentRef, ContentSigs, SealWitness, SigBlob, Supplement, TrustLevel, }; use crate::interface::{Iface, IfaceClass, IfaceId, IfaceImpl, IfaceRef}; +use crate::persistence::fs::FsStored; use crate::resolvers::ResolveHeight; use crate::LIB_NAME_RGB_STD; @@ -87,7 +88,7 @@ impl StrictSerialize for MemStash {} impl StrictDeserialize for MemStash {} impl StoreTransaction for MemStash { - type TransactionErr = confinement::Error; + type TransactionErr = SerializeError; fn begin_transaction(&mut self) -> Result<(), Self::TransactionErr> { self.dirty = true; @@ -95,7 +96,9 @@ impl StoreTransaction for MemStash { } fn commit_transaction(&mut self) -> Result<(), Self::TransactionErr> { - // We do not do anything here since we do not actually save anything + if self.dirty { + self.store()?; + } Ok(()) } @@ -288,9 +291,9 @@ impl StashReadProvider for MemStash { } impl StashWriteProvider for MemStash { - type Error = confinement::Error; + type Error = SerializeError; - fn replace_schema(&mut self, schema: Schema) -> Result { + fn replace_schema(&mut self, schema: Schema) -> Result { let schema_id = schema.schema_id(); if !self.schemata.contains_key(&schema_id) { self.schemata.insert(schema_id, SchemaIfaces::new(schema))?; @@ -299,7 +302,7 @@ impl StashWriteProvider for MemStash { Ok(false) } - fn replace_iface(&mut self, iface: Iface) -> Result { + fn replace_iface(&mut self, iface: Iface) -> Result { let iface_id = iface.iface_id(); if !self.ifaces.contains_key(&iface_id) { self.ifaces.insert(iface_id, iface)?; @@ -308,7 +311,7 @@ impl StashWriteProvider for MemStash { Ok(false) } - fn replace_iimpl(&mut self, iimpl: IfaceImpl) -> Result { + fn replace_iimpl(&mut self, iimpl: IfaceImpl) -> Result { let schema_ifaces = self .schemata .get_mut(&iimpl.schema_id) @@ -329,7 +332,7 @@ impl StashWriteProvider for MemStash { Ok(()) } - fn add_supplement(&mut self, suppl: Supplement) -> Result<(), confinement::Error> { + fn add_supplement(&mut self, suppl: Supplement) -> Result<(), Self::Error> { match self.suppl.get_mut(&suppl.content_id) { None => { self.suppl.insert(suppl.content_id, confined_bset![suppl])?; @@ -339,25 +342,25 @@ impl StashWriteProvider for MemStash { Ok(()) } - fn replace_genesis(&mut self, genesis: Genesis) -> Result { + fn replace_genesis(&mut self, genesis: Genesis) -> Result { let contract_id = genesis.contract_id(); let present = self.geneses.insert(contract_id, genesis)?.is_some(); Ok(!present) } - fn replace_extension(&mut self, extension: Extension) -> Result { + fn replace_extension(&mut self, extension: Extension) -> Result { let opid = extension.id(); let present = self.extensions.insert(opid, extension)?.is_some(); Ok(!present) } - fn replace_bundle(&mut self, bundle: TransitionBundle) -> Result { + fn replace_bundle(&mut self, bundle: TransitionBundle) -> Result { let bundle_id = bundle.bundle_id(); let present = self.bundles.insert(bundle_id, bundle)?.is_some(); Ok(!present) } - fn replace_witness(&mut self, witness: SealWitness) -> Result { + fn replace_witness(&mut self, witness: SealWitness) -> Result { let witness_id = witness.witness_id(); let present = self.witnesses.insert(witness_id, witness)?.is_some(); Ok(!present) @@ -367,21 +370,21 @@ impl StashWriteProvider for MemStash { &mut self, id: AttachId, attach: MediumBlob, - ) -> Result { + ) -> Result { let present = self.attachments.insert(id, attach)?.is_some(); Ok(!present) } - fn consume_types(&mut self, types: TypeSystem) -> Result<(), confinement::Error> { - self.type_system.extend(types) + fn consume_types(&mut self, types: TypeSystem) -> Result<(), Self::Error> { + Ok(self.type_system.extend(types)?) } - fn replace_lib(&mut self, lib: Lib) -> Result { + fn replace_lib(&mut self, lib: Lib) -> Result { let present = self.libs.insert(lib.id(), lib)?.is_some(); Ok(!present) } - fn import_sigs(&mut self, content_id: ContentId, sigs: I) -> Result<(), confinement::Error> + fn import_sigs(&mut self, content_id: ContentId, sigs: I) -> Result<(), Self::Error> where I: IntoIterator { let sigs = sigs.into_iter().filter(|(id, _)| { match self.identities.get(id) { @@ -404,7 +407,7 @@ impl StashWriteProvider for MemStash { Ok(()) } - fn add_secret_seal(&mut self, seal: XChain) -> Result { + fn add_secret_seal(&mut self, seal: XChain) -> Result { let present = self.secret_seals.contains(&seal); self.secret_seals.push(seal)?; Ok(!present) @@ -437,7 +440,7 @@ impl StrictSerialize for MemState {} impl StrictDeserialize for MemState {} impl StoreTransaction for MemState { - type TransactionErr = confinement::Error; + type TransactionErr = SerializeError; fn begin_transaction(&mut self) -> Result<(), Self::TransactionErr> { self.dirty = true; @@ -445,7 +448,9 @@ impl StoreTransaction for MemState { } fn commit_transaction(&mut self) -> Result<(), Self::TransactionErr> { - // We do not do anything here since we do not actually save anything + if self.dirty { + self.store()?; + } Ok(()) } @@ -466,7 +471,7 @@ impl StateReadProvider for MemState { } impl StateWriteProvider for MemState { - type Error = confinement::Error; + type Error = SerializeError; fn create_or_update_state( &mut self, @@ -476,7 +481,9 @@ impl StateWriteProvider for MemState { let state = self.history.get(&contract_id); let updated = updater(state.cloned()).map_err(|e| StateUpdateError::Resolver(e.to_string()))?; - self.history.insert(contract_id, updated)?; + self.history + .insert(contract_id, updated) + .map_err(|e| StateUpdateError::Connectivity(e.into()))?; Ok(()) } @@ -541,7 +548,7 @@ impl StrictSerialize for MemIndex {} impl StrictDeserialize for MemIndex {} impl StoreTransaction for MemIndex { - type TransactionErr = confinement::Error; + type TransactionErr = SerializeError; fn begin_transaction(&mut self) -> Result<(), Self::TransactionErr> { self.dirty = true; @@ -549,7 +556,9 @@ impl StoreTransaction for MemIndex { } fn commit_transaction(&mut self) -> Result<(), Self::TransactionErr> { - // We do not do anything here since we do not actually save anything + if self.dirty { + self.store()?; + } Ok(()) } @@ -647,7 +656,7 @@ impl IndexReadProvider for MemIndex { } impl IndexWriteProvider for MemIndex { - type Error = confinement::Error; + type Error = SerializeError; fn register_contract(&mut self, contract_id: ContractId) -> Result { if !self.contract_index.contains_key(&contract_id) {