global: snapshot

This commit is contained in:
nym21
2025-10-13 13:52:33 +02:00
parent 7bfca87caf
commit db0298ac1b
58 changed files with 1094 additions and 653 deletions
+18 -19
View File
@@ -1,24 +1,21 @@
use std::str::FromStr;
use bitcoin::{Address, Network, PublicKey, ScriptBuf};
use bitcoin::{Network, PublicKey, ScriptBuf};
use brk_error::{Error, Result};
use brk_structs::{
AddressBytes, AddressBytesHash, AddressInfo, AddressPath, AnyAddressDataIndexEnum, Bitcoin,
Address, AddressBytes, AddressBytesHash, AddressStats, AnyAddressDataIndexEnum, Bitcoin,
OutputType,
};
use vecdb::{AnyIterableVec, VecIterator};
use crate::Interface;
pub fn get_address_info(
AddressPath { address }: AddressPath,
interface: &Interface,
) -> Result<AddressInfo> {
pub fn get_address(Address { address }: Address, interface: &Interface) -> Result<AddressStats> {
let indexer = interface.indexer();
let computer = interface.computer();
let stores = &indexer.stores;
let script = if let Ok(address) = Address::from_str(&address) {
let script = if let Ok(address) = bitcoin::Address::from_str(&address) {
if !address.is_valid_for_network(Network::Bitcoin) {
return Err(Error::InvalidNetwork);
}
@@ -109,16 +106,18 @@ pub fn get_address_info(
let balance = address_data.balance();
Ok(AddressInfo {
address: address.to_string(),
r#type: type_,
type_index,
utxo_count: address_data.utxo_count,
total_sent: address_data.sent,
total_received: address_data.received,
balance,
balance_usd: price.map(|p| p * Bitcoin::from(balance)),
estimated_total_invested: price.map(|_| address_data.realized_cap),
estimated_avg_entry_price: price.map(|_| address_data.realized_price()),
})
todo!();
// Ok(Address {
// address: address.to_string(),
// r#type: type_,
// type_index,
// utxo_count: address_data.utxo_count,
// total_sent: address_data.sent,
// total_received: address_data.received,
// balance,
// balance_usd: price.map(|p| p * Bitcoin::from(balance)),
// estimated_total_invested: price.map(|_| address_data.realized_cap),
// estimated_avg_entry_price: price.map(|_| address_data.realized_price()),
// })
}
+9 -10
View File
@@ -7,15 +7,12 @@ use std::{
use bitcoin::{Transaction, consensus::Decodable};
use brk_error::{Error, Result};
use brk_parser::XORIndex;
use brk_structs::{TransactionInfo, Txid, TxidPath, TxidPrefix};
use brk_structs::{Tx, Txid, TxidPath, TxidPrefix};
use vecdb::VecIterator;
use crate::Interface;
pub fn get_transaction_info(
TxidPath { txid }: TxidPath,
interface: &Interface,
) -> Result<TransactionInfo> {
pub fn get_transaction_info(TxidPath { txid }: TxidPath, interface: &Interface) -> Result<Tx> {
let Ok(txid) = bitcoin::Txid::from_str(&txid) else {
return Err(Error::InvalidTxid);
};
@@ -79,9 +76,11 @@ pub fn get_transaction_info(
return Err(Error::Str("Failed decode the transaction"));
};
Ok(TransactionInfo {
txid,
index,
// tx
})
todo!();
// Ok(TxInfo {
// txid,
// index,
// // tx
// })
}
+10 -10
View File
@@ -7,26 +7,26 @@ use brk_error::Result;
use brk_indexer::Indexer;
use brk_parser::Parser;
use brk_structs::{
AddressInfo, AddressPath, Format, Height, Index, IndexInfo, MetricCount, MetricSearchQuery,
TransactionInfo, TxidPath,
Address, AddressStats, Format, Height, Index, IndexInfo, Limit, Metric, MetricCount, Tx,
TxidPath,
};
use brk_traversable::TreeNode;
use vecdb::{AnyCollectableVec, AnyStoredVec};
mod chain;
mod deser;
mod metrics;
mod output;
mod pagination;
mod params;
mod vecs;
pub use metrics::{Output, Value};
pub use output::{Output, Value};
pub use pagination::{PaginatedIndexParam, PaginatedMetrics, PaginationParam};
pub use params::{Params, ParamsDeprec, ParamsOpt};
use vecs::Vecs;
use crate::{
chain::{get_address_info, get_transaction_info},
chain::{get_address, get_transaction_info},
vecs::{IndexToVec, MetricToVec},
};
@@ -57,16 +57,16 @@ impl<'a> Interface<'a> {
Height::from(self.indexer.vecs.height_to_blockhash.stamp())
}
pub fn get_address_info(&self, address: AddressPath) -> Result<AddressInfo> {
get_address_info(address, self)
pub fn get_address(&self, address: Address) -> Result<AddressStats> {
get_address(address, self)
}
pub fn get_transaction_info(&self, txid: TxidPath) -> Result<TransactionInfo> {
pub fn get_transaction_info(&self, txid: TxidPath) -> Result<Tx> {
get_transaction_info(txid, self)
}
pub fn match_metric(&self, query: MetricSearchQuery) -> Vec<&str> {
self.vecs.matches(query)
pub fn match_metric(&self, metric: &Metric, limit: Limit) -> Vec<&str> {
self.vecs.matches(metric, limit)
}
pub fn search_metric_with_index(
-91
View File
@@ -1,91 +0,0 @@
use std::fmt;
use derive_deref::Deref;
use schemars::JsonSchema;
use serde::Deserialize;
mod output;
pub use output::*;
#[derive(Debug, Deref, JsonSchema)]
pub struct MaybeMetrics(Vec<String>);
const MAX_VECS: usize = 32;
const MAX_STRING_SIZE: usize = 64 * MAX_VECS;
impl From<String> for MaybeMetrics {
fn from(value: String) -> Self {
Self(vec![value.replace("-", "_").to_lowercase()])
}
}
impl<'a> From<Vec<&'a str>> for MaybeMetrics {
fn from(value: Vec<&'a str>) -> Self {
Self(
value
.iter()
.map(|s| s.replace("-", "_").to_lowercase())
.collect::<Vec<_>>(),
)
}
}
impl<'de> Deserialize<'de> for MaybeMetrics {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: serde::Deserializer<'de>,
{
let value = serde_json::Value::deserialize(deserializer)?;
if let Some(str) = value.as_str() {
if str.len() <= MAX_STRING_SIZE {
Ok(MaybeMetrics(sanitize_metrics(
str.split(",").map(|s| s.to_string()),
)))
} else {
Err(serde::de::Error::custom("Given parameter is too long"))
}
} else if let Some(vec) = value.as_array() {
if vec.len() <= MAX_VECS {
Ok(MaybeMetrics(sanitize_metrics(
vec.iter().map(|s| s.as_str().unwrap().to_string()),
)))
} else {
Err(serde::de::Error::custom("Given parameter is too long"))
}
} else {
Err(serde::de::Error::custom("Bad ids format"))
}
}
}
impl fmt::Display for MaybeMetrics {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
let s = self.0.join(",");
write!(f, "{s}")
}
}
fn sanitize_metrics(raw_ids: impl Iterator<Item = String>) -> Vec<String> {
let mut results = Vec::new();
raw_ids.for_each(|s| {
let mut current = String::new();
for c in s.to_lowercase().chars() {
match c {
' ' | ',' | '+' => {
if !current.is_empty() {
results.push(std::mem::take(&mut current));
}
}
'-' => current.push('_'),
c if c.is_alphanumeric() || c == '_' => current.push(c),
_ => {}
}
}
if !current.is_empty() {
results.push(current);
}
});
results
}
+18 -11
View File
@@ -1,21 +1,18 @@
use std::ops::Deref;
use brk_structs::{Format, Index};
use brk_structs::{Format, Index, Metric, Metrics};
use derive_deref::Deref;
use schemars::JsonSchema;
use serde::Deserialize;
use crate::{
deser::{de_unquote_i64, de_unquote_usize},
metrics::MaybeMetrics,
};
use crate::deser::{de_unquote_i64, de_unquote_usize};
#[derive(Debug, Deserialize, JsonSchema)]
pub struct Params {
/// Requested metrics
#[serde(alias = "m")]
pub metrics: MaybeMetrics,
pub metrics: Metrics,
/// Requested index
#[serde(alias = "i")]
pub index: Index,
@@ -30,11 +27,21 @@ impl Deref for Params {
}
}
impl From<((Index, String), ParamsOpt)> for Params {
fn from(((index, metric), rest): ((Index, String), ParamsOpt)) -> Self {
impl From<(Index, Metric, ParamsOpt)> for Params {
fn from((index, metric, rest): (Index, Metric, ParamsOpt)) -> Self {
Self {
index,
metrics: MaybeMetrics::from(metric),
metrics: Metrics::from(metric),
rest,
}
}
}
impl From<(Index, Metrics, ParamsOpt)> for Params {
fn from((index, metrics, rest): (Index, Metrics, ParamsOpt)) -> Self {
Self {
index,
metrics,
rest,
}
}
@@ -105,7 +112,7 @@ pub struct ParamsDeprec {
#[serde(alias = "i")]
pub index: Index,
#[serde(alias = "v")]
pub ids: MaybeMetrics,
pub ids: Metrics,
#[serde(flatten)]
pub rest: ParamsOpt,
}
+3 -3
View File
@@ -2,7 +2,7 @@ use std::collections::BTreeMap;
use brk_computer::Computer;
use brk_indexer::Indexer;
use brk_structs::{Index, IndexInfo, MetricSearchQuery};
use brk_structs::{Index, IndexInfo, Limit, Metric};
use brk_traversable::{Traversable, TreeNode};
use derive_deref::{Deref, DerefMut};
use quickmatch::{QuickMatch, QuickMatchConfig};
@@ -172,9 +172,9 @@ impl<'a> Vecs<'a> {
self.catalog.as_ref().unwrap()
}
pub fn matches(&self, query: MetricSearchQuery) -> Vec<&'_ str> {
pub fn matches(&self, metric: &Metric, limit: Limit) -> Vec<&'_ str> {
self.matcher()
.matches_with(&query.q, &QuickMatchConfig::new().with_limit(query.limit))
.matches_with(metric, &QuickMatchConfig::new().with_limit(*limit))
}
fn matcher(&self) -> &QuickMatch<'_> {