diff --git a/Cargo.toml b/Cargo.toml index 56b7c38..8857fea 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -39,3 +39,4 @@ url = { version = "2", features = [ "serde" ] } [profile.release] lto = true codegen-units = 1 +debug = 1 \ No newline at end of file diff --git a/src/cache/mem_cache.rs b/src/cache/mem_cache.rs index a5d2e9f..9f868a2 100644 --- a/src/cache/mem_cache.rs +++ b/src/cache/mem_cache.rs @@ -13,7 +13,6 @@ use tokio::sync::mpsc::{channel, Sender}; use tokio::sync::Mutex; /// Memory accelerated disk cache. Uses an LRU in memory to speed up reads. -/// pub struct MemoryLruCache { inner: Arc>, cur_mem_size: AtomicU64, diff --git a/src/main.rs b/src/main.rs index fad005e..b315bd8 100644 --- a/src/main.rs +++ b/src/main.rs @@ -3,11 +3,12 @@ #![allow(clippy::module_name_repetitions)] use std::env::{self, VarError}; +use std::hint::unreachable_unchecked; +use std::num::ParseIntError; use std::process; -use std::sync::atomic::AtomicBool; +use std::sync::atomic::{AtomicBool, Ordering}; use std::sync::Arc; use std::time::Duration; -use std::{num::ParseIntError, sync::atomic::Ordering}; use actix_web::rt::{spawn, time, System}; use actix_web::web::{self, Data}; @@ -48,7 +49,7 @@ enum ServerError { } #[actix_web::main] -async fn main() -> Result<(), std::io::Error> { +async fn main() -> Result<(), Box> { // It's ok to fail early here, it would imply we have a invalid config. dotenv::dotenv().ok(); let cli_args = CliArgs::parse(); @@ -66,10 +67,10 @@ async fn main() -> Result<(), std::io::Error> { (0, 0) => LevelFilter::Info, (_, 1) => LevelFilter::Debug, (_, n) if n > 1 => LevelFilter::Trace, - _ => unreachable!(), + _ => unsafe { unreachable_unchecked() }, }; - SimpleLogger::new().with_level(log_level).init().unwrap(); + SimpleLogger::new().with_level(log_level).init()?; print_preamble_and_warnings(); @@ -81,7 +82,7 @@ async fn main() -> Result<(), std::io::Error> { }; let client_secret_1 = client_secret.clone(); - let server = ServerState::init(&client_secret, &cli_args).await.unwrap(); + let server = ServerState::init(&client_secret, &cli_args).await?; let data_0 = Arc::new(RwLockServerState(RwLock::new(server))); let data_1 = Arc::clone(&data_0); diff --git a/src/state.rs b/src/state.rs index 399811a..b99ad4a 100644 --- a/src/state.rs +++ b/src/state.rs @@ -8,6 +8,7 @@ use parking_lot::RwLock; use rustls::sign::CertifiedKey; use rustls::ResolvesServerCert; use sodiumoxide::crypto::box_::PrecomputedKey; +use thiserror::Error; use url::Url; pub struct ServerState { @@ -21,8 +22,22 @@ pub struct ServerState { pub static PREVIOUSLY_PAUSED: AtomicBool = AtomicBool::new(false); pub static PREVIOUSLY_COMPROMISED: AtomicBool = AtomicBool::new(false); +#[derive(Error, Debug)] +pub enum ServerInitError { + #[error(transparent)] + MalformedResponse(reqwest::Error), + #[error(transparent)] + Timeout(reqwest::Error), + #[error(transparent)] + SendFailure(reqwest::Error), + #[error("Failed to parse token key")] + KeyParseError(String), + #[error("Token key was not provided in initial request")] + MissingTokenKey, +} + impl ServerState { - pub async fn init(secret: &str, config: &CliArgs) -> Result { + pub async fn init(secret: &str, config: &CliArgs) -> Result { let resp = reqwest::Client::new() .post(CONTROL_CENTER_PING_URL) .json(&Request::from((secret, config))) @@ -39,18 +54,18 @@ impl ServerState { Ok(mut resp) => { let key = resp .token_key + .ok_or(ServerInitError::MissingTokenKey) .and_then(|key| { if let Some(key) = base64::decode(&key) .ok() .and_then(|k| PrecomputedKey::from_slice(&k)) { - Some(key) + Ok(key) } else { error!("Failed to parse token key: got {}", key); - None + Err(ServerInitError::KeyParseError(key)) } - }) - .unwrap(); + })?; PREVIOUSLY_COMPROMISED.store(resp.paused, Ordering::Release); if resp.compromised { @@ -91,17 +106,17 @@ impl ServerState { } Err(e) => { warn!("Got malformed response: {}", e); - Err(()) + Err(ServerInitError::MalformedResponse(e)) } }, Err(e) => match e { e if e.is_timeout() => { error!("Response timed out to control server. Is MangaDex down?"); - Err(()) + Err(ServerInitError::Timeout(e)) } e => { warn!("Failed to send request: {}", e); - Err(()) + Err(ServerInitError::SendFailure(e)) } }, }