mirror of
https://github.com/lov3b/ecb-rates.git
synced 2025-02-22 18:00:11 +01:00
Simplify down to show-days
This commit is contained in:
parent
f501569040
commit
c381ed2a79
4
src/cache/cache.rs
vendored
4
src/cache/cache.rs
vendored
@ -3,8 +3,8 @@ use std::io::{BufReader, BufWriter};
|
|||||||
use std::path::{Path, PathBuf};
|
use std::path::{Path, PathBuf};
|
||||||
|
|
||||||
use super::CacheLine;
|
use super::CacheLine;
|
||||||
use crate::cli::View;
|
|
||||||
use crate::os::Os;
|
use crate::os::Os;
|
||||||
|
use crate::View;
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct Cache {
|
pub struct Cache {
|
||||||
@ -13,7 +13,7 @@ pub struct Cache {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl Cache {
|
impl Cache {
|
||||||
pub fn load(view: View) -> Option<Self> {
|
pub fn load(view: &View) -> Option<Self> {
|
||||||
let config_opt = Os::get_current()?.get_config_path();
|
let config_opt = Os::get_current()?.get_config_path();
|
||||||
let mut config_path = match config_opt {
|
let mut config_path = match config_opt {
|
||||||
Ok(k) => k,
|
Ok(k) => k,
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
use clap::{arg, Parser, ValueEnum};
|
use clap::{arg, Parser, ValueEnum};
|
||||||
|
|
||||||
use crate::ecb_url;
|
use super::{ShowDays, SortBy};
|
||||||
|
|
||||||
#[derive(Debug, Parser)]
|
#[derive(Debug, Parser)]
|
||||||
#[command(author, version, about)]
|
#[command(author, version, about)]
|
||||||
@ -30,7 +30,7 @@ pub struct Cli {
|
|||||||
pub force_color: bool,
|
pub force_color: bool,
|
||||||
|
|
||||||
/// Sort by the currency name (in alphabetical order), or by the rate value (low -> high)
|
/// Sort by the currency name (in alphabetical order), or by the rate value (low -> high)
|
||||||
#[arg(value_enum, long = "sort-by", short = 's', default_value_t = SortBy::Currency)]
|
#[arg(value_enum, long = "sort-by", default_value_t = SortBy::Currency)]
|
||||||
pub sort_by: SortBy,
|
pub sort_by: SortBy,
|
||||||
|
|
||||||
/// Recalculate to the perspective from an included currency
|
/// Recalculate to the perspective from an included currency
|
||||||
@ -46,51 +46,8 @@ pub struct Cli {
|
|||||||
pub max_decimals: u8,
|
pub max_decimals: u8,
|
||||||
|
|
||||||
/// Amount of data
|
/// Amount of data
|
||||||
#[arg(value_enum, default_value_t = View::TODAY, long="view", short='v')]
|
#[arg(default_value_t = ShowDays::Days(1), long="show_days", short='s')]
|
||||||
pub view: View,
|
pub show_days: ShowDays,
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Debug, Clone, Copy, ValueEnum)]
|
|
||||||
pub enum SortBy {
|
|
||||||
Currency,
|
|
||||||
Rate,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Debug, Clone, Copy, ValueEnum)]
|
|
||||||
pub enum View {
|
|
||||||
#[clap(name = "last-day")]
|
|
||||||
TODAY,
|
|
||||||
#[clap(name = "last-90-days")]
|
|
||||||
HistDays90,
|
|
||||||
#[clap(name = "all-days")]
|
|
||||||
HistDaysAll,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl View {
|
|
||||||
pub fn to_ecb_url(&self) -> &'static str {
|
|
||||||
match self {
|
|
||||||
View::TODAY => ecb_url::TODAY,
|
|
||||||
View::HistDays90 => ecb_url::hist::DAYS_90,
|
|
||||||
View::HistDaysAll => ecb_url::hist::DAYS_ALL,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn get_name(&self) -> &'static str {
|
|
||||||
match self {
|
|
||||||
View::TODAY => "today",
|
|
||||||
View::HistDays90 => "last-90-days",
|
|
||||||
View::HistDaysAll => "all-days",
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl SortBy {
|
|
||||||
pub fn get_comparer(&self) -> fn(&(&str, f64), &(&str, f64)) -> std::cmp::Ordering {
|
|
||||||
match self {
|
|
||||||
Self::Currency => |a, b| a.0.cmp(&b.0),
|
|
||||||
Self::Rate => |a, b| a.1.total_cmp(&b.1),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Clone, Copy, ValueEnum)]
|
#[derive(Debug, Clone, Copy, ValueEnum)]
|
7
src/cli/mod.rs
Normal file
7
src/cli/mod.rs
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
mod cli_t;
|
||||||
|
mod since;
|
||||||
|
mod sort_by;
|
||||||
|
|
||||||
|
pub use cli_t::{Cli, FormatOption};
|
||||||
|
pub use since::ShowDays;
|
||||||
|
pub use sort_by::SortBy;
|
54
src/cli/since.rs
Normal file
54
src/cli/since.rs
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
use crate::View;
|
||||||
|
use std::{fmt, str::FromStr};
|
||||||
|
|
||||||
|
#[derive(Debug, Clone, Copy)]
|
||||||
|
pub enum ShowDays {
|
||||||
|
Days(usize),
|
||||||
|
All,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl FromStr for ShowDays {
|
||||||
|
type Err = String;
|
||||||
|
|
||||||
|
fn from_str(s: &str) -> Result<Self, Self::Err> {
|
||||||
|
if s.eq_ignore_ascii_case("all") {
|
||||||
|
return Ok(ShowDays::All);
|
||||||
|
}
|
||||||
|
s.parse::<usize>().map(ShowDays::Days).map_err(|_| {
|
||||||
|
format!(
|
||||||
|
"Invalid value for since: '{}'. Use a positive integer or 'start'.",
|
||||||
|
s
|
||||||
|
)
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
impl fmt::Display for ShowDays {
|
||||||
|
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||||
|
match self {
|
||||||
|
ShowDays::Days(days) => write!(f, "{}", days),
|
||||||
|
ShowDays::All => write!(f, "all"),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl ShowDays {
|
||||||
|
/// None represents infinity
|
||||||
|
pub fn to_option(&self) -> Option<usize> {
|
||||||
|
match self {
|
||||||
|
ShowDays::Days(d) => Some(*d),
|
||||||
|
ShowDays::All => None,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn to_view(&self) -> Option<View> {
|
||||||
|
match self {
|
||||||
|
ShowDays::Days(d) => match d {
|
||||||
|
0 => None,
|
||||||
|
1 => Some(View::TODAY),
|
||||||
|
2..=90 => Some(View::HistDays90),
|
||||||
|
91.. => Some(View::HistDaysAll),
|
||||||
|
},
|
||||||
|
ShowDays::All => Some(View::HistDaysAll),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
16
src/cli/sort_by.rs
Normal file
16
src/cli/sort_by.rs
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
use clap::ValueEnum;
|
||||||
|
|
||||||
|
#[derive(Debug, ValueEnum, Clone)]
|
||||||
|
pub enum SortBy {
|
||||||
|
Currency,
|
||||||
|
Rate,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl SortBy {
|
||||||
|
pub fn get_comparer(&self) -> fn(&(&str, f64), &(&str, f64)) -> std::cmp::Ordering {
|
||||||
|
match self {
|
||||||
|
Self::Currency => |a, b| a.0.cmp(&b.0),
|
||||||
|
Self::Rate => |a, b| a.1.total_cmp(&b.1),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -7,9 +7,11 @@ pub mod os;
|
|||||||
pub mod parsing;
|
pub mod parsing;
|
||||||
pub mod table;
|
pub mod table;
|
||||||
pub mod utils_calc;
|
pub mod utils_calc;
|
||||||
|
mod view;
|
||||||
|
|
||||||
pub use header_description::HeaderDescription;
|
pub use header_description::HeaderDescription;
|
||||||
pub use holiday::Hollidays;
|
pub use holiday::Hollidays;
|
||||||
|
pub use view::View;
|
||||||
|
|
||||||
const APP_NAME: &'static str = "ECB-rates";
|
const APP_NAME: &'static str = "ECB-rates";
|
||||||
const DEFAULT_WIDTH: usize = 20;
|
const DEFAULT_WIDTH: usize = 20;
|
||||||
|
25
src/main.rs
25
src/main.rs
@ -25,11 +25,14 @@ async fn main() -> ExitCode {
|
|||||||
|
|
||||||
let mut header_description = HeaderDescription::new();
|
let mut header_description = HeaderDescription::new();
|
||||||
let use_cache = !cli.no_cache;
|
let use_cache = !cli.no_cache;
|
||||||
let mut cache = if use_cache {
|
let view = match cli.show_days.to_view() {
|
||||||
Cache::load(cli.view)
|
Some(v) => v,
|
||||||
} else {
|
None => {
|
||||||
None
|
eprintln!("It doesn't make any sence to fetch 0 days right?");
|
||||||
|
return ExitCode::SUCCESS;
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
let mut cache = if use_cache { Cache::load(&view) } else { None };
|
||||||
let cache_ok = cache.as_ref().map_or_else(
|
let cache_ok = cache.as_ref().map_or_else(
|
||||||
|| false,
|
|| false,
|
||||||
|c| c.get_cache_line().map_or_else(|| false, |cl| cl.is_valid()),
|
|c| c.get_cache_line().map_or_else(|| false, |cl| cl.is_valid()),
|
||||||
@ -44,7 +47,7 @@ async fn main() -> ExitCode {
|
|||||||
.exchange_rate_results
|
.exchange_rate_results
|
||||||
.clone()
|
.clone()
|
||||||
} else {
|
} else {
|
||||||
let parsed = match get_and_parse(cli.view.to_ecb_url()).await {
|
let parsed = match get_and_parse(view.to_ecb_url()).await {
|
||||||
Ok(k) => k,
|
Ok(k) => k,
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
eprintln!("Failed to get/parse data from ECB: {}", e);
|
eprintln!("Failed to get/parse data from ECB: {}", e);
|
||||||
@ -102,6 +105,18 @@ async fn main() -> ExitCode {
|
|||||||
filter_currencies(&mut parsed, ¤cies);
|
filter_currencies(&mut parsed, ¤cies);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
parsed.reverse();
|
||||||
|
let parsed = match cli.show_days.to_option() {
|
||||||
|
Some(n) => {
|
||||||
|
if parsed.len() <= n {
|
||||||
|
parsed.as_slice()
|
||||||
|
} else {
|
||||||
|
&parsed[0..n]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
None => parsed.as_slice(),
|
||||||
|
};
|
||||||
|
|
||||||
let output = match cli.command {
|
let output = match cli.command {
|
||||||
FormatOption::Json => {
|
FormatOption::Json => {
|
||||||
let mut json_values = parsed
|
let mut json_values = parsed
|
||||||
|
25
src/view.rs
Normal file
25
src/view.rs
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
use crate::ecb_url;
|
||||||
|
|
||||||
|
pub enum View {
|
||||||
|
TODAY,
|
||||||
|
HistDays90,
|
||||||
|
HistDaysAll,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl View {
|
||||||
|
pub fn to_ecb_url(&self) -> &'static str {
|
||||||
|
match self {
|
||||||
|
Self::TODAY => ecb_url::TODAY,
|
||||||
|
Self::HistDays90 => ecb_url::hist::DAYS_90,
|
||||||
|
Self::HistDaysAll => ecb_url::hist::DAYS_ALL,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn get_name(&self) -> &'static str {
|
||||||
|
match self {
|
||||||
|
Self::TODAY => "today",
|
||||||
|
Self::HistDays90 => "last-90-days",
|
||||||
|
Self::HistDaysAll => "all-days",
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user