mirror of
https://github.com/hl-archive-node/nanoreth.git
synced 2025-12-06 19:09:54 +00:00
refactor: use DBProvider in HistoricalStateProvider (#12556)
This commit is contained in:
@ -178,11 +178,7 @@ impl<TX: DbTx + 'static, N: NodeTypes> DatabaseProvider<TX, N> {
|
||||
let storage_history_prune_checkpoint =
|
||||
self.get_prune_checkpoint(PruneSegment::StorageHistory)?;
|
||||
|
||||
let mut state_provider = HistoricalStateProviderRef::new(
|
||||
&self.tx,
|
||||
block_number,
|
||||
self.static_file_provider.clone(),
|
||||
);
|
||||
let mut state_provider = HistoricalStateProviderRef::new(self, block_number);
|
||||
|
||||
// If we pruned account or storage history, we can't return state on every historical block.
|
||||
// Instead, we should cap it at the latest prune checkpoint for corresponding prune segment.
|
||||
@ -259,8 +255,7 @@ impl<TX: DbTx + 'static, N: NodeTypes> TryIntoHistoricalStateProvider for Databa
|
||||
let storage_history_prune_checkpoint =
|
||||
self.get_prune_checkpoint(PruneSegment::StorageHistory)?;
|
||||
|
||||
let mut state_provider =
|
||||
HistoricalStateProvider::new(self.tx, block_number, self.static_file_provider);
|
||||
let mut state_provider = HistoricalStateProvider::new(self, block_number);
|
||||
|
||||
// If we pruned account or storage history, we can't return state on every historical block.
|
||||
// Instead, we should cap it at the latest prune checkpoint for corresponding prune segment.
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
use crate::{
|
||||
providers::{state::macros::delegate_provider_impls, StaticFileProvider},
|
||||
AccountReader, BlockHashReader, ProviderError, StateProvider, StateRootProvider,
|
||||
providers::state::macros::delegate_provider_impls, AccountReader, BlockHashReader,
|
||||
ProviderError, StateProvider, StateRootProvider,
|
||||
};
|
||||
use alloy_eips::merge::EPOCH_SLOTS;
|
||||
use alloy_primitives::{
|
||||
@ -14,8 +14,8 @@ use reth_db_api::{
|
||||
table::Table,
|
||||
transaction::DbTx,
|
||||
};
|
||||
use reth_primitives::{Account, Bytecode, StaticFileSegment};
|
||||
use reth_storage_api::{StateProofProvider, StorageRootProvider};
|
||||
use reth_primitives::{Account, Bytecode};
|
||||
use reth_storage_api::{BlockNumReader, DBProvider, StateProofProvider, StorageRootProvider};
|
||||
use reth_storage_errors::provider::ProviderResult;
|
||||
use reth_trie::{
|
||||
proof::{Proof, StorageProof},
|
||||
@ -41,15 +41,13 @@ use std::fmt::Debug;
|
||||
/// - [`tables::AccountChangeSets`]
|
||||
/// - [`tables::StorageChangeSets`]
|
||||
#[derive(Debug)]
|
||||
pub struct HistoricalStateProviderRef<'b, TX: DbTx> {
|
||||
/// Transaction
|
||||
tx: &'b TX,
|
||||
pub struct HistoricalStateProviderRef<'b, Provider> {
|
||||
/// Database provider
|
||||
provider: &'b Provider,
|
||||
/// Block number is main index for the history state of accounts and storages.
|
||||
block_number: BlockNumber,
|
||||
/// Lowest blocks at which different parts of the state are available.
|
||||
lowest_available_blocks: LowestAvailableBlocks,
|
||||
/// Static File provider
|
||||
static_file_provider: StaticFileProvider,
|
||||
}
|
||||
|
||||
#[derive(Debug, Eq, PartialEq)]
|
||||
@ -60,25 +58,20 @@ pub enum HistoryInfo {
|
||||
MaybeInPlainState,
|
||||
}
|
||||
|
||||
impl<'b, TX: DbTx> HistoricalStateProviderRef<'b, TX> {
|
||||
impl<'b, Provider: DBProvider + BlockNumReader> HistoricalStateProviderRef<'b, Provider> {
|
||||
/// Create new `StateProvider` for historical block number
|
||||
pub fn new(
|
||||
tx: &'b TX,
|
||||
block_number: BlockNumber,
|
||||
static_file_provider: StaticFileProvider,
|
||||
) -> Self {
|
||||
Self { tx, block_number, lowest_available_blocks: Default::default(), static_file_provider }
|
||||
pub fn new(provider: &'b Provider, block_number: BlockNumber) -> Self {
|
||||
Self { provider, block_number, lowest_available_blocks: Default::default() }
|
||||
}
|
||||
|
||||
/// Create new `StateProvider` for historical block number and lowest block numbers at which
|
||||
/// account & storage histories are available.
|
||||
pub const fn new_with_lowest_available_blocks(
|
||||
tx: &'b TX,
|
||||
provider: &'b Provider,
|
||||
block_number: BlockNumber,
|
||||
lowest_available_blocks: LowestAvailableBlocks,
|
||||
static_file_provider: StaticFileProvider,
|
||||
) -> Self {
|
||||
Self { tx, block_number, lowest_available_blocks, static_file_provider }
|
||||
Self { provider, block_number, lowest_available_blocks }
|
||||
}
|
||||
|
||||
/// Lookup an account in the `AccountsHistory` table
|
||||
@ -117,15 +110,7 @@ impl<'b, TX: DbTx> HistoricalStateProviderRef<'b, TX> {
|
||||
|
||||
/// Checks and returns `true` if distance to historical block exceeds the provided limit.
|
||||
fn check_distance_against_limit(&self, limit: u64) -> ProviderResult<bool> {
|
||||
let tip = self
|
||||
.tx
|
||||
.cursor_read::<tables::CanonicalHeaders>()?
|
||||
.last()?
|
||||
.map(|(tip, _)| tip)
|
||||
.or_else(|| {
|
||||
self.static_file_provider.get_highest_static_file_block(StaticFileSegment::Headers)
|
||||
})
|
||||
.ok_or(ProviderError::BestBlockNotFound)?;
|
||||
let tip = self.provider.last_block_number()?;
|
||||
|
||||
Ok(tip.saturating_sub(self.block_number) > limit)
|
||||
}
|
||||
@ -146,7 +131,7 @@ impl<'b, TX: DbTx> HistoricalStateProviderRef<'b, TX> {
|
||||
);
|
||||
}
|
||||
|
||||
Ok(HashedPostState::from_reverts(self.tx, self.block_number)?)
|
||||
Ok(HashedPostState::from_reverts(self.tx(), self.block_number)?)
|
||||
}
|
||||
|
||||
/// Retrieve revert hashed storage for this history provider and target address.
|
||||
@ -163,7 +148,7 @@ impl<'b, TX: DbTx> HistoricalStateProviderRef<'b, TX> {
|
||||
);
|
||||
}
|
||||
|
||||
Ok(HashedStorage::from_reverts(self.tx, address, self.block_number)?)
|
||||
Ok(HashedStorage::from_reverts(self.tx(), address, self.block_number)?)
|
||||
}
|
||||
|
||||
fn history_info<T, K>(
|
||||
@ -175,7 +160,7 @@ impl<'b, TX: DbTx> HistoricalStateProviderRef<'b, TX> {
|
||||
where
|
||||
T: Table<Key = K, Value = BlockNumberList>,
|
||||
{
|
||||
let mut cursor = self.tx.cursor_read::<T>()?;
|
||||
let mut cursor = self.tx().cursor_read::<T>()?;
|
||||
|
||||
// Lookup the history chunk in the history index. If they key does not appear in the
|
||||
// index, the first chunk for the next key will be returned so we filter out chunks that
|
||||
@ -248,13 +233,21 @@ impl<'b, TX: DbTx> HistoricalStateProviderRef<'b, TX> {
|
||||
}
|
||||
}
|
||||
|
||||
impl<TX: DbTx> AccountReader for HistoricalStateProviderRef<'_, TX> {
|
||||
impl<Provider: DBProvider + BlockNumReader> HistoricalStateProviderRef<'_, Provider> {
|
||||
fn tx(&self) -> &Provider::Tx {
|
||||
self.provider.tx_ref()
|
||||
}
|
||||
}
|
||||
|
||||
impl<Provider: DBProvider + BlockNumReader> AccountReader
|
||||
for HistoricalStateProviderRef<'_, Provider>
|
||||
{
|
||||
/// Get basic account information.
|
||||
fn basic_account(&self, address: Address) -> ProviderResult<Option<Account>> {
|
||||
match self.account_history_lookup(address)? {
|
||||
HistoryInfo::NotYetWritten => Ok(None),
|
||||
HistoryInfo::InChangeset(changeset_block_number) => Ok(self
|
||||
.tx
|
||||
.tx()
|
||||
.cursor_dup_read::<tables::AccountChangeSets>()?
|
||||
.seek_by_key_subkey(changeset_block_number, address)?
|
||||
.filter(|acc| acc.address == address)
|
||||
@ -264,21 +257,18 @@ impl<TX: DbTx> AccountReader for HistoricalStateProviderRef<'_, TX> {
|
||||
})?
|
||||
.info),
|
||||
HistoryInfo::InPlainState | HistoryInfo::MaybeInPlainState => {
|
||||
Ok(self.tx.get::<tables::PlainAccountState>(address)?)
|
||||
Ok(self.tx().get::<tables::PlainAccountState>(address)?)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<TX: DbTx> BlockHashReader for HistoricalStateProviderRef<'_, TX> {
|
||||
impl<Provider: DBProvider + BlockNumReader + BlockHashReader> BlockHashReader
|
||||
for HistoricalStateProviderRef<'_, Provider>
|
||||
{
|
||||
/// Get block hash by number.
|
||||
fn block_hash(&self, number: u64) -> ProviderResult<Option<B256>> {
|
||||
self.static_file_provider.get_with_static_file_or_database(
|
||||
StaticFileSegment::Headers,
|
||||
number,
|
||||
|static_file| static_file.block_hash(number),
|
||||
|| Ok(self.tx.get::<tables::CanonicalHeaders>(number)?),
|
||||
)
|
||||
self.provider.block_hash(number)
|
||||
}
|
||||
|
||||
fn canonical_hashes_range(
|
||||
@ -286,37 +276,23 @@ impl<TX: DbTx> BlockHashReader for HistoricalStateProviderRef<'_, TX> {
|
||||
start: BlockNumber,
|
||||
end: BlockNumber,
|
||||
) -> ProviderResult<Vec<B256>> {
|
||||
self.static_file_provider.get_range_with_static_file_or_database(
|
||||
StaticFileSegment::Headers,
|
||||
start..end,
|
||||
|static_file, range, _| static_file.canonical_hashes_range(range.start, range.end),
|
||||
|range, _| {
|
||||
self.tx
|
||||
.cursor_read::<tables::CanonicalHeaders>()
|
||||
.map(|mut cursor| {
|
||||
cursor
|
||||
.walk_range(range)?
|
||||
.map(|result| result.map(|(_, hash)| hash).map_err(Into::into))
|
||||
.collect::<ProviderResult<Vec<_>>>()
|
||||
})?
|
||||
.map_err(Into::into)
|
||||
},
|
||||
|_| true,
|
||||
)
|
||||
self.provider.canonical_hashes_range(start, end)
|
||||
}
|
||||
}
|
||||
|
||||
impl<TX: DbTx> StateRootProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
impl<Provider: DBProvider + BlockNumReader> StateRootProvider
|
||||
for HistoricalStateProviderRef<'_, Provider>
|
||||
{
|
||||
fn state_root(&self, hashed_state: HashedPostState) -> ProviderResult<B256> {
|
||||
let mut revert_state = self.revert_state()?;
|
||||
revert_state.extend(hashed_state);
|
||||
StateRoot::overlay_root(self.tx, revert_state)
|
||||
StateRoot::overlay_root(self.tx(), revert_state)
|
||||
.map_err(|err| ProviderError::Database(err.into()))
|
||||
}
|
||||
|
||||
fn state_root_from_nodes(&self, mut input: TrieInput) -> ProviderResult<B256> {
|
||||
input.prepend(self.revert_state()?);
|
||||
StateRoot::overlay_root_from_nodes(self.tx, input)
|
||||
StateRoot::overlay_root_from_nodes(self.tx(), input)
|
||||
.map_err(|err| ProviderError::Database(err.into()))
|
||||
}
|
||||
|
||||
@ -326,7 +302,7 @@ impl<TX: DbTx> StateRootProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
) -> ProviderResult<(B256, TrieUpdates)> {
|
||||
let mut revert_state = self.revert_state()?;
|
||||
revert_state.extend(hashed_state);
|
||||
StateRoot::overlay_root_with_updates(self.tx, revert_state)
|
||||
StateRoot::overlay_root_with_updates(self.tx(), revert_state)
|
||||
.map_err(|err| ProviderError::Database(err.into()))
|
||||
}
|
||||
|
||||
@ -335,12 +311,14 @@ impl<TX: DbTx> StateRootProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
mut input: TrieInput,
|
||||
) -> ProviderResult<(B256, TrieUpdates)> {
|
||||
input.prepend(self.revert_state()?);
|
||||
StateRoot::overlay_root_from_nodes_with_updates(self.tx, input)
|
||||
StateRoot::overlay_root_from_nodes_with_updates(self.tx(), input)
|
||||
.map_err(|err| ProviderError::Database(err.into()))
|
||||
}
|
||||
}
|
||||
|
||||
impl<TX: DbTx> StorageRootProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
impl<Provider: DBProvider + BlockNumReader> StorageRootProvider
|
||||
for HistoricalStateProviderRef<'_, Provider>
|
||||
{
|
||||
fn storage_root(
|
||||
&self,
|
||||
address: Address,
|
||||
@ -348,7 +326,7 @@ impl<TX: DbTx> StorageRootProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
) -> ProviderResult<B256> {
|
||||
let mut revert_storage = self.revert_storage(address)?;
|
||||
revert_storage.extend(&hashed_storage);
|
||||
StorageRoot::overlay_root(self.tx, address, revert_storage)
|
||||
StorageRoot::overlay_root(self.tx(), address, revert_storage)
|
||||
.map_err(|err| ProviderError::Database(err.into()))
|
||||
}
|
||||
|
||||
@ -360,12 +338,14 @@ impl<TX: DbTx> StorageRootProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
) -> ProviderResult<reth_trie::StorageProof> {
|
||||
let mut revert_storage = self.revert_storage(address)?;
|
||||
revert_storage.extend(&hashed_storage);
|
||||
StorageProof::overlay_storage_proof(self.tx, address, slot, revert_storage)
|
||||
StorageProof::overlay_storage_proof(self.tx(), address, slot, revert_storage)
|
||||
.map_err(Into::<ProviderError>::into)
|
||||
}
|
||||
}
|
||||
|
||||
impl<TX: DbTx> StateProofProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
impl<Provider: DBProvider + BlockNumReader> StateProofProvider
|
||||
for HistoricalStateProviderRef<'_, Provider>
|
||||
{
|
||||
/// Get account and storage proofs.
|
||||
fn proof(
|
||||
&self,
|
||||
@ -374,7 +354,7 @@ impl<TX: DbTx> StateProofProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
slots: &[B256],
|
||||
) -> ProviderResult<AccountProof> {
|
||||
input.prepend(self.revert_state()?);
|
||||
Proof::overlay_account_proof(self.tx, input, address, slots)
|
||||
Proof::overlay_account_proof(self.tx(), input, address, slots)
|
||||
.map_err(Into::<ProviderError>::into)
|
||||
}
|
||||
|
||||
@ -384,7 +364,7 @@ impl<TX: DbTx> StateProofProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
targets: HashMap<B256, HashSet<B256>>,
|
||||
) -> ProviderResult<MultiProof> {
|
||||
input.prepend(self.revert_state()?);
|
||||
Proof::overlay_multiproof(self.tx, input, targets).map_err(Into::<ProviderError>::into)
|
||||
Proof::overlay_multiproof(self.tx(), input, targets).map_err(Into::<ProviderError>::into)
|
||||
}
|
||||
|
||||
fn witness(
|
||||
@ -393,11 +373,13 @@ impl<TX: DbTx> StateProofProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
target: HashedPostState,
|
||||
) -> ProviderResult<HashMap<B256, Bytes>> {
|
||||
input.prepend(self.revert_state()?);
|
||||
TrieWitness::overlay_witness(self.tx, input, target).map_err(Into::<ProviderError>::into)
|
||||
TrieWitness::overlay_witness(self.tx(), input, target).map_err(Into::<ProviderError>::into)
|
||||
}
|
||||
}
|
||||
|
||||
impl<TX: DbTx> StateProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
impl<Provider: DBProvider + BlockNumReader + BlockHashReader> StateProvider
|
||||
for HistoricalStateProviderRef<'_, Provider>
|
||||
{
|
||||
/// Get storage.
|
||||
fn storage(
|
||||
&self,
|
||||
@ -407,7 +389,7 @@ impl<TX: DbTx> StateProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
match self.storage_history_lookup(address, storage_key)? {
|
||||
HistoryInfo::NotYetWritten => Ok(None),
|
||||
HistoryInfo::InChangeset(changeset_block_number) => Ok(Some(
|
||||
self.tx
|
||||
self.tx()
|
||||
.cursor_dup_read::<tables::StorageChangeSets>()?
|
||||
.seek_by_key_subkey((changeset_block_number, address).into(), storage_key)?
|
||||
.filter(|entry| entry.key == storage_key)
|
||||
@ -419,7 +401,7 @@ impl<TX: DbTx> StateProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
.value,
|
||||
)),
|
||||
HistoryInfo::InPlainState | HistoryInfo::MaybeInPlainState => Ok(self
|
||||
.tx
|
||||
.tx()
|
||||
.cursor_dup_read::<tables::PlainStorageState>()?
|
||||
.seek_by_key_subkey(address, storage_key)?
|
||||
.filter(|entry| entry.key == storage_key)
|
||||
@ -430,32 +412,26 @@ impl<TX: DbTx> StateProvider for HistoricalStateProviderRef<'_, TX> {
|
||||
|
||||
/// Get account code by its hash
|
||||
fn bytecode_by_hash(&self, code_hash: B256) -> ProviderResult<Option<Bytecode>> {
|
||||
self.tx.get::<tables::Bytecodes>(code_hash).map_err(Into::into)
|
||||
self.tx().get::<tables::Bytecodes>(code_hash).map_err(Into::into)
|
||||
}
|
||||
}
|
||||
|
||||
/// State provider for a given block number.
|
||||
/// For more detailed description, see [`HistoricalStateProviderRef`].
|
||||
#[derive(Debug)]
|
||||
pub struct HistoricalStateProvider<TX: DbTx> {
|
||||
/// Database transaction
|
||||
tx: TX,
|
||||
pub struct HistoricalStateProvider<Provider> {
|
||||
/// Database provider.
|
||||
provider: Provider,
|
||||
/// State at the block number is the main indexer of the state.
|
||||
block_number: BlockNumber,
|
||||
/// Lowest blocks at which different parts of the state are available.
|
||||
lowest_available_blocks: LowestAvailableBlocks,
|
||||
/// Static File provider
|
||||
static_file_provider: StaticFileProvider,
|
||||
}
|
||||
|
||||
impl<TX: DbTx> HistoricalStateProvider<TX> {
|
||||
impl<Provider: DBProvider + BlockNumReader> HistoricalStateProvider<Provider> {
|
||||
/// Create new `StateProvider` for historical block number
|
||||
pub fn new(
|
||||
tx: TX,
|
||||
block_number: BlockNumber,
|
||||
static_file_provider: StaticFileProvider,
|
||||
) -> Self {
|
||||
Self { tx, block_number, lowest_available_blocks: Default::default(), static_file_provider }
|
||||
pub fn new(provider: Provider, block_number: BlockNumber) -> Self {
|
||||
Self { provider, block_number, lowest_available_blocks: Default::default() }
|
||||
}
|
||||
|
||||
/// Set the lowest block number at which the account history is available.
|
||||
@ -478,18 +454,17 @@ impl<TX: DbTx> HistoricalStateProvider<TX> {
|
||||
|
||||
/// Returns a new provider that takes the `TX` as reference
|
||||
#[inline(always)]
|
||||
fn as_ref(&self) -> HistoricalStateProviderRef<'_, TX> {
|
||||
const fn as_ref(&self) -> HistoricalStateProviderRef<'_, Provider> {
|
||||
HistoricalStateProviderRef::new_with_lowest_available_blocks(
|
||||
&self.tx,
|
||||
&self.provider,
|
||||
self.block_number,
|
||||
self.lowest_available_blocks,
|
||||
self.static_file_provider.clone(),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
// Delegates all provider impls to [HistoricalStateProviderRef]
|
||||
delegate_provider_impls!(HistoricalStateProvider<TX> where [TX: DbTx]);
|
||||
delegate_provider_impls!(HistoricalStateProvider<Provider> where [Provider: DBProvider + BlockNumReader + BlockHashReader]);
|
||||
|
||||
/// Lowest blocks at which different parts of the state are available.
|
||||
/// They may be [Some] if pruning is enabled.
|
||||
@ -525,7 +500,6 @@ mod tests {
|
||||
providers::state::historical::{HistoryInfo, LowestAvailableBlocks},
|
||||
test_utils::create_test_provider_factory,
|
||||
AccountReader, HistoricalStateProvider, HistoricalStateProviderRef, StateProvider,
|
||||
StaticFileProviderFactory,
|
||||
};
|
||||
use alloy_primitives::{address, b256, Address, B256, U256};
|
||||
use reth_db::{tables, BlockNumberList};
|
||||
@ -534,6 +508,7 @@ mod tests {
|
||||
transaction::{DbTx, DbTxMut},
|
||||
};
|
||||
use reth_primitives::{Account, StorageEntry};
|
||||
use reth_storage_api::{BlockHashReader, BlockNumReader, DBProvider, DatabaseProviderFactory};
|
||||
use reth_storage_errors::provider::ProviderError;
|
||||
|
||||
const ADDRESS: Address = address!("0000000000000000000000000000000000000001");
|
||||
@ -542,7 +517,7 @@ mod tests {
|
||||
|
||||
const fn assert_state_provider<T: StateProvider>() {}
|
||||
#[allow(dead_code)]
|
||||
const fn assert_historical_state_provider<T: DbTx>() {
|
||||
const fn assert_historical_state_provider<T: DBProvider + BlockNumReader + BlockHashReader>() {
|
||||
assert_state_provider::<HistoricalStateProvider<T>>();
|
||||
}
|
||||
|
||||
@ -550,7 +525,6 @@ mod tests {
|
||||
fn history_provider_get_account() {
|
||||
let factory = create_test_provider_factory();
|
||||
let tx = factory.provider_rw().unwrap().into_tx();
|
||||
let static_file_provider = factory.static_file_provider();
|
||||
|
||||
tx.put::<tables::AccountsHistory>(
|
||||
ShardedKey { key: ADDRESS, highest_block_number: 7 },
|
||||
@ -610,63 +584,46 @@ mod tests {
|
||||
tx.put::<tables::PlainAccountState>(HIGHER_ADDRESS, higher_acc_plain).unwrap();
|
||||
tx.commit().unwrap();
|
||||
|
||||
let tx = factory.provider().unwrap().into_tx();
|
||||
let db = factory.provider().unwrap();
|
||||
|
||||
// run
|
||||
assert_eq!(HistoricalStateProviderRef::new(&db, 1).basic_account(ADDRESS), Ok(None));
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 1, static_file_provider.clone())
|
||||
.basic_account(ADDRESS),
|
||||
Ok(None)
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 2, static_file_provider.clone())
|
||||
.basic_account(ADDRESS),
|
||||
HistoricalStateProviderRef::new(&db, 2).basic_account(ADDRESS),
|
||||
Ok(Some(acc_at3))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 3, static_file_provider.clone())
|
||||
.basic_account(ADDRESS),
|
||||
HistoricalStateProviderRef::new(&db, 3).basic_account(ADDRESS),
|
||||
Ok(Some(acc_at3))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 4, static_file_provider.clone())
|
||||
.basic_account(ADDRESS),
|
||||
HistoricalStateProviderRef::new(&db, 4).basic_account(ADDRESS),
|
||||
Ok(Some(acc_at7))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 7, static_file_provider.clone())
|
||||
.basic_account(ADDRESS),
|
||||
HistoricalStateProviderRef::new(&db, 7).basic_account(ADDRESS),
|
||||
Ok(Some(acc_at7))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 9, static_file_provider.clone())
|
||||
.basic_account(ADDRESS),
|
||||
HistoricalStateProviderRef::new(&db, 9).basic_account(ADDRESS),
|
||||
Ok(Some(acc_at10))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 10, static_file_provider.clone())
|
||||
.basic_account(ADDRESS),
|
||||
HistoricalStateProviderRef::new(&db, 10).basic_account(ADDRESS),
|
||||
Ok(Some(acc_at10))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 11, static_file_provider.clone())
|
||||
.basic_account(ADDRESS),
|
||||
HistoricalStateProviderRef::new(&db, 11).basic_account(ADDRESS),
|
||||
Ok(Some(acc_at15))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 16, static_file_provider.clone())
|
||||
.basic_account(ADDRESS),
|
||||
HistoricalStateProviderRef::new(&db, 16).basic_account(ADDRESS),
|
||||
Ok(Some(acc_plain))
|
||||
);
|
||||
|
||||
assert_eq!(HistoricalStateProviderRef::new(&db, 1).basic_account(HIGHER_ADDRESS), Ok(None));
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 1, static_file_provider.clone())
|
||||
.basic_account(HIGHER_ADDRESS),
|
||||
Ok(None)
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 1000, static_file_provider)
|
||||
.basic_account(HIGHER_ADDRESS),
|
||||
HistoricalStateProviderRef::new(&db, 1000).basic_account(HIGHER_ADDRESS),
|
||||
Ok(Some(higher_acc_plain))
|
||||
);
|
||||
}
|
||||
@ -675,7 +632,6 @@ mod tests {
|
||||
fn history_provider_get_storage() {
|
||||
let factory = create_test_provider_factory();
|
||||
let tx = factory.provider_rw().unwrap().into_tx();
|
||||
let static_file_provider = factory.static_file_provider();
|
||||
|
||||
tx.put::<tables::StoragesHistory>(
|
||||
StorageShardedKey {
|
||||
@ -722,57 +678,44 @@ mod tests {
|
||||
tx.put::<tables::PlainStorageState>(HIGHER_ADDRESS, higher_entry_plain).unwrap();
|
||||
tx.commit().unwrap();
|
||||
|
||||
let tx = factory.provider().unwrap().into_tx();
|
||||
let db = factory.provider().unwrap();
|
||||
|
||||
// run
|
||||
assert_eq!(HistoricalStateProviderRef::new(&db, 0).storage(ADDRESS, STORAGE), Ok(None));
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 0, static_file_provider.clone())
|
||||
.storage(ADDRESS, STORAGE),
|
||||
Ok(None)
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 3, static_file_provider.clone())
|
||||
.storage(ADDRESS, STORAGE),
|
||||
HistoricalStateProviderRef::new(&db, 3).storage(ADDRESS, STORAGE),
|
||||
Ok(Some(U256::ZERO))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 4, static_file_provider.clone())
|
||||
.storage(ADDRESS, STORAGE),
|
||||
HistoricalStateProviderRef::new(&db, 4).storage(ADDRESS, STORAGE),
|
||||
Ok(Some(entry_at7.value))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 7, static_file_provider.clone())
|
||||
.storage(ADDRESS, STORAGE),
|
||||
HistoricalStateProviderRef::new(&db, 7).storage(ADDRESS, STORAGE),
|
||||
Ok(Some(entry_at7.value))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 9, static_file_provider.clone())
|
||||
.storage(ADDRESS, STORAGE),
|
||||
HistoricalStateProviderRef::new(&db, 9).storage(ADDRESS, STORAGE),
|
||||
Ok(Some(entry_at10.value))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 10, static_file_provider.clone())
|
||||
.storage(ADDRESS, STORAGE),
|
||||
HistoricalStateProviderRef::new(&db, 10).storage(ADDRESS, STORAGE),
|
||||
Ok(Some(entry_at10.value))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 11, static_file_provider.clone())
|
||||
.storage(ADDRESS, STORAGE),
|
||||
HistoricalStateProviderRef::new(&db, 11).storage(ADDRESS, STORAGE),
|
||||
Ok(Some(entry_at15.value))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 16, static_file_provider.clone())
|
||||
.storage(ADDRESS, STORAGE),
|
||||
HistoricalStateProviderRef::new(&db, 16).storage(ADDRESS, STORAGE),
|
||||
Ok(Some(entry_plain.value))
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 1, static_file_provider.clone())
|
||||
.storage(HIGHER_ADDRESS, STORAGE),
|
||||
HistoricalStateProviderRef::new(&db, 1).storage(HIGHER_ADDRESS, STORAGE),
|
||||
Ok(None)
|
||||
);
|
||||
assert_eq!(
|
||||
HistoricalStateProviderRef::new(&tx, 1000, static_file_provider)
|
||||
.storage(HIGHER_ADDRESS, STORAGE),
|
||||
HistoricalStateProviderRef::new(&db, 1000).storage(HIGHER_ADDRESS, STORAGE),
|
||||
Ok(Some(higher_entry_plain.value))
|
||||
);
|
||||
}
|
||||
@ -780,19 +723,17 @@ mod tests {
|
||||
#[test]
|
||||
fn history_provider_unavailable() {
|
||||
let factory = create_test_provider_factory();
|
||||
let tx = factory.provider_rw().unwrap().into_tx();
|
||||
let static_file_provider = factory.static_file_provider();
|
||||
let db = factory.database_provider_rw().unwrap();
|
||||
|
||||
// provider block_number < lowest available block number,
|
||||
// i.e. state at provider block is pruned
|
||||
let provider = HistoricalStateProviderRef::new_with_lowest_available_blocks(
|
||||
&tx,
|
||||
&db,
|
||||
2,
|
||||
LowestAvailableBlocks {
|
||||
account_history_block_number: Some(3),
|
||||
storage_history_block_number: Some(3),
|
||||
},
|
||||
static_file_provider.clone(),
|
||||
);
|
||||
assert_eq!(
|
||||
provider.account_history_lookup(ADDRESS),
|
||||
@ -806,13 +747,12 @@ mod tests {
|
||||
// provider block_number == lowest available block number,
|
||||
// i.e. state at provider block is available
|
||||
let provider = HistoricalStateProviderRef::new_with_lowest_available_blocks(
|
||||
&tx,
|
||||
&db,
|
||||
2,
|
||||
LowestAvailableBlocks {
|
||||
account_history_block_number: Some(2),
|
||||
storage_history_block_number: Some(2),
|
||||
},
|
||||
static_file_provider.clone(),
|
||||
);
|
||||
assert_eq!(provider.account_history_lookup(ADDRESS), Ok(HistoryInfo::MaybeInPlainState));
|
||||
assert_eq!(
|
||||
@ -823,13 +763,12 @@ mod tests {
|
||||
// provider block_number == lowest available block number,
|
||||
// i.e. state at provider block is available
|
||||
let provider = HistoricalStateProviderRef::new_with_lowest_available_blocks(
|
||||
&tx,
|
||||
&db,
|
||||
2,
|
||||
LowestAvailableBlocks {
|
||||
account_history_block_number: Some(1),
|
||||
storage_history_block_number: Some(1),
|
||||
},
|
||||
static_file_provider,
|
||||
);
|
||||
assert_eq!(provider.account_history_lookup(ADDRESS), Ok(HistoryInfo::MaybeInPlainState));
|
||||
assert_eq!(
|
||||
|
||||
Reference in New Issue
Block a user