server: use etag for vecs instead of date modified
@@ -1,15 +1,17 @@
|
||||
<!--
|
||||
# v0.X.Y | WIP
|
||||

|
||||

|
||||
-->
|
||||
|
||||
# v0.X.0 | WIP | A new beginning
|
||||
|
||||

|
||||
|
||||
Full rewrite
|
||||
|
||||
# [kibo-v0.5.0](https://github.com/kibo-money/kibo/tree/eea56d394bf92c62c81da8b78b8c47ea730683f5) | [873199](https://mempool.space/block/0000000000000000000270925aa6a565be92e13164565a3f7994ca1966e48050) - 2024/12/04
|
||||
# [kibo-v0.5.0](https://github.com/bitcoinresearchkit/brk/tree/eea56d394bf92c62c81da8b78b8c47ea730683f5) | [873199](https://mempool.space/block/0000000000000000000270925aa6a565be92e13164565a3f7994ca1966e48050) - 2024/12/04
|
||||
|
||||

|
||||

|
||||
|
||||
## Datasets
|
||||
|
||||
@@ -74,9 +76,9 @@ Full rewrite
|
||||
|
||||
- Moved back to this repo
|
||||
|
||||
# [kibo-v0.4.0](https://github.com/kibo-money/kibo/tree/a64c544815d9ef785e2fc1323582f774f16b9200) | [861950](https://mempool.space/block/00000000000000000000530d0e30ccf7deeace122dcc99f2668a06c6dad83629) - 2024/09/19
|
||||
# [kibo-v0.4.0](https://github.com/bitcoinresearchkit/brk/tree/a64c544815d9ef785e2fc1323582f774f16b9200) | [861950](https://mempool.space/block/00000000000000000000530d0e30ccf7deeace122dcc99f2668a06c6dad83629) - 2024/09/19
|
||||
|
||||

|
||||

|
||||
|
||||
## Brand
|
||||
|
||||
@@ -111,9 +113,9 @@ Full rewrite
|
||||
- Added serving of the website
|
||||
- Improved `Cache-Control` behavior
|
||||
|
||||
# [kibo-v0.3.0](https://github.com/kibo-money/kibo/tree/b68b016091c45b071218fba01bac5b76e8eaf18c) | [853930](https://mempool.space/block/00000000000000000002eb5e9a7950ca2d5d98bd1ed28fc9098aa630d417985d) - 2024/07/26
|
||||
# [kibo-v0.3.0](https://github.com/bitcoinresearchkit/brk/tree/b68b016091c45b071218fba01bac5b76e8eaf18c) | [853930](https://mempool.space/block/00000000000000000002eb5e9a7950ca2d5d98bd1ed28fc9098aa630d417985d) - 2024/07/26
|
||||
|
||||

|
||||

|
||||
|
||||
## Parser
|
||||
|
||||
@@ -190,9 +192,9 @@ Full rewrite
|
||||
- Only run with a watcher if `cargo watch` is available
|
||||
- Removed id_to_path file in favor for only `paths.d.ts` in `app/src/types`
|
||||
|
||||
# [kibo-v0.2.0](https://github.com/kibo-money/kibo/tree/248187889283597c5dbb806292297453c25e97b8) | [851286](https://mempool.space/block/0000000000000000000281ca7f1bf8c50702bfca168c7af1bdc67c977c1ac8ed) - 2024/07/08
|
||||
# [kibo-v0.2.0](https://github.com/bitcoinresearchkit/brk/tree/248187889283597c5dbb806292297453c25e97b8) | [851286](https://mempool.space/block/0000000000000000000281ca7f1bf8c50702bfca168c7af1bdc67c977c1ac8ed) - 2024/07/08
|
||||
|
||||

|
||||

|
||||
|
||||
## App
|
||||
|
||||
@@ -226,9 +228,9 @@ Full rewrite
|
||||
|
||||
- Fixed ulimit only being run in Mac OS instead of whenever the program is detected
|
||||
|
||||
# [kibo-v0.1.1](https://github.com/kibo-money/kibo/tree/e55b5195a9de9aea306903c94ed63cb1720fda5f) | [849240](https://mempool.space/block/000000000000000000002b8653988655071c07bb5f7181c038f9326bc86db741) - 2024/06/24
|
||||
# [kibo-v0.1.1](https://github.com/bitcoinresearchkit/brk/tree/e55b5195a9de9aea306903c94ed63cb1720fda5f) | [849240](https://mempool.space/block/000000000000000000002b8653988655071c07bb5f7181c038f9326bc86db741) - 2024/06/24
|
||||
|
||||

|
||||

