mirror of
https://github.com/bitcoinresearchkit/brk.git
synced 2026-04-30 09:30:00 -07:00
server: smart generic vec routes build
This commit is contained in:
@@ -100,7 +100,7 @@ fn req_to_response_res(
|
||||
let values = ids
|
||||
.iter()
|
||||
.flat_map(|(_, i_to_v)| i_to_v.get(indexes.first().unwrap()))
|
||||
.map(|vec| -> storable_vec::Result<Vec<Value>> { vec.collect_range(from, to) })
|
||||
.map(|vec| -> storable_vec::Result<Vec<Value>> { vec.collect_range_values(from, to) })
|
||||
.collect::<storable_vec::Result<Vec<_>>>()?;
|
||||
|
||||
if ids.is_empty() {
|
||||
|
||||
@@ -1,15 +1,9 @@
|
||||
use std::fmt::{self, Debug};
|
||||
|
||||
use computer::Dateindex;
|
||||
use indexer::{
|
||||
Addressindex, Height, P2PK33index, P2PK65index, P2PKHindex, P2SHindex, P2TRindex, P2WPKHindex, P2WSHindex, Txindex,
|
||||
Txinindex, Txoutindex,
|
||||
};
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord)]
|
||||
pub enum Index {
|
||||
Addressindex,
|
||||
DateIndex,
|
||||
Dateindex,
|
||||
Height,
|
||||
P2PK33index,
|
||||
P2PK65index,
|
||||
@@ -27,7 +21,7 @@ impl TryFrom<&str> for Index {
|
||||
type Error = ();
|
||||
fn try_from(value: &str) -> Result<Self, Self::Error> {
|
||||
Ok(match value {
|
||||
"d" | "date" => Self::Date,
|
||||
"d" | "date" | "dateindex" => Self::Dateindex,
|
||||
"h" | "height" => Self::Height,
|
||||
"txi" | "txindex" => Self::Txindex,
|
||||
"txini" | "txinindex" => Self::Txinindex,
|
||||
@@ -50,73 +44,3 @@ impl fmt::Display for Index {
|
||||
Debug::fmt(self, f)
|
||||
}
|
||||
}
|
||||
|
||||
pub trait IndexTypeToIndexEnum {
|
||||
fn to_enum() -> Index;
|
||||
}
|
||||
|
||||
impl IndexTypeToIndexEnum for Addressindex {
|
||||
fn to_enum() -> Index {
|
||||
Index::Addressindex
|
||||
}
|
||||
}
|
||||
impl IndexTypeToIndexEnum for Dateindex {
|
||||
fn to_enum() -> Index {
|
||||
Index::DateIndex
|
||||
}
|
||||
}
|
||||
impl IndexTypeToIndexEnum for Height {
|
||||
fn to_enum() -> Index {
|
||||
Index::Height
|
||||
}
|
||||
}
|
||||
impl IndexTypeToIndexEnum for Txindex {
|
||||
fn to_enum() -> Index {
|
||||
Index::Txindex
|
||||
}
|
||||
}
|
||||
impl IndexTypeToIndexEnum for Txinindex {
|
||||
fn to_enum() -> Index {
|
||||
Index::Txinindex
|
||||
}
|
||||
}
|
||||
impl IndexTypeToIndexEnum for Txoutindex {
|
||||
fn to_enum() -> Index {
|
||||
Index::Txoutindex
|
||||
}
|
||||
}
|
||||
impl IndexTypeToIndexEnum for P2PK33index {
|
||||
fn to_enum() -> Index {
|
||||
Index::P2PK33index
|
||||
}
|
||||
}
|
||||
impl IndexTypeToIndexEnum for P2PK65index {
|
||||
fn to_enum() -> Index {
|
||||
Index::P2PK65index
|
||||
}
|
||||
}
|
||||
impl IndexTypeToIndexEnum for P2PKHindex {
|
||||
fn to_enum() -> Index {
|
||||
Index::P2PKHindex
|
||||
}
|
||||
}
|
||||
impl IndexTypeToIndexEnum for P2SHindex {
|
||||
fn to_enum() -> Index {
|
||||
Index::P2SHindex
|
||||
}
|
||||
}
|
||||
impl IndexTypeToIndexEnum for P2TRindex {
|
||||
fn to_enum() -> Index {
|
||||
Index::P2TRindex
|
||||
}
|
||||
}
|
||||
impl IndexTypeToIndexEnum for P2WPKHindex {
|
||||
fn to_enum() -> Index {
|
||||
Index::P2WPKHindex
|
||||
}
|
||||
}
|
||||
impl IndexTypeToIndexEnum for P2WSHindex {
|
||||
fn to_enum() -> Index {
|
||||
Index::P2WSHindex
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,52 +0,0 @@
|
||||
use std::collections::BTreeSet;
|
||||
|
||||
use color_eyre::eyre::{eyre, ContextCompat};
|
||||
use serde::Deserialize;
|
||||
|
||||
use crate::structs::{AnyMap, Date, Height, MapKey};
|
||||
|
||||
#[derive(Debug, Clone, Copy, Deserialize, PartialEq, Eq, PartialOrd, Ord)]
|
||||
pub enum Kind {
|
||||
Date,
|
||||
Height,
|
||||
// Timestamp,
|
||||
// Last,
|
||||
}
|
||||
|
||||
impl TryFrom<&String> for Kind {
|
||||
type Error = color_eyre::Report;
|
||||
|
||||
fn try_from(str: &String) -> Result<Self, Self::Error> {
|
||||
Ok(
|
||||
match str
|
||||
.to_lowercase()
|
||||
.chars()
|
||||
.next()
|
||||
.context("Expect kind to have first letter")?
|
||||
{
|
||||
'd' => Self::Date,
|
||||
'h' => Self::Height,
|
||||
// 't' => Self::Timestamp,
|
||||
// 'l' => Self::Last,
|
||||
_ => return Err(eyre!("Bad kind")),
|
||||
},
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
impl From<&(dyn AnyMap + Send + Sync)> for BTreeSet<Kind> {
|
||||
fn from(map: &(dyn AnyMap + Send + Sync)) -> Self {
|
||||
let mut s = Self::new();
|
||||
if map.key_name() == Date::map_name() {
|
||||
s.insert(Kind::Date);
|
||||
}
|
||||
if map.key_name() == Height::map_name() {
|
||||
s.insert(Kind::Height);
|
||||
s.insert(Kind::Timestamp);
|
||||
}
|
||||
if map.last_value().is_some() {
|
||||
s.insert(Kind::Last);
|
||||
}
|
||||
s
|
||||
}
|
||||
}
|
||||
@@ -1,19 +1,15 @@
|
||||
use std::{collections::BTreeMap, time::Instant};
|
||||
|
||||
use api::{
|
||||
structs::{Index, IndexTypeToIndexEnum},
|
||||
ApiRoutes,
|
||||
};
|
||||
use axum::{body::Body, response::IntoResponse, routing::get, serve, Router};
|
||||
use api::{structs::Index, ApiRoutes};
|
||||
use axum::{routing::get, serve, Router};
|
||||
use color_eyre::owo_colors::OwoColorize;
|
||||
use computer::Computer;
|
||||
use derive_deref::{Deref, DerefMut};
|
||||
use indexer::Indexer;
|
||||
use logger::{error, info};
|
||||
use oxc::syntax::identifier::LF;
|
||||
use reqwest::StatusCode;
|
||||
use serde::Serialize;
|
||||
use serde_json::Value;
|
||||
use storable_vec::{StorableVecIndex, StorableVecType, STATELESS};
|
||||
use storable_vec::{AnyJsonStorableVec, STATELESS};
|
||||
use tokio::net::TcpListener;
|
||||
use tower_http::compression::CompressionLayer;
|
||||
use website::WebsiteRoutes;
|
||||
@@ -33,17 +29,18 @@ pub struct AppState {
|
||||
pub struct VecIdToIndexToVec(BTreeMap<String, IndexToVec>);
|
||||
|
||||
impl VecIdToIndexToVec {
|
||||
pub fn insert<I, T>(&mut self, vec: &'static storable_vec::StorableVec<I, T, STATELESS>)
|
||||
where
|
||||
I: StorableVecIndex + IndexTypeToIndexEnum + Send + Sync,
|
||||
T: StorableVecType + Send + Sync + Serialize,
|
||||
{
|
||||
pub fn insert(&mut self, vec: &'static dyn AnyJsonStorableVec) {
|
||||
let file_name = vec.file_name();
|
||||
let split = file_name.split("_to_").collect::<Vec<_>>();
|
||||
if split.len() != 2 {
|
||||
panic!();
|
||||
}
|
||||
let index = vec.key_to_enum();
|
||||
let str = vec.index_type_to_string().split("::").last().unwrap().to_lowercase();
|
||||
let index = Index::try_from(str.as_str())
|
||||
.inspect_err(|_| {
|
||||
dbg!(str);
|
||||
})
|
||||
.unwrap();
|
||||
if split[0] != index.to_string().to_lowercase() {
|
||||
dbg!(split[0], index.to_string());
|
||||
panic!();
|
||||
@@ -58,80 +55,7 @@ impl VecIdToIndexToVec {
|
||||
|
||||
#[derive(Default, Deref, DerefMut)]
|
||||
pub struct IndexToVec {
|
||||
pub index_to_vec: BTreeMap<Index, &'static (dyn AnyStatelessStorableVec + Send + Sync)>,
|
||||
}
|
||||
|
||||
pub trait AnyStatelessStorableVec {
|
||||
fn key_to_enum(&self) -> Index;
|
||||
fn collect_range(&self, from: Option<i64>, to: Option<i64>) -> storable_vec::Result<Vec<Value>>;
|
||||
// fn collect_range(&self, from: Option<i64>, to: Option<i64>) -> storable_vec::Result<Vec<T>>;
|
||||
}
|
||||
|
||||
impl<I, T> AnyStatelessStorableVec for storable_vec::StorableVec<I, T, STATELESS>
|
||||
where
|
||||
I: StorableVecIndex + IndexTypeToIndexEnum + Send + Sync,
|
||||
T: StorableVecType + Send + Sync + Serialize,
|
||||
{
|
||||
fn key_to_enum(&self) -> Index {
|
||||
I::to_enum()
|
||||
}
|
||||
|
||||
fn collect_range(&self, from: Option<i64>, to: Option<i64>) -> storable_vec::Result<Vec<Value>> {
|
||||
Ok(self
|
||||
.collect_range(from, to)?
|
||||
.into_iter()
|
||||
.map(|v| serde_json::to_value(v).unwrap())
|
||||
.collect::<Vec<_>>())
|
||||
}
|
||||
}
|
||||
|
||||
trait StatelessVecs {
|
||||
fn parse(&'static self, vecs: &mut VecIdToIndexToVec);
|
||||
}
|
||||
|
||||
impl StatelessVecs for Indexer<STATELESS> {
|
||||
fn parse(&'static self, vecs: &mut VecIdToIndexToVec) {
|
||||
vecs.insert(&self.vecs.addressindex_to_addresstype);
|
||||
vecs.insert(&self.vecs.addressindex_to_addresstypeindex);
|
||||
vecs.insert(&self.vecs.addressindex_to_height);
|
||||
vecs.insert(&self.vecs.height_to_blockhash);
|
||||
vecs.insert(&self.vecs.height_to_difficulty);
|
||||
vecs.insert(&self.vecs.height_to_first_addressindex);
|
||||
vecs.insert(&self.vecs.height_to_first_emptyindex);
|
||||
vecs.insert(&self.vecs.height_to_first_multisigindex);
|
||||
vecs.insert(&self.vecs.height_to_first_opreturnindex);
|
||||
vecs.insert(&self.vecs.height_to_first_pushonlyindex);
|
||||
vecs.insert(&self.vecs.height_to_first_txindex);
|
||||
vecs.insert(&self.vecs.height_to_first_txinindex);
|
||||
vecs.insert(&self.vecs.height_to_first_txoutindex);
|
||||
vecs.insert(&self.vecs.height_to_first_unknownindex);
|
||||
vecs.insert(&self.vecs.height_to_first_p2pk33index);
|
||||
vecs.insert(&self.vecs.height_to_first_p2pk65index);
|
||||
vecs.insert(&self.vecs.height_to_first_p2pkhindex);
|
||||
vecs.insert(&self.vecs.height_to_first_p2shindex);
|
||||
vecs.insert(&self.vecs.height_to_first_p2trindex);
|
||||
vecs.insert(&self.vecs.height_to_first_p2wpkhindex);
|
||||
vecs.insert(&self.vecs.height_to_first_p2wshindex);
|
||||
vecs.insert(&self.vecs.height_to_size);
|
||||
vecs.insert(&self.vecs.height_to_timestamp);
|
||||
vecs.insert(&self.vecs.height_to_weight);
|
||||
vecs.insert(&self.vecs.p2pk33index_to_p2pk33addressbytes);
|
||||
vecs.insert(&self.vecs.p2pk65index_to_p2pk65addressbytes);
|
||||
vecs.insert(&self.vecs.p2pkhindex_to_p2pkhaddressbytes);
|
||||
vecs.insert(&self.vecs.p2shindex_to_p2shaddressbytes);
|
||||
vecs.insert(&self.vecs.p2trindex_to_p2traddressbytes);
|
||||
vecs.insert(&self.vecs.p2wpkhindex_to_p2wpkhaddressbytes);
|
||||
vecs.insert(&self.vecs.p2wshindex_to_p2wshaddressbytes);
|
||||
vecs.insert(&self.vecs.txindex_to_first_txinindex);
|
||||
vecs.insert(&self.vecs.txindex_to_first_txoutindex);
|
||||
vecs.insert(&self.vecs.txindex_to_height);
|
||||
vecs.insert(&self.vecs.txindex_to_locktime);
|
||||
vecs.insert(&self.vecs.txindex_to_txid);
|
||||
vecs.insert(&self.vecs.txindex_to_txversion);
|
||||
vecs.insert(&self.vecs.txinindex_to_txoutindex);
|
||||
vecs.insert(&self.vecs.txoutindex_to_addressindex);
|
||||
vecs.insert(&self.vecs.txoutindex_to_amount);
|
||||
}
|
||||
pub index_to_vec: BTreeMap<Index, &'static dyn AnyJsonStorableVec>,
|
||||
}
|
||||
|
||||
pub async fn main(indexer: Indexer<STATELESS>, computer: Computer<STATELESS>) -> color_eyre::Result<()> {
|
||||
@@ -141,7 +65,12 @@ pub async fn main(indexer: Indexer<STATELESS>, computer: Computer<STATELESS>) ->
|
||||
let indexer = Box::leak(Box::new(indexer));
|
||||
let computer = Box::leak(Box::new(computer));
|
||||
let vecs = Box::leak(Box::new(VecIdToIndexToVec::default()));
|
||||
indexer.parse(vecs);
|
||||
|
||||
indexer
|
||||
.vecs
|
||||
.as_any_json_vec_slice()
|
||||
.into_iter()
|
||||
.for_each(|vec| vecs.insert(vec));
|
||||
|
||||
let state = AppState {
|
||||
vecs,
|
||||
|
||||
Reference in New Issue
Block a user