diff --git a/crates/fuel-core/src/service/adapters/gas_price_adapters.rs b/crates/fuel-core/src/service/adapters/gas_price_adapters.rs index 93737d0cc59..b504335f798 100644 --- a/crates/fuel-core/src/service/adapters/gas_price_adapters.rs +++ b/crates/fuel-core/src/service/adapters/gas_price_adapters.rs @@ -1,17 +1,44 @@ -use crate::service::adapters::ConsensusParametersProvider; -use fuel_core_gas_price_service::fuel_gas_price_updater::{ - fuel_core_storage_adapter::{ - GasPriceSettings, - GasPriceSettingsProvider, +use crate::{ + database::OnChainIterableKeyValueView, + service::adapters::ConsensusParametersProvider, +}; +use fuel_core_gas_price_service::{ + fuel_gas_price_updater::{ + fuel_core_storage_adapter::{ + GasPriceSettings, + GasPriceSettingsProvider, + }, + Error as GasPriceError, + Result as GasPriceResult, + }, + ports::L2Data, +}; +use fuel_core_storage::Result as StorageResult; +use fuel_core_types::{ + blockchain::{ + block::Block, + header::ConsensusParametersVersion, }, - Error as GasPriceError, - Result as GasPriceResult, + fuel_tx::Transaction, + fuel_types::BlockHeight, }; -use fuel_core_types::blockchain::header::ConsensusParametersVersion; #[cfg(test)] mod tests; +impl L2Data for OnChainIterableKeyValueView { + fn latest_height(&self) -> StorageResult { + self.latest_height() + } + + fn get_block( + &self, + height: &BlockHeight, + ) -> StorageResult>> { + self.get_full_block(height) + } +} + impl GasPriceSettingsProvider for ConsensusParametersProvider { fn settings( &self, diff --git a/crates/fuel-core/src/service/sub_services/algorithm_updater.rs b/crates/fuel-core/src/service/sub_services/algorithm_updater.rs index 002ecebe039..f1d8e7308d7 100644 --- a/crates/fuel-core/src/service/sub_services/algorithm_updater.rs +++ b/crates/fuel-core/src/service/sub_services/algorithm_updater.rs @@ -1,9 +1,6 @@ use crate::{ database::{ - database_description::{ - gas_price::GasPriceDatabase, - on_chain::OnChain, - }, + database_description::gas_price::GasPriceDatabase, Database, RegularStage, }, @@ -21,18 +18,22 @@ use fuel_core_gas_price_service::{ DaBlockCostsSharedState, }, fuel_core_storage_adapter::{ + get_block_info, storage::GasPriceMetadata, FuelL2BlockSource, + GasPriceSettings, GasPriceSettingsProvider, }, Algorithm, AlgorithmUpdater, AlgorithmUpdaterV0, + BlockInfo, FuelGasPriceUpdater, MetadataStorage, UpdaterMetadata, V0Metadata, }, + ports::L2Data, GasPriceService, SharedGasPriceAlgo, }; @@ -43,11 +44,8 @@ use fuel_core_services::{ StateWatcher, }; use fuel_core_storage::{ + not_found, structured_storage::StructuredStorage, - tables::{ - FuelBlocks, - Transactions, - }, transactional::{ AtomicView, HistoricalView, @@ -55,7 +53,6 @@ use fuel_core_storage::{ StorageAsRef, }; use fuel_core_types::{ - fuel_tx::field::MintAmount, fuel_types::BlockHeight, services::block_importer::SharedImportResult, }; @@ -66,12 +63,12 @@ type Updater = FuelGasPriceUpdater< DaBlockCostsSharedState, >; -pub struct InitializeTask { +pub struct InitializeTask { pub config: Config, pub genesis_block_height: BlockHeight, pub settings: ConsensusParametersProvider, pub gas_price_db: Database>, - pub on_chain_db: Database>, + pub on_chain_db: L2DataStoreView, pub block_stream: BoxStream, pub shared_algo: SharedGasPriceAlgo, pub da_block_costs_provider: DaBlockCostsProvider, @@ -82,19 +79,22 @@ type MetadataStorageAdapter = type Task = GasPriceService; -impl InitializeTask { +impl InitializeTask +where + L2DataStore: L2Data, + L2DataStoreView: AtomicView, +{ pub fn new( config: Config, genesis_block_height: BlockHeight, settings: ConsensusParametersProvider, block_stream: BoxStream, gas_price_db: Database>, - on_chain_db: Database>, + on_chain_db: L2DataStoreView, ) -> anyhow::Result { - let latest_block_height = on_chain_db - .latest_height() - .unwrap_or(genesis_block_height) - .into(); + let view = on_chain_db.latest_view()?; + let latest_block_height = + view.latest_height().unwrap_or(genesis_block_height).into(); let default_metadata = get_default_metadata(&config, latest_block_height); let algo = get_best_algo(&gas_price_db, default_metadata)?; let shared_algo = SharedGasPriceAlgo::new_with_algorithm(algo); @@ -147,7 +147,11 @@ fn get_best_algo( Ok(algo) } #[async_trait::async_trait] -impl RunnableService for InitializeTask { +impl RunnableService for InitializeTask +where + L2DataStore: L2Data, + L2DataStoreView: AtomicView, +{ const NAME: &'static str = "GasPriceUpdater"; type SharedData = SharedGasPriceAlgo; type Task = Task; @@ -162,17 +166,15 @@ impl RunnableService for InitializeTask { _state_watcher: &StateWatcher, _params: Self::TaskParams, ) -> anyhow::Result { - let starting_height = self - .on_chain_db - .latest_height() - .unwrap_or(self.genesis_block_height); + let view = self.on_chain_db.latest_view()?; + let starting_height = view.latest_height().unwrap_or(self.genesis_block_height); let updater = get_synced_gas_price_updater( self.config, self.genesis_block_height, self.settings, self.gas_price_db, - self.on_chain_db, + &self.on_chain_db, self.block_stream, self.da_block_costs_provider.shared_state, )?; @@ -187,17 +189,22 @@ impl RunnableService for InitializeTask { } } -pub fn get_synced_gas_price_updater( +pub fn get_synced_gas_price_updater( config: Config, genesis_block_height: BlockHeight, settings: ConsensusParametersProvider, mut gas_price_db: Database>, - on_chain_db: Database>, + on_chain_db: &L2DataStoreView, block_stream: BoxStream, da_block_costs: DaBlockCostsSharedState, -) -> anyhow::Result { +) -> anyhow::Result +where + L2DataStore: L2Data, + L2DataStoreView: AtomicView, +{ let mut first_run = false; let latest_block_height: u32 = on_chain_db + .latest_view()? .latest_height() .unwrap_or(genesis_block_height) .into(); @@ -257,15 +264,19 @@ pub fn get_synced_gas_price_updater( } } -fn sync_metadata_storage_with_on_chain_storage( +fn sync_metadata_storage_with_on_chain_storage( settings: &ConsensusParametersProvider, metadata_storage: &mut StructuredStorage< Database>, >, - on_chain_db: Database>, + on_chain_db: &L2DataStoreView, metadata_height: u32, latest_block_height: u32, -) -> anyhow::Result<()> { +) -> anyhow::Result<()> +where + L2DataStore: L2Data, + L2DataStoreView: AtomicView, +{ let metadata = metadata_storage .get_metadata(&metadata_height.into())? .ok_or(anyhow::anyhow!( @@ -290,41 +301,47 @@ fn sync_metadata_storage_with_on_chain_storage( Ok(()) } -fn sync_v0_metadata( +fn sync_v0_metadata( settings: &ConsensusParametersProvider, - on_chain_db: Database>, + on_chain_db: &L2DataStoreView, metadata_height: u32, latest_block_height: u32, updater: &mut AlgorithmUpdaterV0, metadata_storage: &mut StructuredStorage< Database>, >, -) -> anyhow::Result<()> { +) -> anyhow::Result<()> +where + L2DataStore: L2Data, + L2DataStoreView: AtomicView, +{ let first = metadata_height.saturating_add(1); let view = on_chain_db.latest_view()?; for height in first..=latest_block_height { let block = view - .storage::() - .get(&height.into())? - .ok_or(anyhow::anyhow!("Expected block to exist"))?; - let last_tx_id = block.transactions().last().ok_or(anyhow::anyhow!( - "Expected block to have at least one transaction" - ))?; + .get_block(&height.into())? + .ok_or(not_found!("FullBlock"))?; let param_version = block.header().consensus_parameters_version; - let params = settings.settings(¶m_version)?; - let mint = view - .storage::() - .get(last_tx_id)? - .ok_or(anyhow::anyhow!("Expected tx to exist for id: {last_tx_id}"))? - .as_mint() - .ok_or(anyhow::anyhow!("Expected tx to be a mint"))? - .to_owned(); - let block_gas_used = mint.mint_amount(); - let block_gas_capacity = params.block_gas_limit.try_into()?; - updater.update_l2_block_data(height, *block_gas_used, block_gas_capacity)?; + + let GasPriceSettings { + gas_price_factor, + block_gas_limit, + } = settings.settings(¶m_version)?; + let block_gas_capacity = block_gas_limit.try_into()?; + + let block_gas_used = + match get_block_info(&block, gas_price_factor, block_gas_limit)? { + BlockInfo::GenesisBlock => { + Err(anyhow::anyhow!("should not be genesis block"))? + } + BlockInfo::Block { gas_used, .. } => gas_used, + }; + + updater.update_l2_block_data(height, block_gas_used, block_gas_capacity)?; let metadata = AlgorithmUpdater::V0(updater.clone()).into(); metadata_storage.set_metadata(metadata)?; } + Ok(()) } diff --git a/crates/services/gas_price_service/src/fuel_gas_price_updater/fuel_core_storage_adapter.rs b/crates/services/gas_price_service/src/fuel_gas_price_updater/fuel_core_storage_adapter.rs index 21ac241be9e..a1e4de8ed80 100644 --- a/crates/services/gas_price_service/src/fuel_gas_price_updater/fuel_core_storage_adapter.rs +++ b/crates/services/gas_price_service/src/fuel_gas_price_updater/fuel_core_storage_adapter.rs @@ -118,7 +118,7 @@ pub trait GasPriceSettingsProvider { ) -> Result; } -fn get_block_info( +pub fn get_block_info( block: &Block, gas_price_factor: u64, block_gas_limit: u64, diff --git a/crates/services/gas_price_service/src/lib.rs b/crates/services/gas_price_service/src/lib.rs index 10caf66ec54..2e254ed037e 100644 --- a/crates/services/gas_price_service/src/lib.rs +++ b/crates/services/gas_price_service/src/lib.rs @@ -18,6 +18,7 @@ use tokio::sync::RwLock; pub mod static_updater; pub mod fuel_gas_price_updater; +pub mod ports; /// The service that updates the gas price algorithm. pub struct GasPriceService { diff --git a/crates/services/gas_price_service/src/ports.rs b/crates/services/gas_price_service/src/ports.rs new file mode 100644 index 00000000000..7b4169c9454 --- /dev/null +++ b/crates/services/gas_price_service/src/ports.rs @@ -0,0 +1,14 @@ +use fuel_core_storage::Result as StorageResult; +use fuel_core_types::{ + blockchain::block::Block, + fuel_tx::Transaction, + fuel_types::BlockHeight, +}; + +pub trait L2Data: Send + Sync { + fn latest_height(&self) -> StorageResult; + fn get_block( + &self, + height: &BlockHeight, + ) -> StorageResult>>; +}