|
||||
|
||||
## Parser
|
||||
|
||||
@@ -276,10 +278,10 @@ Full rewrite
|
||||
|
||||
- Deleted old price datasets and their backups
|
||||
|
||||
# [kibo-v0.1.0](https://github.com/kibo-money/kibo/tree/a1a576d088c8f83ed32d48753a7611f70a964574) | [848642](https://mempool.space/block/000000000000000000020be5761d70751252219a9557f55e91ecdfb86c4e026a) - 2024/06/19
|
||||
# [kibo-v0.1.0](https://github.com/bitcoinresearchkit/brk/tree/a1a576d088c8f83ed32d48753a7611f70a964574) | [848642](https://mempool.space/block/000000000000000000020be5761d70751252219a9557f55e91ecdfb86c4e026a) - 2024/06/19
|
||||
|
||||

|
||||

|
||||
|
||||
# kibo-v0.0.1 | [835444](https://mempool.space/block/000000000000000000009f93907a0dd83c080d5585cc7ec82c076d45f6d7c872) - 2024/03/20
|
||||
|
||||

|
||||

|
||||
|
||||
@@ -454,6 +454,7 @@ dependencies = [
|
||||
"brk_indexer",
|
||||
"brk_interface",
|
||||
"brk_logger",
|
||||
"brk_mcp",
|
||||
"brk_parser",
|
||||
"brk_server",
|
||||
"brk_state",
|
||||
@@ -482,7 +483,6 @@ dependencies = [
|
||||
"brk_exit",
|
||||
"brk_fetcher",
|
||||
"brk_indexer",
|
||||
"brk_interface",
|
||||
"brk_logger",
|
||||
"brk_parser",
|
||||
"brk_server",
|
||||
@@ -492,7 +492,6 @@ dependencies = [
|
||||
"color-eyre",
|
||||
"log",
|
||||
"serde",
|
||||
"tabled",
|
||||
"tokio",
|
||||
"toml",
|
||||
]
|
||||
@@ -606,6 +605,17 @@ dependencies = [
|
||||
"log",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "brk_mcp"
|
||||
version = "0.0.66"
|
||||
dependencies = [
|
||||
"axum",
|
||||
"brk_interface",
|
||||
"brk_rmcp",
|
||||
"log",
|
||||
"tracing",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "brk_parser"
|
||||
version = "0.0.66"
|
||||
@@ -982,8 +992,8 @@ dependencies = [
|
||||
"brk_indexer",
|
||||
"brk_interface",
|
||||
"brk_logger",
|
||||
"brk_mcp",
|
||||
"brk_parser",
|
||||
"brk_rmcp",
|
||||
"brk_vec",
|
||||
"clap",
|
||||
"clap_derive",
|
||||
@@ -1014,7 +1024,6 @@ dependencies = [
|
||||
name = "brk_store"
|
||||
version = "0.0.66"
|
||||
dependencies = [
|
||||
"arc-swap",
|
||||
"brk_core",
|
||||
"byteview",
|
||||
"fjall",
|
||||
@@ -2530,9 +2539,9 @@ checksum = "b15813163c1d831bf4a13c3610c05c0d03b39feb07f7e09fa234dac9b15aaf39"
|
||||
|
||||
[[package]]
|
||||
name = "owo-colors"
|
||||
version = "4.2.1"
|
||||
version = "4.2.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "26995317201fa17f3656c36716aed4a7c81743a9634ac4c99c0eeda495db0cec"
|
||||
checksum = "48dd4f4a2c8405440fd0462561f0e5806bd0f77e86f51c761481bdd4018b545e"
|
||||
|
||||
[[package]]
|
||||
name = "oxc"
|
||||
|
||||
@@ -31,6 +31,7 @@ brk_fetcher = { version = "0.0.66", path = "crates/brk_fetcher" }
|
||||
brk_indexer = { version = "0.0.66", path = "crates/brk_indexer" }
|
||||
brk_interface = { version = "0.0.66", path = "crates/brk_interface" }
|
||||
brk_logger = { version = "0.0.66", path = "crates/brk_logger" }
|
||||
brk_mcp = { version = "0.0.66", path = "crates/brk_mcp" }
|
||||
brk_parser = { version = "0.0.66", path = "crates/brk_parser" }
|
||||
brk_rmcp = { version = "0.1.7", features = ["transport-streamable-http-server", "transport-worker"]}
|
||||
brk_server = { version = "0.0.66", path = "crates/brk_server" }
|
||||
|
||||
@@ -68,7 +68,8 @@ In contrast, existing alternatives tend to be either [very costly](https://studi
|
||||
- [`brk_exit`](https://crates.io/crates/brk_exit): An exit blocker built on top of ctrlc
|
||||
- [`brk_fetcher`](https://crates.io/crates/brk_fetcher): A Bitcoin price fetcher
|
||||
- [`brk_indexer`](https://crates.io/crates/brk_indexer): A Bitcoin Core indexer built on top of brk_parser
|
||||
- [`brk_logger`](https://crates.io/crates/brk_logger): A clean logger used in the Bitcoin Research Kit.
|
||||
- [`brk_logger`](https://crates.io/crates/brk_logger): A clean logger used in the Bitcoin Research Kit
|
||||
- [`brk_mcp`](https://crates.io/crates/brk_mcp): A Model Context Protocol (MCP) which gives LLMs access to all available tools in BRK
|
||||
- [`brk_parser`](https://crates.io/crates/brk_parser): A very fast Bitcoin Core block parser and iterator built on top of bitcoin-rust
|
||||
- [`brk_interface`](https://crates.io/crates/brk_interface): An interface to BRK's engine
|
||||
- [`brk_server`](https://crates.io/crates/brk_server): A server that serves Bitcoin data and swappable front-ends, built on top of `brk_indexer`, `brk_fetcher` and `brk_computer`
|
||||
|
||||
|
After Width: | Height: | Size: 340 KiB |
|
After Width: | Height: | Size: 208 KiB |
|
After Width: | Height: | Size: 386 KiB |
|
After Width: | Height: | Size: 496 KiB |
|
After Width: | Height: | Size: 564 KiB |
|
After Width: | Height: | Size: 592 KiB |
|
After Width: | Height: | Size: 453 KiB |
|
After Width: | Height: | Size: 526 KiB |
@@ -17,6 +17,7 @@ full = [
|
||||
"fetcher",
|
||||
"indexer",
|
||||
"logger",
|
||||
"mcp",
|
||||
"parser",
|
||||
"interface",
|
||||
"server",
|
||||
@@ -31,6 +32,7 @@ exit = ["brk_exit"]
|
||||
fetcher = ["brk_fetcher"]
|
||||
indexer = ["brk_indexer"]
|
||||
logger = ["brk_logger"]
|
||||
mcp = ["brk_mcp"]
|
||||
parser = ["brk_parser"]
|
||||
interface = ["brk_interface"]
|
||||
server = ["brk_server"]
|
||||
@@ -47,6 +49,7 @@ brk_exit = { workspace = true, optional = true }
|
||||
brk_fetcher = { workspace = true, optional = true }
|
||||
brk_indexer = { workspace = true, optional = true }
|
||||
brk_logger = { workspace = true, optional = true }
|
||||
brk_mcp = { workspace = true, optional = true }
|
||||
brk_parser = { workspace = true, optional = true }
|
||||
brk_interface = { workspace = true, optional = true }
|
||||
brk_server = { workspace = true, optional = true }
|
||||
|
||||
@@ -31,6 +31,10 @@ pub use brk_indexer as indexer;
|
||||
#[doc(inline)]
|
||||
pub use brk_logger as logger;
|
||||
|
||||
#[cfg(feature = "mcp")]
|
||||
#[doc(inline)]
|
||||
pub use brk_mcp as mcp;
|
||||
|
||||
#[cfg(feature = "parser")]
|
||||
#[doc(inline)]
|
||||
pub use brk_parser as parser;
|
||||
|
||||
@@ -16,7 +16,6 @@ brk_fetcher = { workspace = true }
|
||||
brk_indexer = { workspace = true }
|
||||
brk_logger = { workspace = true }
|
||||
brk_parser = { workspace = true }
|
||||
brk_interface = { workspace = true }
|
||||
brk_server = { workspace = true }
|
||||
brk_vec = { workspace = true }
|
||||
clap = { workspace = true }
|
||||
@@ -24,7 +23,6 @@ clap_derive = { workspace = true }
|
||||
color-eyre = { workspace = true }
|
||||
log = { workspace = true }
|
||||
serde = { workspace = true }
|
||||
tabled = { workspace = true }
|
||||
tokio = { workspace = true }
|
||||
toml = "0.8.23"
|
||||
|
||||
|
||||
@@ -61,7 +61,6 @@ pub use cents::*;
|
||||
pub use date::*;
|
||||
pub use dateindex::*;
|
||||
pub use decadeindex::*;
|
||||
pub use decadeindex::*;
|
||||
pub use difficultyepoch::*;
|
||||
pub use dollars::*;
|
||||
pub use emptyoutputindex::*;
|
||||
|
||||
@@ -0,0 +1,15 @@
|
||||
[package]
|
||||
name = "brk_mcp"
|
||||
description = "A Model Context Protocol (MCP) which gives LLMs access to all available tools in BRK"
|
||||
version.workspace = true
|
||||
edition.workspace = true
|
||||
license.workspace = true
|
||||
homepage.workspace = true
|
||||
repository.workspace = true
|
||||
|
||||
[dependencies]
|
||||
axum = { workspace = true }
|
||||
brk_interface = { workspace = true }
|
||||
log = { workspace = true }
|
||||
brk_rmcp = { workspace = true }
|
||||
tracing = "0.1.41"
|
||||
@@ -0,0 +1,3 @@
|
||||
# BRK MCP
|
||||
|
||||
A Model Context Protocol (MCP) which gives LLMs access to all available tools in BRK
|
||||
@@ -1,3 +1,8 @@
|
||||
#![doc = include_str!("../README.md")]
|
||||
// #![doc = "\n## Example\n\n```rust"]
|
||||
// #![doc = include_str!("../examples/main.rs")]
|
||||
// #![doc = "```"]
|
||||
|
||||
use brk_interface::{IdParam, Interface, PaginatedIndexParam, PaginationParam, Params};
|
||||
use brk_rmcp::{
|
||||
Error as McpError, RoleServer, ServerHandler,
|
||||
@@ -10,15 +15,17 @@ use brk_rmcp::{
|
||||
};
|
||||
use log::info;
|
||||
|
||||
pub mod route;
|
||||
|
||||
#[derive(Clone)]
|
||||
pub struct API {
|
||||
pub struct MCP {
|
||||
interface: &'static Interface<'static>,
|
||||
}
|
||||
|
||||
const VERSION: &str = env!("CARGO_PKG_VERSION");
|
||||
|
||||
#[tool(tool_box)]
|
||||
impl API {
|
||||
impl MCP {
|
||||
pub fn new(interface: &'static Interface<'static>) -> Self {
|
||||
Self { interface }
|
||||
}
|
||||
@@ -146,7 +153,7 @@ Get the running version of the Bitcoin Research Kit
|
||||
}
|
||||
|
||||
#[tool(tool_box)]
|
||||
impl ServerHandler for API {
|
||||
impl ServerHandler for MCP {
|
||||
fn get_info(&self) -> ServerInfo {
|
||||
ServerInfo {
|
||||
protocol_version: ProtocolVersion::LATEST,
|
||||
@@ -5,17 +5,18 @@ use brk_rmcp::transport::{
|
||||
streamable_http_server::{StreamableHttpService, session::local::LocalSessionManager},
|
||||
};
|
||||
|
||||
mod api;
|
||||
use api::*;
|
||||
use log::info;
|
||||
|
||||
use crate::AppState;
|
||||
use crate::MCP;
|
||||
|
||||
pub trait MCPRoutes {
|
||||
fn add_mcp_routes(self, interface: &'static Interface<'static>, mcp: bool) -> Self;
|
||||
}
|
||||
|
||||
impl MCPRoutes for Router<AppState> {
|
||||
impl<T> MCPRoutes for Router<T>
|
||||
where
|
||||
T: Clone + Send + Sync + 'static,
|
||||
{
|
||||
fn add_mcp_routes(self, interface: &'static Interface<'static>, mcp: bool) -> Self {
|
||||
if !mcp {
|
||||
return self;
|
||||
@@ -27,7 +28,7 @@ impl MCPRoutes for Router<AppState> {
|
||||
};
|
||||
|
||||
let service = StreamableHttpService::new(
|
||||
move || Ok(API::new(interface)),
|
||||
move || Ok(MCP::new(interface)),
|
||||
LocalSessionManager::default().into(),
|
||||
config,
|
||||
);
|
||||
@@ -1,12 +0,0 @@
|
||||
# v0.2.1
|
||||
|
||||
- Clean `.json` if necessary
|
||||
- Only save `.json` if needed
|
||||
- Updated benchmarks
|
||||
- Updated packages
|
||||
|
||||
# v0.2.0
|
||||
|
||||
- Removed the need for an output directory path
|
||||
- Changed the location of the saved json file from the previously needed output directory path to the Bitcoin data directory
|
||||
- Added a save of the json file every 144 * 30 blocks instead of only at the end
|
||||
@@ -1,21 +0,0 @@
|
||||
MIT License
|
||||
|
||||
Copyright (c) 2024 biter
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
@@ -16,9 +16,10 @@ brk_core = { workspace = true }
|
||||
brk_exit = { workspace = true }
|
||||
brk_fetcher = { workspace = true }
|
||||
brk_indexer = { workspace = true }
|
||||
brk_logger = { workspace = true }
|
||||
brk_parser = { workspace = true }
|
||||
brk_interface = { workspace = true }
|
||||
brk_logger = { workspace = true }
|
||||
brk_mcp = { workspace = true }
|
||||
brk_parser = { workspace = true }
|
||||
brk_vec = { workspace = true }
|
||||
clap = { workspace = true }
|
||||
clap_derive = { workspace = true }
|
||||
@@ -26,7 +27,6 @@ color-eyre = { workspace = true }
|
||||
jiff = { workspace = true }
|
||||
log = { workspace = true }
|
||||
minreq = { workspace = true }
|
||||
brk_rmcp = { workspace = true }
|
||||
serde = { workspace = true }
|
||||
tokio = { workspace = true }
|
||||
tower-http = { version = "0.6.6", features = ["compression-full", "trace"] }
|
||||
|
||||
@@ -9,7 +9,7 @@ use brk_interface::{Format, Output, Params};
|
||||
use brk_vec::{CollectableVec, StoredVec};
|
||||
use color_eyre::eyre::eyre;
|
||||
|
||||
use crate::traits::{HeaderMapExtended, ModifiedState, ResponseExtended};
|
||||
use crate::traits::{HeaderMapExtended, ResponseExtended};
|
||||
|
||||
use super::AppState;
|
||||
|
||||
@@ -63,24 +63,13 @@ fn req_to_response_res(
|
||||
return Err(eyre!("Request is too heavy, max weight is {MAX_WEIGHT}"));
|
||||
}
|
||||
|
||||
let mut date_modified_opt = None;
|
||||
let etag = vecs.first().unwrap().1.etag(to);
|
||||
|
||||
if to.is_none() {
|
||||
let not_modified = vecs
|
||||
.iter()
|
||||
.map(|(_, vec)| headers.check_if_modified_since_(vec.modified_time()?))
|
||||
.all(|res| {
|
||||
res.ok().is_some_and(|(modified, date_modified)| {
|
||||
if date_modified_opt.is_none_or(|dm| dm > date_modified) {
|
||||
date_modified_opt.replace(date_modified);
|
||||
}
|
||||
modified == ModifiedState::NotModifiedSince
|
||||
})
|
||||
});
|
||||
|
||||
if not_modified {
|
||||
return Ok(Response::new_not_modified());
|
||||
}
|
||||
if headers
|
||||
.get_if_none_match()
|
||||
.is_some_and(|prev_etag| etag == prev_etag)
|
||||
{
|
||||
return Ok(Response::new_not_modified());
|
||||
}
|
||||
|
||||
let output = interface.format(vecs, ¶ms.rest)?;
|
||||
@@ -100,9 +89,7 @@ fn req_to_response_res(
|
||||
|
||||
headers.insert_cors();
|
||||
|
||||
if let Some(date_modified) = date_modified_opt {
|
||||
headers.insert_last_modified(date_modified);
|
||||
}
|
||||
headers.insert_etag(&etag);
|
||||
|
||||
match format {
|
||||
Some(format) => {
|
||||
|
||||
@@ -24,6 +24,7 @@ use brk_computer::Computer;
|
||||
use brk_core::dot_brk_path;
|
||||
use brk_indexer::Indexer;
|
||||
use brk_interface::Interface;
|
||||
use brk_mcp::route::MCPRoutes;
|
||||
use color_eyre::owo_colors::OwoColorize;
|
||||
use files::FilesRoutes;
|
||||
use log::{error, info};
|
||||
@@ -32,11 +33,9 @@ use tower_http::{compression::CompressionLayer, trace::TraceLayer};
|
||||
|
||||
mod api;
|
||||
mod files;
|
||||
mod mcp;
|
||||
mod traits;
|
||||
|
||||
pub use files::Website;
|
||||
use mcp::*;
|
||||
use tracing::Span;
|
||||
|
||||
#[derive(Clone)]
|
||||
|
||||
@@ -5,7 +5,7 @@ use std::{
|
||||
|
||||
use axum::http::{
|
||||
HeaderMap,
|
||||
header::{self, IF_MODIFIED_SINCE},
|
||||
header::{self, IF_MODIFIED_SINCE, IF_NONE_MATCH},
|
||||
};
|
||||
use jiff::{Timestamp, civil::DateTime, fmt::strtime, tz::TimeZone};
|
||||
use log::info;
|
||||
@@ -21,6 +21,8 @@ pub enum ModifiedState {
|
||||
pub trait HeaderMapExtended {
|
||||
fn insert_cors(&mut self);
|
||||
|
||||
fn get_if_none_match(&self) -> Option<&str>;
|
||||
|
||||
fn get_if_modified_since(&self) -> Option<DateTime>;
|
||||
fn check_if_modified_since(&self, path: &Path)
|
||||
-> color_eyre::Result<(ModifiedState, DateTime)>;
|
||||
@@ -31,6 +33,7 @@ pub trait HeaderMapExtended {
|
||||
|
||||
fn insert_cache_control_must_revalidate(&mut self);
|
||||
fn insert_cache_control_immutable(&mut self);
|
||||
fn insert_etag(&mut self, etag: &str);
|
||||
fn insert_last_modified(&mut self, date: DateTime);
|
||||
|
||||
fn insert_content_disposition_attachment(&mut self);
|
||||
@@ -85,6 +88,10 @@ impl HeaderMapExtended for HeaderMap {
|
||||
self.insert(header::LAST_MODIFIED, formatted.parse().unwrap());
|
||||
}
|
||||
|
||||
fn insert_etag(&mut self, etag: &str) {
|
||||
self.insert(header::ETAG, etag.parse().unwrap());
|
||||
}
|
||||
|
||||
fn check_if_modified_since(
|
||||
&self,
|
||||
path: &Path,
|
||||
@@ -127,6 +134,10 @@ impl HeaderMapExtended for HeaderMap {
|
||||
None
|
||||
}
|
||||
|
||||
fn get_if_none_match(&self) -> Option<&str> {
|
||||
self.get(IF_NONE_MATCH).and_then(|v| v.to_str().ok())
|
||||
}
|
||||
|
||||
// https://developer.mozilla.org/en-US/docs/Web/HTTP/Basics_of_HTTP/MIME_types/Common_types
|
||||
fn insert_content_type(&mut self, path: &Path) {
|
||||
match path.extension().unwrap().to_str().unwrap() {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
[package]
|
||||
name = "brk_state"
|
||||
description = "Various states used mainly by the computer"
|
||||
description = "Various states used in the Bitcoin Research Kit"
|
||||
version.workspace = true
|
||||
edition.workspace = true
|
||||
license.workspace = true
|
||||
|
||||
@@ -0,0 +1,3 @@
|
||||
# BRK State
|
||||
|
||||
Various states used in the Bitcoin Research Kit
|
||||
@@ -1,3 +1,8 @@
|
||||
#![doc = include_str!("../README.md")]
|
||||
// #![doc = "\n## Example\n\n```rust"]
|
||||
// #![doc = include_str!("../examples/main.rs")]
|
||||
// #![doc = "```"]
|
||||
|
||||
mod block;
|
||||
mod cohort;
|
||||
mod outputs;
|
||||
|
||||
@@ -10,7 +10,6 @@ homepage.workspace = true
|
||||
repository.workspace = true
|
||||
|
||||
[dependencies]
|
||||
arc-swap = { workspace = true }
|
||||
brk_core = { workspace = true }
|
||||
byteview = { workspace = true }
|
||||
fjall = { workspace = true }
|
||||
|
||||
@@ -1,6 +1,4 @@
|
||||
use std::time::Duration;
|
||||
|
||||
use brk_core::{Result, Version};
|
||||
use brk_core::Version;
|
||||
|
||||
use super::{BoxedVecIterator, StoredIndex, StoredType};
|
||||
|
||||
@@ -11,9 +9,23 @@ pub trait AnyVec: Send + Sync {
|
||||
fn is_empty(&self) -> bool {
|
||||
self.len() == 0
|
||||
}
|
||||
fn modified_time(&self) -> Result<Duration>;
|
||||
fn index_type_to_string(&self) -> &'static str;
|
||||
fn value_type_to_size_of(&self) -> usize;
|
||||
fn etag(&self, to: Option<i64>) -> String {
|
||||
let len = self.len();
|
||||
format!(
|
||||
"{}-{:?}",
|
||||
to.map_or(len, |to| {
|
||||
if to.is_negative() {
|
||||
len.checked_sub(to.unsigned_abs() as usize)
|
||||
.unwrap_or_default()
|
||||
} else {
|
||||
to as usize
|
||||
}
|
||||
}),
|
||||
self.version()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
pub trait AnyIterableVec<I, T>: AnyVec {
|
||||
|
||||
@@ -3,7 +3,6 @@ use std::{
|
||||
io::{self, Seek, SeekFrom, Write},
|
||||
path::{Path, PathBuf},
|
||||
sync::Arc,
|
||||
time::{self, Duration},
|
||||
};
|
||||
|
||||
use arc_swap::ArcSwap;
|
||||
@@ -168,12 +167,4 @@ where
|
||||
fn flush(&mut self) -> Result<()>;
|
||||
|
||||
fn truncate_if_needed(&mut self, index: I) -> Result<()>;
|
||||
|
||||
fn modified_time_(&self) -> Result<Duration> {
|
||||
Ok(self
|
||||
.file()
|
||||
.metadata()?
|
||||
.modified()?
|
||||
.duration_since(time::UNIX_EPOCH)?)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,7 +3,6 @@ use std::{
|
||||
mem,
|
||||
path::{Path, PathBuf},
|
||||
sync::Arc,
|
||||
time::Duration,
|
||||
};
|
||||
|
||||
use arc_swap::{ArcSwap, Guard};
|
||||
@@ -381,11 +380,6 @@ where
|
||||
self.len_()
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn modified_time(&self) -> Result<Duration> {
|
||||
self.modified_time_()
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn index_type_to_string(&self) -> &'static str {
|
||||
I::to_string()
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
use std::{fs, path::Path, time::Duration};
|
||||
use std::{fs, path::Path};
|
||||
|
||||
use brk_exit::Exit;
|
||||
use clap_derive::ValueEnum;
|
||||
@@ -245,15 +245,6 @@ where
|
||||
}
|
||||
}
|
||||
|
||||
fn modified_time(&self) -> Result<Duration> {
|
||||
match self {
|
||||
ComputedVec::Eager { vec, .. } => vec.modified_time(),
|
||||
ComputedVec::LazyFrom1(v) => v.modified_time(),
|
||||
ComputedVec::LazyFrom2(v) => v.modified_time(),
|
||||
ComputedVec::LazyFrom3(v) => v.modified_time(),
|
||||
}
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn value_type_to_size_of(&self) -> usize {
|
||||
size_of::<T>()
|
||||
|
||||
@@ -5,7 +5,6 @@ use std::{
|
||||
fmt::Debug,
|
||||
ops::{Add, Div, Mul},
|
||||
path::{Path, PathBuf},
|
||||
time::Duration,
|
||||
};
|
||||
|
||||
use arc_swap::ArcSwap;
|
||||
@@ -1304,11 +1303,6 @@ where
|
||||
self.0.len()
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn modified_time(&self) -> Result<Duration> {
|
||||
self.0.modified_time()
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn index_type_to_string(&self) -> &'static str {
|
||||
I::to_string()
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
use std::{cmp::Ordering, fmt::Debug, path::Path, time::Duration};
|
||||
use std::{cmp::Ordering, fmt::Debug, path::Path};
|
||||
|
||||
use arc_swap::ArcSwap;
|
||||
use brk_core::{Error, Height, Result, Value, Version};
|
||||
@@ -103,11 +103,6 @@ where
|
||||
self.0.len()
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn modified_time(&self) -> Result<Duration> {
|
||||
self.0.modified_time()
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn index_type_to_string(&self) -> &'static str {
|
||||
I::to_string()
|
||||
|
||||
@@ -143,10 +143,6 @@ where
|
||||
self.source.len()
|
||||
}
|
||||
|
||||
fn modified_time(&self) -> Result<std::time::Duration> {
|
||||
self.source.modified_time()
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn value_type_to_size_of(&self) -> usize {
|
||||
size_of::<T>()
|
||||
|
||||
@@ -188,13 +188,6 @@ where
|
||||
len1.min(len2)
|
||||
}
|
||||
|
||||
fn modified_time(&self) -> Result<std::time::Duration> {
|
||||
Ok(self
|
||||
.source1
|
||||
.modified_time()?
|
||||
.min(self.source2.modified_time()?))
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn value_type_to_size_of(&self) -> usize {
|
||||
size_of::<T>()
|
||||
|
||||
@@ -222,14 +222,6 @@ where
|
||||
len1.min(len2).min(len3)
|
||||
}
|
||||
|
||||
fn modified_time(&self) -> Result<std::time::Duration> {
|
||||
Ok(self
|
||||
.source1
|
||||
.modified_time()?
|
||||
.min(self.source2.modified_time()?)
|
||||
.min(self.source3.modified_time()?))
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn value_type_to_size_of(&self) -> usize {
|
||||
size_of::<T>()
|
||||
|
||||
@@ -5,7 +5,6 @@ use std::{
|
||||
mem,
|
||||
path::{Path, PathBuf},
|
||||
sync::Arc,
|
||||
time::Duration,
|
||||
};
|
||||
|
||||
use arc_swap::{ArcSwap, Guard};
|
||||
@@ -250,11 +249,6 @@ where
|
||||
self.len_()
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn modified_time(&self) -> Result<Duration> {
|
||||
self.modified_time_()
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn index_type_to_string(&self) -> &'static str {
|
||||
I::to_string()
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
use std::{
|
||||
fs::File,
|
||||
path::{Path, PathBuf},
|
||||
time::Duration,
|
||||
};
|
||||
|
||||
use arc_swap::ArcSwap;
|
||||
@@ -191,14 +190,6 @@ where
|
||||
self.pushed_len() + self.stored_len()
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn modified_time(&self) -> Result<Duration> {
|
||||
match self {
|
||||
StoredVec::Raw(v) => v.modified_time(),
|
||||
StoredVec::Compressed(v) => v.modified_time(),
|
||||
}
|
||||
}
|
||||
|
||||
fn name(&self) -> &str {
|
||||
match self {
|
||||
StoredVec::Raw(v) => v.name(),
|
||||
|
||||
@@ -951,10 +951,7 @@ function createUtils() {
|
||||
if (unit) throw Error(`Unit "${unit}" already assigned "${id}"`);
|
||||
unit = "Years";
|
||||
}
|
||||
if (
|
||||
(!unit || thoroughUnitCheck) &&
|
||||
(id === "0" || id === "1" || id === "50" || id === "100")
|
||||
) {
|
||||
if ((!unit || thoroughUnitCheck) && id.startsWith("constant")) {
|
||||
if (unit) throw Error(`Unit "${unit}" already assigned "${id}"`);
|
||||
unit = "constant";
|
||||
}
|
||||
@@ -2226,7 +2223,6 @@ function main() {
|
||||
import("./table.js").then(({ init }) =>
|
||||
signals.runWithOwner(owner, () =>
|
||||
init({
|
||||
colors,
|
||||
elements,
|
||||
signals,
|
||||
utils,
|
||||
|
||||
@@ -3484,7 +3484,7 @@ export function initOptions({ colors, signals, env, utils, qrcode }) {
|
||||
}
|
||||
} else {
|
||||
const { input, label } = utils.dom.createLabeledInput({
|
||||
inputId: `${option.id}_${frame}${id || ""}_selector`,
|
||||
inputId: `${option.id}-${frame}${id || ""}-selector`,
|
||||
inputValue: option.id,
|
||||
inputName: `option_${frame}${id || ""}`,
|
||||
labelTitle: option.title,
|
||||
@@ -3667,7 +3667,7 @@ export function initOptions({ colors, signals, env, utils, qrcode }) {
|
||||
} else if ("url" in anyPartial) {
|
||||
option = /** @satisfies {UrlOption} */ ({
|
||||
kind: "url",
|
||||
id: `${utils.stringToId(anyPartial.name)}_url`,
|
||||
id: `${utils.stringToId(anyPartial.name)}-url`,
|
||||
name: anyPartial.name,
|
||||
path: path || [],
|
||||
title: anyPartial.name,
|
||||
@@ -3676,7 +3676,7 @@ export function initOptions({ colors, signals, env, utils, qrcode }) {
|
||||
});
|
||||
} else {
|
||||
const title = anyPartial.title || anyPartial.name;
|
||||
const id = `chart_${utils.stringToId(title)}`;
|
||||
const id = `chart-${utils.stringToId(title)}`;
|
||||
option = /** @satisfies {ChartOption} */ ({
|
||||
kind: "chart",
|
||||
id,
|
||||
|
||||
@@ -268,7 +268,7 @@ export function init({
|
||||
/** @type {Record<string, Frequency>} */
|
||||
const idToFrequency = {};
|
||||
|
||||
list.forEach((anyFreq, index) => {
|
||||
list.forEach((anyFreq) => {
|
||||
if ("list" in anyFreq) {
|
||||
anyFreq.list?.forEach((freq) => {
|
||||
idToFrequency[freq.value] = freq;
|
||||
|
||||
@@ -353,7 +353,6 @@ function createTable({
|
||||
|
||||
/**
|
||||
* @param {Object} args
|
||||
* @param {Colors} args.colors
|
||||
* @param {Signals} args.signals
|
||||
* @param {Utilities} args.utils
|
||||
* @param {Option} args.option
|
||||
@@ -362,7 +361,6 @@ function createTable({
|
||||
* @param {VecIdToIndexes} args.vecIdToIndexes
|
||||
*/
|
||||
export function init({
|
||||
colors,
|
||||
elements,
|
||||
signals,
|
||||
option,
|
||||
@@ -500,7 +498,7 @@ function createIndexToVecIds(vecIdToIndexes) {
|
||||
});
|
||||
return arr;
|
||||
},
|
||||
/** @type {VecId[][]} */ (new Array(24)),
|
||||
/** @type {VecId[][]} */ (Array.from({ length: 24 })),
|
||||
);
|
||||
indexToVecIds.forEach((arr) => {
|
||||
arr.sort();
|
||||
|
||||