use std::{ hash::{DefaultHasher, Hash, Hasher}, time::Duration, }; use clap::{Parser, builder::PossibleValuesParser}; use super::sharry::{Alias, FileChecked, NewShareRequest, Uri}; #[derive(Parser, Debug, Hash)] #[command(version, about, long_about = None)] pub struct Cli { /// Timeout in seconds for HTTP actions (set 0 or invalid to disable) #[arg( short, long, default_value = "10", value_name = "SECS", value_parser = parse_seconds, )] timeout: Duration, /// Protocol for Sharry instance #[arg( short, long, default_value = "https", value_name = "VARIANT", value_parser = PossibleValuesParser::new(["http", "https"]), )] protocol: String, /// Name of the new share #[arg(short, long, default_value = "ShrUpl Upload", value_name = "TEXT")] name: String, /// Description of the new share #[arg(short, long, value_name = "TEXT")] description: Option, /// Maximum number of views for the new share #[arg(short, long, default_value_t = 100, value_name = "N")] max_views: u32, /// Chunk size for uploading, in MiB #[arg(short, long, default_value_t = 10, value_name = "N")] pub chunk_size: usize, /// Base URL for Sharry Instance url: String, /// ID of a public alias to use alias: String, /// Files to upload to the new share #[arg(value_name = "FILE", required = true, value_parser = parse_sharry_file)] pub files: Vec, } fn parse_seconds(data: &str) -> Result { data.parse().or(Ok(0)).map(Duration::from_secs) } fn parse_sharry_file(data: &str) -> Result { FileChecked::new(data).map_err(|e| e.to_string()) } impl Cli { pub fn get_timeout(&self) -> Option { (!self.timeout.is_zero()).then_some(self.timeout) } pub fn get_alias(&self) -> Alias { Alias::new(Uri::with_protocol(&self.protocol, &self.url), &self.alias) } pub fn get_share_request(&self) -> NewShareRequest { NewShareRequest::new(&self.name, self.description.as_ref(), self.max_views) } pub fn get_hash(&self) -> String { let file_refs = { let mut refs: Vec<_> = self.files.iter().collect(); refs.sort_unstable(); refs }; let mut hasher = DefaultHasher::new(); (self.get_alias(), file_refs).hash(&mut hasher); format!("{:x}", hasher.finish()) } }