diff --git a/CHANGELOG.md b/CHANGELOG.md index 86c8226c7..ac4d65945 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -12,10 +12,16 @@ ## Datasets - Added `Sell Side Risk Ratio` to all entities -- Added `Adjusted Value Created`, `Adjusted Value Destroyed` and `Adjusted Spent Output Profit Ratio` to all entities +- Added `Open`, `High` and `Low` datasets - Added `Satoshis Per Dollar` - Added `All Time High` +- Added `All Time High Date` +- Added `Days Since All Time High` +- Added `Max Days Between All Time Highs` +- Added `Max Years Between All Time Highs` - Added `Drawdown` +- Added `Adjusted Value Created`, `Adjusted Value Destroyed` and `Adjusted Spent Output Profit Ratio` to all entities +- Added `Realized Profit To Loss Ratio` to all entities - Removed datasets split by liquidity for all datasets already split by any address kind, while fun to have, they took time to compute, ram, and space to store and no one was actually checking them - Fixed a lot of values in split by liquidity datasets diff --git a/biter/Cargo.lock b/biter/Cargo.lock index bf9479ffe..e178bb13f 100644 --- a/biter/Cargo.lock +++ b/biter/Cargo.lock @@ -110,7 +110,7 @@ dependencies = [ [[package]] name = "biter" -version = "0.1.0" +version = "0.1.1" dependencies = [ "bitcoin", "bitcoincore-rpc", diff --git a/parser/Cargo.toml b/parser/Cargo.toml index 7ac138319..f4c6345f8 100644 --- a/parser/Cargo.toml +++ b/parser/Cargo.toml @@ -10,7 +10,6 @@ allocative = "0.3.3" bincode = { git = "https://github.com/bincode-org/bincode.git", features = [ "serde", ] } -# biter = "0.1.0" biter = { path = "../biter" } bitcoin_hashes = { version = "0.14.0" } chrono = { version = "0.4.38", features = ["serde"] } diff --git a/parser/src/actions/iter_blocks.rs b/parser/src/actions/iter_blocks.rs index 50c2fd3e6..3c69b2e45 100644 --- a/parser/src/actions/iter_blocks.rs +++ b/parser/src/actions/iter_blocks.rs @@ -27,12 +27,10 @@ pub fn iter_blocks( log("Starting..."); let mut datasets = AllDatasets::import()?; - // RAM: 200MB at this point log("Imported datasets"); let mut databases = Databases::import(); - // RAM: 200MB too log("Imported databases"); diff --git a/parser/src/databases/address_index_to_address_data.rs b/parser/src/databases/address_index_to_address_data.rs index f5d079b31..b89385502 100644 --- a/parser/src/databases/address_index_to_address_data.rs +++ b/parser/src/databases/address_index_to_address_data.rs @@ -23,7 +23,7 @@ type Database = _Database; pub struct AddressIndexToAddressData { pub metadata: Metadata, - map: BTreeMap, + pub map: BTreeMap, } impl Deref for AddressIndexToAddressData { @@ -99,7 +99,7 @@ impl AddressIndexToAddressData { }) } - fn open_all(&mut self) { + pub fn open_all(&mut self) { let path = Self::full_path(); fs::create_dir_all(&path).unwrap(); diff --git a/parser/src/databases/txout_index_to_amount.rs b/parser/src/databases/txout_index_to_amount.rs index 432385916..28319a4d2 100644 --- a/parser/src/databases/txout_index_to_amount.rs +++ b/parser/src/databases/txout_index_to_amount.rs @@ -19,7 +19,7 @@ type Database = _Database; pub struct TxoutIndexToAmount { pub metadata: Metadata, - pub map: BTreeMap, + map: BTreeMap, } impl Deref for TxoutIndexToAmount { diff --git a/parser/src/datasets/cointime.rs b/parser/src/datasets/cointime.rs index 11e7e2613..6224ee36e 100644 --- a/parser/src/datasets/cointime.rs +++ b/parser/src/datasets/cointime.rs @@ -186,7 +186,7 @@ impl CointimeDataset { .multi_insert_simple_transform( heights, &mut circulating_supply.height, - |circulating_supply| circulating_supply as f32, + |circulating_supply, _| circulating_supply as f32, ); self.coinblocks_created .multi_date_insert_sum_range(dates, first_height, last_height); @@ -414,7 +414,7 @@ impl CointimeDataset { .multi_insert_complex_transform( dates, &mut self.active_cap.date, - |(active_cap, date, _)| { + |(active_cap, date, _, _)| { let investor_cap = self.investor_cap.date.get(date).unwrap(); (active_cap - investor_cap) / active_cap }, diff --git a/parser/src/datasets/mod.rs b/parser/src/datasets/mod.rs index d9e461826..73e343d37 100644 --- a/parser/src/datasets/mod.rs +++ b/parser/src/datasets/mod.rs @@ -215,14 +215,14 @@ impl AllDatasets { self.address.compute( &compute_data, - &mut self.price.closes, + &mut self.price.close, &mut self.mining.cumulative_subsidy, &mut self.price.market_cap, ); self.utxo.compute( &compute_data, - &mut self.price.closes, + &mut self.price.close, &mut self.mining.cumulative_subsidy, &mut self.price.market_cap, ); @@ -255,7 +255,7 @@ impl AllDatasets { &compute_data, &mut self.date_metadata.first_height, &mut self.date_metadata.last_height, - &mut self.price.closes, + &mut self.price.close, &mut self.mining.cumulative_subsidy, &mut self.address.cohorts.all.subs.capitalization.realized_cap, &mut self.address.cohorts.all.subs.capitalization.realized_price, diff --git a/parser/src/datasets/price/mod.rs b/parser/src/datasets/price/mod.rs index 0a9817718..c3e85b9f0 100644 --- a/parser/src/datasets/price/mod.rs +++ b/parser/src/datasets/price/mod.rs @@ -32,10 +32,13 @@ pub struct PriceDatasets { kibo_by_date: BTreeMap>, // Inserted - pub ohlcs: BiMap, + pub ohlc: BiMap, // Computed - pub closes: BiMap, + pub open: BiMap, + pub high: BiMap, + pub low: BiMap, + pub close: BiMap, pub market_cap: BiMap, pub price_1w_sma: BiMap, pub price_1w_sma_ratio: RatioDataset, @@ -76,6 +79,10 @@ pub struct PriceDatasets { pub price_4y_compound_return: DateMap, // projection via lowest 4y compound value pub all_time_high: BiMap, + pub all_time_high_date: DateMap, + pub days_since_all_time_high: DateMap, + pub max_days_between_all_time_highs: DateMap, + pub max_years_between_all_time_highs: DateMap, pub market_price_to_all_time_high_ratio: BiMap, pub drawdown: BiMap, pub sats_per_dollar: BiMap, @@ -99,8 +106,11 @@ impl PriceDatasets { kibo_by_height: BTreeMap::default(), kibo_by_date: BTreeMap::default(), - ohlcs: BiMap::new_json(1, price_path), - closes: BiMap::new_bin(1, &f("close")), + ohlc: BiMap::new_json(1, price_path), + open: BiMap::new_bin(1, &f("open")), + high: BiMap::new_bin(1, &f("high")), + low: BiMap::new_bin(1, &f("low")), + close: BiMap::new_bin(1, &f("close")), market_cap: BiMap::new_bin(1, &f("market_cap")), price_1w_sma: BiMap::new_bin(1, &f("price_1w_sma")), price_1w_sma_ratio: RatioDataset::import(datasets_path, "price_1w_sma")?, @@ -140,6 +150,16 @@ impl PriceDatasets { price_10y_total_return: DateMap::new_bin(1, &f("price_10y_total_return")), price_4y_compound_return: DateMap::new_bin(1, &f("price_4y_compound_return")), all_time_high: BiMap::new_bin(1, &f("all_time_high")), + all_time_high_date: DateMap::new_bin(1, &f("all_time_high_date")), + days_since_all_time_high: DateMap::new_bin(1, &f("days_since_all_time_high")), + max_days_between_all_time_highs: DateMap::new_bin( + 1, + &f("max_days_between_all_time_highs"), + ), + max_years_between_all_time_highs: DateMap::new_bin( + 2, + &f("max_years_between_all_time_highs"), + ), market_price_to_all_time_high_ratio: BiMap::new_bin( 1, &f("market_price_to_all_time_high_ratio"), @@ -157,128 +177,137 @@ impl PriceDatasets { pub fn compute(&mut self, compute_data: &ComputeData, circulating_supply: &mut BiMap) { let &ComputeData { dates, heights, .. } = compute_data; - self.closes - .multi_insert_simple_transform(heights, dates, &mut self.ohlcs, &|ohlc| ohlc.close); + self.open + .multi_insert_simple_transform(heights, dates, &mut self.ohlc, &|ohlc| ohlc.open); + + self.high + .multi_insert_simple_transform(heights, dates, &mut self.ohlc, &|ohlc| ohlc.high); + + self.low + .multi_insert_simple_transform(heights, dates, &mut self.ohlc, &|ohlc| ohlc.low); + + self.close + .multi_insert_simple_transform(heights, dates, &mut self.ohlc, &|ohlc| ohlc.close); self.market_cap - .multi_insert_multiply(heights, dates, &mut self.closes, circulating_supply); + .multi_insert_multiply(heights, dates, &mut self.close, circulating_supply); self.price_1w_sma.multi_insert_simple_average( heights, dates, - &mut self.closes, + &mut self.close, ONE_WEEK_IN_DAYS, ); self.price_1m_sma.multi_insert_simple_average( heights, dates, - &mut self.closes, + &mut self.close, ONE_MONTH_IN_DAYS, ); self.price_1y_sma.multi_insert_simple_average( heights, dates, - &mut self.closes, + &mut self.close, ONE_YEAR_IN_DAYS, ); self.price_2y_sma.multi_insert_simple_average( heights, dates, - &mut self.closes, + &mut self.close, 2 * ONE_YEAR_IN_DAYS, ); self.price_4y_sma.multi_insert_simple_average( heights, dates, - &mut self.closes, + &mut self.close, 4 * ONE_YEAR_IN_DAYS, ); self.price_8d_sma - .multi_insert_simple_average(heights, dates, &mut self.closes, 8); + .multi_insert_simple_average(heights, dates, &mut self.close, 8); self.price_13d_sma - .multi_insert_simple_average(heights, dates, &mut self.closes, 13); + .multi_insert_simple_average(heights, dates, &mut self.close, 13); self.price_21d_sma - .multi_insert_simple_average(heights, dates, &mut self.closes, 21); + .multi_insert_simple_average(heights, dates, &mut self.close, 21); self.price_34d_sma - .multi_insert_simple_average(heights, dates, &mut self.closes, 34); + .multi_insert_simple_average(heights, dates, &mut self.close, 34); self.price_55d_sma - .multi_insert_simple_average(heights, dates, &mut self.closes, 55); + .multi_insert_simple_average(heights, dates, &mut self.close, 55); self.price_89d_sma - .multi_insert_simple_average(heights, dates, &mut self.closes, 89); + .multi_insert_simple_average(heights, dates, &mut self.close, 89); self.price_144d_sma - .multi_insert_simple_average(heights, dates, &mut self.closes, 144); + .multi_insert_simple_average(heights, dates, &mut self.close, 144); self.price_200w_sma.multi_insert_simple_average( heights, dates, - &mut self.closes, + &mut self.close, 200 * ONE_WEEK_IN_DAYS, ); self.price_1d_total_return - .multi_insert_percentage_change(dates, &mut self.closes.date, 1); + .multi_insert_percentage_change(dates, &mut self.close.date, 1); self.price_1m_total_return.multi_insert_percentage_change( dates, - &mut self.closes.date, + &mut self.close.date, ONE_MONTH_IN_DAYS, ); self.price_6m_total_return.multi_insert_percentage_change( dates, - &mut self.closes.date, + &mut self.close.date, 6 * ONE_MONTH_IN_DAYS, ); self.price_1y_total_return.multi_insert_percentage_change( dates, - &mut self.closes.date, + &mut self.close.date, ONE_YEAR_IN_DAYS, ); self.price_2y_total_return.multi_insert_percentage_change( dates, - &mut self.closes.date, + &mut self.close.date, 2 * ONE_YEAR_IN_DAYS, ); self.price_3y_total_return.multi_insert_percentage_change( dates, - &mut self.closes.date, + &mut self.close.date, 3 * ONE_YEAR_IN_DAYS, ); self.price_4y_total_return.multi_insert_percentage_change( dates, - &mut self.closes.date, + &mut self.close.date, 4 * ONE_YEAR_IN_DAYS, ); self.price_6y_total_return.multi_insert_percentage_change( dates, - &mut self.closes.date, + &mut self.close.date, 6 * ONE_YEAR_IN_DAYS, ); self.price_8y_total_return.multi_insert_percentage_change( dates, - &mut self.closes.date, + &mut self.close.date, 8 * ONE_YEAR_IN_DAYS, ); self.price_10y_total_return.multi_insert_percentage_change( dates, - &mut self.closes.date, + &mut self.close.date, 10 * ONE_YEAR_IN_DAYS, ); self.price_4y_compound_return .multi_insert_complex_transform( dates, - &mut self.closes.date, - |(last_value, date, closes)| { + &mut self.close.date, + |(last_value, date, closes, _)| { let previous_value = date .checked_sub_days(Days::new(4 * ONE_YEAR_IN_DAYS as u64)) .and_then(|date| closes.get_or_import(&Date::wrap(date))) @@ -289,37 +318,69 @@ impl PriceDatasets { ); self.price_1w_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_1w_sma); + .compute(compute_data, &mut self.close, &mut self.price_1w_sma); self.price_1m_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_1m_sma); + .compute(compute_data, &mut self.close, &mut self.price_1m_sma); self.price_1y_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_1y_sma); + .compute(compute_data, &mut self.close, &mut self.price_1y_sma); self.price_2y_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_2y_sma); + .compute(compute_data, &mut self.close, &mut self.price_2y_sma); self.price_4y_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_4y_sma); + .compute(compute_data, &mut self.close, &mut self.price_4y_sma); self.price_8d_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_8d_sma); + .compute(compute_data, &mut self.close, &mut self.price_8d_sma); self.price_13d_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_13d_sma); + .compute(compute_data, &mut self.close, &mut self.price_13d_sma); self.price_21d_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_21d_sma); + .compute(compute_data, &mut self.close, &mut self.price_21d_sma); self.price_34d_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_34d_sma); + .compute(compute_data, &mut self.close, &mut self.price_34d_sma); self.price_55d_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_55d_sma); + .compute(compute_data, &mut self.close, &mut self.price_55d_sma); self.price_89d_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_89d_sma); + .compute(compute_data, &mut self.close, &mut self.price_89d_sma); self.price_144d_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_144d_sma); + .compute(compute_data, &mut self.close, &mut self.price_144d_sma); self.price_200w_sma_ratio - .compute(compute_data, &mut self.closes, &mut self.price_200w_sma); + .compute(compute_data, &mut self.close, &mut self.price_200w_sma); self.all_time_high - .multi_insert_max(heights, dates, &mut self.closes); + .multi_insert_max(heights, dates, &mut self.high); self.market_price_to_all_time_high_ratio - .multi_insert_percentage(heights, dates, &mut self.closes, &mut self.all_time_high); + .multi_insert_percentage(heights, dates, &mut self.close, &mut self.all_time_high); + + self.all_time_high_date.multi_insert_complex_transform( + dates, + &mut self.all_time_high.date, + |(value, date, _, map)| { + let high = self.high.date.get(date).unwrap(); + let is_ath = high == value; + + if is_ath { + *date + } else { + let previous_date = date.checked_sub(1).unwrap(); + *map.get(&previous_date).as_ref().unwrap_or(date) + } + }, + ); + + self.days_since_all_time_high.multi_insert_simple_transform( + dates, + &mut self.all_time_high_date, + |value, key| key.difference_in_days_between(value), + ); + + self.max_days_between_all_time_highs + .multi_insert_max(dates, &mut self.days_since_all_time_high); + + self.max_years_between_all_time_highs + .multi_insert_simple_transform( + dates, + &mut self.max_days_between_all_time_highs, + |days, _| (days as f64 / ONE_YEAR_IN_DAYS as f64) as f32, + ); self.drawdown.multi_insert_simple_transform( heights, @@ -331,21 +392,21 @@ impl PriceDatasets { self.sats_per_dollar.multi_insert_simple_transform( heights, dates, - &mut self.closes, + &mut self.close, &|price| Amount::ONE_BTC_F32 / price, ); } pub fn get_date_ohlc(&mut self, date: Date) -> color_eyre::Result { - if self.ohlcs.date.is_key_safe(date) { - Ok(self.ohlcs.date.get(&date).unwrap().to_owned()) + if self.ohlc.date.is_key_safe(date) { + Ok(self.ohlc.date.get(&date).unwrap().to_owned()) } else { let ohlc = self .get_from_daily_kraken(&date) .or_else(|_| self.get_from_daily_binance(&date)) .or_else(|_| self.get_from_date_kibo(&date))?; - self.ohlcs.date.insert(date, ohlc); + self.ohlc.date.insert(date, ohlc); Ok(ohlc) } @@ -427,7 +488,7 @@ impl PriceDatasets { timestamp: Timestamp, previous_timestamp: Option, ) -> color_eyre::Result { - if let Some(ohlc) = self.ohlcs.height.get(&height) { + if let Some(ohlc) = self.ohlc.height.get(&height) { return Ok(ohlc); } @@ -469,7 +530,7 @@ How to fix this: }) }); - self.ohlcs.height.insert(height, ohlc); + self.ohlc.height.insert(height, ohlc); Ok(ohlc) } @@ -617,16 +678,19 @@ impl AnyDataset for PriceDatasets { } fn to_inserted_bi_map_vec(&self) -> Vec<&(dyn AnyBiMap + Send + Sync)> { - vec![&self.ohlcs] + vec![&self.ohlc] } fn to_inserted_mut_bi_map_vec(&mut self) -> Vec<&mut dyn AnyBiMap> { - vec![&mut self.ohlcs] + vec![&mut self.ohlc] } fn to_computed_bi_map_vec(&self) -> Vec<&(dyn AnyBiMap + Send + Sync)> { let mut v = vec![ - &self.closes as &(dyn AnyBiMap + Send + Sync), + &self.open as &(dyn AnyBiMap + Send + Sync), + &self.high, + &self.low, + &self.close, &self.market_cap, &self.price_1w_sma, &self.price_1m_sma, @@ -666,7 +730,10 @@ impl AnyDataset for PriceDatasets { fn to_computed_mut_bi_map_vec(&mut self) -> Vec<&mut dyn AnyBiMap> { let mut v = vec![ - &mut self.closes as &mut dyn AnyBiMap, + &mut self.open as &mut dyn AnyBiMap, + &mut self.high, + &mut self.low, + &mut self.close, &mut self.market_cap, &mut self.price_1w_sma, &mut self.price_1m_sma, @@ -717,6 +784,10 @@ impl AnyDataset for PriceDatasets { &self.price_8y_total_return, &self.price_10y_total_return, &self.price_4y_compound_return, + &self.all_time_high_date, + &self.days_since_all_time_high, + &self.max_days_between_all_time_highs, + &self.max_years_between_all_time_highs, ] } @@ -733,6 +804,10 @@ impl AnyDataset for PriceDatasets { &mut self.price_8y_total_return, &mut self.price_10y_total_return, &mut self.price_4y_compound_return, + &mut self.all_time_high_date, + &mut self.days_since_all_time_high, + &mut self.max_days_between_all_time_highs, + &mut self.max_years_between_all_time_highs, ] } } diff --git a/parser/src/datasets/subs/ratio.rs b/parser/src/datasets/subs/ratio.rs index e2b6e55c0..cce412307 100644 --- a/parser/src/datasets/subs/ratio.rs +++ b/parser/src/datasets/subs/ratio.rs @@ -122,7 +122,7 @@ impl RatioDataset { self.ratio_1y_sma_momentum_oscillator .date - .multi_insert_complex_transform(dates, &mut self.ratio.date, |(ratio, date, _)| { + .multi_insert_complex_transform(dates, &mut self.ratio.date, |(ratio, date, _, _)| { (ratio / self.ratio_1y_sma.date.get_or_import(date).unwrap()) - 1.0 }); diff --git a/parser/src/datasets/subs/realized.rs b/parser/src/datasets/subs/realized.rs index a0d93c4d7..3882457e1 100644 --- a/parser/src/datasets/subs/realized.rs +++ b/parser/src/datasets/subs/realized.rs @@ -32,6 +32,7 @@ pub struct RealizedSubDataset { cumulative_net_realized_profit_and_loss_1m_net_change: BiMap, realized_value: BiMap, sell_side_risk_ratio: DateMap, + realized_profit_to_loss_ratio: BiMap, } impl RealizedSubDataset { @@ -77,6 +78,7 @@ impl RealizedSubDataset { ), realized_value: BiMap::new_bin(1, &f("realized_value")), sell_side_risk_ratio: DateMap::new_bin(1, &f("sell_side_risk_ratio")), + realized_profit_to_loss_ratio: BiMap::new_bin(1, &f("realized_profit_to_loss_ratio")), }; s.min_initial_states @@ -243,6 +245,13 @@ impl RealizedSubDataset { &mut self.realized_value.date, &mut market_cap.date, ); + + self.realized_profit_to_loss_ratio.multi_insert_divide( + heights, + dates, + &mut self.realized_profit, + &mut self.realized_loss, + ); } } @@ -287,6 +296,7 @@ impl AnyDataset for RealizedSubDataset { &self.cumulative_net_realized_profit_and_loss, &self.cumulative_net_realized_profit_and_loss_1m_net_change, &self.realized_value, + &self.realized_profit_to_loss_ratio, ] } @@ -304,6 +314,7 @@ impl AnyDataset for RealizedSubDataset { &mut self.cumulative_net_realized_profit_and_loss, &mut self.cumulative_net_realized_profit_and_loss_1m_net_change, &mut self.realized_value, + &mut self.realized_profit_to_loss_ratio, ] } diff --git a/parser/src/datasets/transaction.rs b/parser/src/datasets/transaction.rs index 63ab80a43..3fac5c963 100644 --- a/parser/src/datasets/transaction.rs +++ b/parser/src/datasets/transaction.rs @@ -182,7 +182,7 @@ impl TransactionDataset { self.transactions_per_second .date - .multi_insert_simple_transform(dates, &mut self.count.date, |count| { + .multi_insert_simple_transform(dates, &mut self.count.date, |count, _| { count as f32 / ONE_DAY_IN_S as f32 }); diff --git a/parser/src/structs/bi_map.rs b/parser/src/structs/bi_map.rs index b0f095a68..11969869c 100644 --- a/parser/src/structs/bi_map.rs +++ b/parser/src/structs/bi_map.rs @@ -67,21 +67,21 @@ where self.date.multi_insert_const(dates, constant); } - pub fn multi_insert_simple_transform( + pub fn multi_insert_simple_transform( &mut self, heights: &[Height], dates: &[Date], - source: &mut BiMap, + source: &mut BiMap, transform: &F, ) where Value: Div, - F: Fn(K) -> Value, - K: MapValue, + F: Fn(V) -> Value, + V: MapValue, { self.height - .multi_insert_simple_transform(heights, &mut source.height, transform); + .multi_insert_simple_transform(heights, &mut source.height, |v, _| transform(v)); self.date - .multi_insert_simple_transform(dates, &mut source.date, transform); + .multi_insert_simple_transform(dates, &mut source.date, |v, _| transform(v)); } #[allow(unused)] diff --git a/parser/src/structs/date.rs b/parser/src/structs/date.rs index 1cbb67321..358135deb 100644 --- a/parser/src/structs/date.rs +++ b/parser/src/structs/date.rs @@ -45,6 +45,10 @@ impl Date { pub fn yesterday() -> Self { Self(Self::today().checked_sub_days(Days::new(1)).unwrap()) } + + pub fn difference_in_days_between(&self, older: Self) -> u32 { + (**self - *older).num_days() as u32 + } } impl MapKey for Date { diff --git a/parser/src/structs/date_map_chunk_id.rs b/parser/src/structs/date_map_chunk_id.rs index 4fe77d300..ca3fdac32 100644 --- a/parser/src/structs/date_map_chunk_id.rs +++ b/parser/src/structs/date_map_chunk_id.rs @@ -21,8 +21,8 @@ impl MapChunkId for DateMapChunkId { self.0.to_string() } - fn from_path(path: &Path) -> Self { - Self( + fn from_path(path: &Path) -> color_eyre::Result { + Ok(Self( path.file_name() .unwrap() .to_str() @@ -30,9 +30,8 @@ impl MapChunkId for DateMapChunkId { .split(".") .next() .unwrap() - .parse::() - .unwrap(), - ) + .parse::()?, + )) } fn to_usize(self) -> usize { diff --git a/parser/src/structs/generic_map.rs b/parser/src/structs/generic_map.rs index 8539783cb..a53324880 100644 --- a/parser/src/structs/generic_map.rs +++ b/parser/src/structs/generic_map.rs @@ -63,7 +63,7 @@ where Self: Ord + Debug + Copy + Clone, { fn to_name(&self) -> String; - fn from_path(path: &Path) -> Self; + fn from_path(path: &Path) -> color_eyre::Result; fn to_usize(self) -> usize; fn from_usize(id: usize) -> Self; } @@ -189,9 +189,12 @@ where .unwrap() .map(|entry| entry.unwrap().path()) .filter(|path| serialization.is_serializable(path)) - .map(|path| { - let chunk_id = ChunkId::from_path(&path); - (chunk_id, path) + .flat_map(|path| { + if let Ok(chunk_id) = ChunkId::from_path(&path) { + Some((chunk_id, path)) + } else { + None + } }) .collect() } @@ -414,10 +417,10 @@ where ) where SourceValue: MapValue, SourceSerialized: MapSerialized, - F: Fn(SourceValue) -> Value, + F: Fn(SourceValue, &Key) -> Value, { keys.iter().for_each(|key| { - self.insert(*key, transform(source.get_or_import(key).unwrap())); + self.insert(*key, transform(source.get_or_import(key).unwrap(), key)); }); } @@ -434,13 +437,14 @@ where SourceValue, &Key, &mut GenericMap, + &Self, ), ) -> Value, { keys.iter().for_each(|key| { self.insert( *key, - transform((source.get_or_import(key).unwrap(), key, source)), + transform((source.get_or_import(key).unwrap(), key, source, self)), ); }); } @@ -823,31 +827,27 @@ where where Value: Default + PartialOrd, { - let mut max = None; + let mut previous_max = None; keys.iter().for_each(|key| { - let previous_max = max.unwrap_or_else(|| { + if previous_max.is_none() { key.checked_sub(1) .and_then(|previous_max_key| self.get(&previous_max_key)) - .unwrap_or_default() - }); + .and_then(|v| previous_max.replace(v)); + } let last_value = source.get_or_import(key).unwrap_or_else(|| { dbg!(key); panic!() }); - if max.is_none() || last_value > previous_max { - max.replace(last_value); + if previous_max.is_none() + || previous_max.is_some_and(|previous_max| previous_max < last_value) + { + previous_max.replace(last_value); } - self.insert( - *key, - max.unwrap_or_else(|| { - dbg!(previous_max, last_value, max); - panic!(); - }), - ); + self.insert(*key, previous_max.unwrap()); }); } } diff --git a/parser/src/structs/height_map_chunk_id.rs b/parser/src/structs/height_map_chunk_id.rs index 37d34bc36..6f662529d 100644 --- a/parser/src/structs/height_map_chunk_id.rs +++ b/parser/src/structs/height_map_chunk_id.rs @@ -28,8 +28,8 @@ impl MapChunkId for HeightMapChunkId { format!("{start}..{end}") } - fn from_path(path: &Path) -> Self { - Self(Height::new( + fn from_path(path: &Path) -> color_eyre::Result { + Ok(Self(Height::new( path.file_name() .unwrap() .to_str() @@ -37,12 +37,8 @@ impl MapChunkId for HeightMapChunkId { .split("..") .next() .unwrap() - .parse::() - .unwrap_or_else(|_| { - dbg!(path); - panic!() - }), - )) + .parse::()?, + ))) } fn to_usize(self) -> usize { diff --git a/website/index.html b/website/index.html index df280c839..3826e9e87 100644 --- a/website/index.html +++ b/website/index.html @@ -15,11 +15,12 @@ + + + + + + + + +