mirror of
https://github.com/bitcoinresearchkit/brk.git
synced 2026-04-26 07:39:59 -07:00
132 lines
3.2 KiB
Rust
132 lines
3.2 KiB
Rust
#![doc = include_str!("../README.md")]
|
|
#![allow(clippy::module_inception)]
|
|
|
|
use std::sync::Arc;
|
|
|
|
use brk_computer::Computer;
|
|
use brk_indexer::Indexer;
|
|
use brk_mempool::Mempool;
|
|
use brk_reader::Reader;
|
|
use brk_rpc::Client;
|
|
use brk_types::{Height, SyncStatus};
|
|
use vecdb::{AnyVec, ReadOnlyClone, ReadableVec, Ro};
|
|
|
|
#[cfg(feature = "tokio")]
|
|
mod r#async;
|
|
mod vecs;
|
|
|
|
mod r#impl;
|
|
|
|
#[cfg(feature = "tokio")]
|
|
pub use r#async::*;
|
|
pub use r#impl::{BLOCK_TXS_PAGE_SIZE, ResolvedQuery};
|
|
pub use vecs::Vecs;
|
|
|
|
#[derive(Clone)]
|
|
pub struct Query(Arc<QueryInner<'static>>);
|
|
struct QueryInner<'a> {
|
|
vecs: &'a Vecs<'a>,
|
|
client: Client,
|
|
reader: Reader,
|
|
indexer: &'a Indexer<Ro>,
|
|
computer: &'a Computer<Ro>,
|
|
mempool: Option<Mempool>,
|
|
}
|
|
|
|
impl Query {
|
|
pub fn build(
|
|
reader: &Reader,
|
|
indexer: &Indexer,
|
|
computer: &Computer,
|
|
mempool: Option<Mempool>,
|
|
) -> Self {
|
|
let client = reader.client().clone();
|
|
let reader = reader.clone();
|
|
let indexer = Box::leak(Box::new(indexer.read_only_clone()));
|
|
let computer = Box::leak(Box::new(computer.read_only_clone()));
|
|
let vecs = Box::leak(Box::new(Vecs::build(indexer, computer)));
|
|
|
|
Self(Arc::new(QueryInner {
|
|
vecs,
|
|
client,
|
|
reader,
|
|
indexer,
|
|
computer,
|
|
mempool,
|
|
}))
|
|
}
|
|
|
|
/// Current indexed height
|
|
pub fn indexed_height(&self) -> Height {
|
|
Height::from(self.indexer().vecs.blocks.blockhash.stamp())
|
|
}
|
|
|
|
/// Current computed height (metrics)
|
|
pub fn computed_height(&self) -> Height {
|
|
Height::from(self.computer().distribution.supply_state.len())
|
|
}
|
|
|
|
/// Minimum of indexed and computed heights
|
|
pub fn height(&self) -> Height {
|
|
self.indexed_height().min(self.computed_height())
|
|
}
|
|
|
|
/// Build sync status with the given tip height
|
|
pub fn sync_status(&self, tip_height: Height) -> SyncStatus {
|
|
let indexed_height = self.indexed_height();
|
|
let computed_height = self.computed_height();
|
|
let blocks_behind = Height::from(tip_height.saturating_sub(*indexed_height));
|
|
let last_indexed_at_unix = self
|
|
.indexer()
|
|
.vecs
|
|
.blocks
|
|
.timestamp
|
|
.collect_one(indexed_height)
|
|
.unwrap();
|
|
|
|
SyncStatus {
|
|
indexed_height,
|
|
computed_height,
|
|
tip_height,
|
|
blocks_behind,
|
|
last_indexed_at: last_indexed_at_unix.to_iso8601(),
|
|
last_indexed_at_unix,
|
|
}
|
|
}
|
|
|
|
#[inline]
|
|
pub fn reader(&self) -> &Reader {
|
|
&self.0.reader
|
|
}
|
|
|
|
#[inline]
|
|
pub fn client(&self) -> &Client {
|
|
&self.0.client
|
|
}
|
|
|
|
#[inline]
|
|
pub fn blocks_dir(&self) -> &std::path::Path {
|
|
self.0.reader.blocks_dir()
|
|
}
|
|
|
|
#[inline]
|
|
pub fn indexer(&self) -> &Indexer<Ro> {
|
|
self.0.indexer
|
|
}
|
|
|
|
#[inline]
|
|
pub fn computer(&self) -> &Computer<Ro> {
|
|
self.0.computer
|
|
}
|
|
|
|
#[inline]
|
|
pub fn mempool(&self) -> Option<&Mempool> {
|
|
self.0.mempool.as_ref()
|
|
}
|
|
|
|
#[inline]
|
|
pub fn vecs(&self) -> &'static Vecs<'static> {
|
|
self.0.vecs
|
|
}
|
|
}
|