mirror of
https://github.com/hl-archive-node/nanoreth.git
synced 2025-12-06 10:59:55 +00:00
feat(provider): implement BlockProvider::block (#1426)
This commit is contained in:
@ -150,7 +150,7 @@ impl Command {
|
|||||||
|
|
||||||
// TODO(mattsse): cleanup, add cli args
|
// TODO(mattsse): cleanup, add cli args
|
||||||
let _rpc_server = reth_rpc_builder::launch(
|
let _rpc_server = reth_rpc_builder::launch(
|
||||||
ShareableDatabase::new(db.clone()),
|
ShareableDatabase::new(db.clone(), self.chain.clone()),
|
||||||
reth_transaction_pool::test_utils::testing_pool(),
|
reth_transaction_pool::test_utils::testing_pool(),
|
||||||
network.clone(),
|
network.clone(),
|
||||||
TransportRpcModuleConfig::default()
|
TransportRpcModuleConfig::default()
|
||||||
@ -324,7 +324,7 @@ impl Command {
|
|||||||
.network_config(config, self.chain.clone())
|
.network_config(config, self.chain.clone())
|
||||||
.with_task_executor(Box::new(executor))
|
.with_task_executor(Box::new(executor))
|
||||||
.set_head(head)
|
.set_head(head)
|
||||||
.build(Arc::new(ShareableDatabase::new(db)))
|
.build(Arc::new(ShareableDatabase::new(db, self.chain.clone())))
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn build_pipeline<H, B, U>(
|
async fn build_pipeline<H, B, U>(
|
||||||
|
|||||||
@ -107,7 +107,7 @@ impl Command {
|
|||||||
network_config_builder = self.discovery.apply_to_builder(network_config_builder);
|
network_config_builder = self.discovery.apply_to_builder(network_config_builder);
|
||||||
|
|
||||||
let network = network_config_builder
|
let network = network_config_builder
|
||||||
.build(Arc::new(ShareableDatabase::new(noop_db)))
|
.build(Arc::new(ShareableDatabase::new(noop_db, self.chain.clone())))
|
||||||
.start_network()
|
.start_network()
|
||||||
.await?;
|
.await?;
|
||||||
|
|
||||||
|
|||||||
@ -136,7 +136,7 @@ impl Command {
|
|||||||
let network = self
|
let network = self
|
||||||
.network
|
.network
|
||||||
.network_config(&config, self.chain.clone())
|
.network_config(&config, self.chain.clone())
|
||||||
.build(Arc::new(ShareableDatabase::new(db.clone())))
|
.build(Arc::new(ShareableDatabase::new(db.clone(), self.chain.clone())))
|
||||||
.start_network()
|
.start_network()
|
||||||
.await?;
|
.await?;
|
||||||
let fetch_client = Arc::new(network.fetch_client().await?);
|
let fetch_client = Arc::new(network.fetch_client().await?);
|
||||||
|
|||||||
@ -5,7 +5,9 @@ use reth_db::{
|
|||||||
transaction::DbTx,
|
transaction::DbTx,
|
||||||
};
|
};
|
||||||
use reth_interfaces::Result;
|
use reth_interfaces::Result;
|
||||||
use reth_primitives::{rpc::BlockId, Block, BlockHash, BlockNumber, ChainInfo, Header, H256, U256};
|
use reth_primitives::{
|
||||||
|
rpc::BlockId, Block, BlockHash, BlockNumber, ChainInfo, ChainSpec, Hardfork, Header, H256, U256,
|
||||||
|
};
|
||||||
use std::ops::RangeBounds;
|
use std::ops::RangeBounds;
|
||||||
|
|
||||||
mod state;
|
mod state;
|
||||||
@ -22,18 +24,20 @@ pub use state::{
|
|||||||
pub struct ShareableDatabase<DB> {
|
pub struct ShareableDatabase<DB> {
|
||||||
/// Database
|
/// Database
|
||||||
db: DB,
|
db: DB,
|
||||||
|
/// Chain spec
|
||||||
|
chain_spec: ChainSpec,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<DB> ShareableDatabase<DB> {
|
impl<DB> ShareableDatabase<DB> {
|
||||||
/// create new database provider
|
/// create new database provider
|
||||||
pub fn new(db: DB) -> Self {
|
pub fn new(db: DB, chain_spec: ChainSpec) -> Self {
|
||||||
Self { db }
|
Self { db, chain_spec }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<DB: Clone> Clone for ShareableDatabase<DB> {
|
impl<DB: Clone> Clone for ShareableDatabase<DB> {
|
||||||
fn clone(&self) -> Self {
|
fn clone(&self) -> Self {
|
||||||
Self { db: self.db.clone() }
|
Self { db: self.db.clone(), chain_spec: self.chain_spec.clone() }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -99,8 +103,42 @@ impl<DB: Database> BlockProvider for ShareableDatabase<DB> {
|
|||||||
Ok(ChainInfo { best_hash, best_number, last_finalized: None, safe_finalized: None })
|
Ok(ChainInfo { best_hash, best_number, last_finalized: None, safe_finalized: None })
|
||||||
}
|
}
|
||||||
|
|
||||||
fn block(&self, _id: BlockId) -> Result<Option<Block>> {
|
fn block(&self, id: BlockId) -> Result<Option<Block>> {
|
||||||
// TODO
|
if let Some(number) = self.block_number_for_id(id)? {
|
||||||
|
if let Some(header) = self.header_by_number(number)? {
|
||||||
|
let tx = self.db.tx()?;
|
||||||
|
let body = tx
|
||||||
|
.get::<tables::BlockBodies>(header.number)?
|
||||||
|
.ok_or(Error::BlockBody { number })?;
|
||||||
|
|
||||||
|
let mut tx_cursor = tx.cursor_read::<tables::Transactions>()?;
|
||||||
|
let mut transactions = Vec::with_capacity(body.tx_count as usize);
|
||||||
|
for id in body.tx_id_range() {
|
||||||
|
let (_, transaction) =
|
||||||
|
tx_cursor.seek_exact(id)?.ok_or(Error::Transaction { id })?;
|
||||||
|
transactions.push(transaction);
|
||||||
|
}
|
||||||
|
|
||||||
|
let ommers = tx.get::<tables::BlockOmmers>(header.number)?.map(|o| o.ommers);
|
||||||
|
|
||||||
|
let header_timestamp = header.timestamp;
|
||||||
|
let mut block = Block {
|
||||||
|
header,
|
||||||
|
body: transactions,
|
||||||
|
ommers: ommers.unwrap_or_default(),
|
||||||
|
withdrawals: None,
|
||||||
|
};
|
||||||
|
|
||||||
|
if self.chain_spec.fork(Hardfork::Shanghai).active_at_timestamp(header_timestamp) {
|
||||||
|
let withdrawals =
|
||||||
|
tx.get::<tables::BlockWithdrawals>(number)?.map(|w| w.withdrawals);
|
||||||
|
block.withdrawals = Some(withdrawals.unwrap_or_default());
|
||||||
|
}
|
||||||
|
|
||||||
|
return Ok(Some(block))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
Ok(None)
|
Ok(None)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -149,19 +187,21 @@ mod tests {
|
|||||||
|
|
||||||
use super::ShareableDatabase;
|
use super::ShareableDatabase;
|
||||||
use reth_db::mdbx::{test_utils::create_test_db, EnvKind, WriteMap};
|
use reth_db::mdbx::{test_utils::create_test_db, EnvKind, WriteMap};
|
||||||
use reth_primitives::H256;
|
use reth_primitives::{ChainSpecBuilder, H256};
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn common_history_provider() {
|
fn common_history_provider() {
|
||||||
|
let chain_spec = ChainSpecBuilder::mainnet().build();
|
||||||
let db = create_test_db::<WriteMap>(EnvKind::RW);
|
let db = create_test_db::<WriteMap>(EnvKind::RW);
|
||||||
let provider = ShareableDatabase::new(db);
|
let provider = ShareableDatabase::new(db, chain_spec);
|
||||||
let _ = provider.latest();
|
let _ = provider.latest();
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn default_chain_info() {
|
fn default_chain_info() {
|
||||||
|
let chain_spec = ChainSpecBuilder::mainnet().build();
|
||||||
let db = create_test_db::<WriteMap>(EnvKind::RW);
|
let db = create_test_db::<WriteMap>(EnvKind::RW);
|
||||||
let provider = ShareableDatabase::new(db);
|
let provider = ShareableDatabase::new(db, chain_spec);
|
||||||
|
|
||||||
let chain_info = provider.chain_info().expect("should be ok");
|
let chain_info = provider.chain_info().expect("should be ok");
|
||||||
assert_eq!(chain_info.best_number, 0);
|
assert_eq!(chain_info.best_number, 0);
|
||||||
|
|||||||
@ -1,3 +1,5 @@
|
|||||||
|
use crate::HeaderProvider;
|
||||||
|
|
||||||
use super::BlockHashProvider;
|
use super::BlockHashProvider;
|
||||||
use reth_interfaces::Result;
|
use reth_interfaces::Result;
|
||||||
use reth_primitives::{
|
use reth_primitives::{
|
||||||
@ -6,7 +8,7 @@ use reth_primitives::{
|
|||||||
};
|
};
|
||||||
|
|
||||||
/// Api trait for fetching `Block` related data.
|
/// Api trait for fetching `Block` related data.
|
||||||
pub trait BlockProvider: BlockHashProvider + Send + Sync {
|
pub trait BlockProvider: BlockHashProvider + HeaderProvider + Send + Sync {
|
||||||
/// Returns the current info for the chain.
|
/// Returns the current info for the chain.
|
||||||
fn chain_info(&self) -> Result<ChainInfo>;
|
fn chain_info(&self) -> Result<ChainInfo>;
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user