Skip to content

Commit

Permalink
changed DEBUG to setting; streamlined error handling
Browse files Browse the repository at this point in the history
  • Loading branch information
9FS committed Sep 12, 2024
1 parent 8495c90 commit 3a458ec
Show file tree
Hide file tree
Showing 10 changed files with 329 additions and 452 deletions.
314 changes: 72 additions & 242 deletions Cargo.lock

Large diffs are not rendered by default.

12 changes: 6 additions & 6 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -9,18 +9,18 @@ license = "MIT"
name = "nhentai_archivist"
readme = "readme.md"
repository = "https://github.com/9-FS/nhentai_archivist"
version = "3.0.3"
version = "3.1.0"

[dependencies]
chrono = { version = "^0.4.0", features = ["serde"] }
load_config = { git = "https://github.com/9-FS/load_config", tag = "1.0.0", features = [
load_config = { git = "https://github.com/9-FS/load_config", tag = "1.1.0", features = [
"toml_file",
] }
log = "^0.4.0"
openssl = { version = "^0.10.0", features = [
"vendored",
] } # because otherwise some wild fuckywuckys during cross compilation
reqwest = { version = "^0.12.0", features = ["cookies"] }
reqwest = { version = "^0.12.0", default-features = false, features = [
"cookies",
"rustls-tls",
] }
scaler = "^1.0.0"
serde = { version = "^1.0.0", features = ["derive"] }
serde-xml-rs = "^0.6.0"
Expand Down
2 changes: 1 addition & 1 deletion docker-compose.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ version: "3"
services:
nhentai_archivist:
container_name: "nhentai_archivist"
image: "ghcr.io/9-fs/nhentai_archivist:3.0.3"
image: "ghcr.io/9-fs/nhentai_archivist:3.1.0"
environment:
HOST_OS: "Unraid"
PGID: 100
Expand Down
2 changes: 2 additions & 0 deletions src/config.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ pub struct Config
pub CF_CLEARANCE: String, // bypass bot protection
pub CSRFTOKEN: String, // bypass bot protection
pub DATABASE_URL: String, // url to database file
pub DEBUG: Option<bool>, // debug mode?
pub DOWNLOADME_FILEPATH: String, // path to file containing hentai ID to download
pub LIBRARY_PATH: String, // path to download hentai to
pub LIBRARY_SPLIT: u32, // split library into subdirectories of maximum this many hentai, 0 to disable
Expand All @@ -27,6 +28,7 @@ impl Default for Config
CF_CLEARANCE: "".to_string(),
CSRFTOKEN: "".to_string(),
DATABASE_URL: "sqlite://./db/db.sqlite".to_owned(),
DEBUG: None, // no entry in default config, defaults to false
DOWNLOADME_FILEPATH: "./config/downloadme.txt".to_owned(),
LIBRARY_PATH: "./hentai/".to_string(),
LIBRARY_SPLIT: 0,
Expand Down
125 changes: 109 additions & 16 deletions src/error.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,36 +4,129 @@
#[derive(Debug, thiserror::Error)]
pub enum Error
{
#[error("{directory_path}")]
BlockedByDirectory {directory_path: String},
#[error("Test connecting to \"{}\" failed with: {0}", .0.url().map_or_else(|| "<unknown>", |o| o.as_str()))]
Reqwest(#[from] reqwest::Error),

#[error("Creating HTTP client failed with: {source}")]
ReqwestClientBuilder {source: reqwest::Error},

#[error("Test connecting to \"{url}\" failed with status code {status}.")]
ReqwestStatus {url: String, status: reqwest::StatusCode},

#[error("Connecting to database failed with: {0}")]
Sqlx(#[from] sqlx::Error),
}

#[error("")]
Download {},

#[error("")]
#[derive(Debug, thiserror::Error)]
pub enum HentaiNewError
{
#[error
(
"Hentai has {} page types specified, but {} pages were expected.",
scaler::Formatter::new().set_scaling(scaler::Scaling::None).set_rounding(scaler::Rounding::Magnitude(0)).format(*page_types),
scaler::Formatter::new().set_scaling(scaler::Scaling::None).set_rounding(scaler::Rounding::Magnitude(0)).format(*num_pages)
)]
HentaiLengthInconsistency {page_types: u16, num_pages: u16},

#[error(transparent)]
SearchByIdError(#[from] SearchByIdError),

#[error("Loading hentai tags from database failed with: {0}")]
Sqlx(#[from] sqlx::Error),
}


#[derive(Debug, thiserror::Error)]
pub enum HentaiDownloadError
{
#[error("Saving hentai failed, because \"{directory_path}\" already is a directory.")]
BlockedByDirectory {directory_path: String}, // directory blocked

#[error("Downloading hentai failed multiple times. Giving up...")]
Download(), // download failed multiple times, more specific error messages already in download logged

#[error("Serialising hentai metadata failed with: {0}")]
SerdeXml(#[from] serde_xml_rs::Error), // serde xml error

#[error("Saving hentai failed with: {0}")]
StdIo(#[from] std::io::Error), // std io error

#[error("Saving hentai failed with: {0}")]
Zip(#[from] zip::result::ZipError), // zip error
}


#[derive(Debug, thiserror::Error)]
pub enum HentaiDownloadImageError
{
#[error("Saving hentai image failed, because \"{directory_path}\" already is a directory.")]
BlockedByDirectory {directory_path: String}, // directory blocked

#[error("Downloading hentai image from \"{}\" failed with: {0}", .0.url().map_or_else(|| "<unknown>", |o| o.as_str()))]
Reqwest(#[from] reqwest::Error),

#[error("{status}")]
#[error("Downloading hentai image from \"{url}\" failed with status code {status}.")]
ReqwestStatus {url: String, status: reqwest::StatusCode},

#[error(transparent)]
#[error("Saving hentai image at \"{filepath}\" failed with: {source}")]
StdIo {filepath: String, source: std::io::Error},
}


#[derive(Debug, thiserror::Error)]
pub enum SearchByIdError
{
#[error("Hentai metadata could not be loaded from database and downloading from \"{}\" failed with: {0}", .0.url().map_or_else(|| "<unknown>", |o| o.as_str()))]
Reqwest(#[from] reqwest::Error),

#[error("Hentai metadata could not be loaded from database and downloading from \"{url}\" failed with status code {status}.")]
ReqwestStatus {url: String, status: reqwest::StatusCode},

#[error("Hentai metadata could not be loaded from database and after downloading, deserialising API response failed with: {0}")]
SerdeJson(#[from] serde_json::Error),
}

#[error(transparent)]
SerdeXml(#[from] serde_xml_rs::Error),

#[error(transparent)]
Sqlx(#[from] sqlx::Error),
#[derive(Debug, thiserror::Error)]
pub enum SearchByTagError
{
#[error("Downloading hentai metadata page 1 from \"{}\" failed with: {0}", .0.url().map_or_else(|| "<unknown>", |o| o.as_str()))]
Reqwest(#[from] reqwest::Error),

#[error(transparent)]
StdIo(#[from] std::io::Error),
#[error("Downloading hentai metadata page 1 from \"{url}\" failed with status code {status}.")]
ReqwestStatus {url: String, status: reqwest::StatusCode},

#[error(transparent)]
Zip(#[from] zip::result::ZipError),
#[error("Saving hentai metadata page 1 in database failed with: {0}")]
SerdeJson(#[from] serde_json::Error),
}


pub type Result<T> = std::result::Result<T, Error>; // strict error handling, only takes pre defined Error type
#[derive(Debug, thiserror::Error)]
pub enum SearchByTagOnPageError
{
#[error
(
"Downloading hentai metadata page {} / {} from \"{}\" failed with: {source}",
scaler::Formatter::new().set_scaling(scaler::Scaling::None).set_rounding(scaler::Rounding::Magnitude(0)).format(*page_no),
scaler::Formatter::new().set_scaling(scaler::Scaling::None).set_rounding(scaler::Rounding::Magnitude(0)).format(*num_pages),
source.url().map_or_else(|| "<unknown>", |o| o.as_str())
)]
Reqwest {page_no: u32, num_pages: u32, source: reqwest::Error},

#[error
(
"Downloading hentai metadata page {} / {} from \"{url}\" failed with status code {status}.",
scaler::Formatter::new().set_scaling(scaler::Scaling::None).set_rounding(scaler::Rounding::Magnitude(0)).format(*page_no),
scaler::Formatter::new().set_scaling(scaler::Scaling::None).set_rounding(scaler::Rounding::Magnitude(0)).format(*num_pages),
)]
ReqwestStatus {page_no: u32, num_pages: u32, url: String, status: reqwest::StatusCode},

#[error
(
"Saving hentai metadata page {} / {} in database failed with: {source}",
scaler::Formatter::new().set_scaling(scaler::Scaling::None).set_rounding(scaler::Rounding::Magnitude(0)).format(*page_no),
scaler::Formatter::new().set_scaling(scaler::Scaling::None).set_rounding(scaler::Rounding::Magnitude(0)).format(*num_pages),
)]
SerdeJson {page_no: u32, num_pages: u32, source: serde_json::Error},
}
45 changes: 11 additions & 34 deletions src/get_hentai_id_list.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
// Copyright (c) 2024 구FS, all rights reserved. Subject to the MIT licence in `licence.md`.
use crate::error::*;
use crate::search_api::*;
use tokio::io::AsyncWriteExt;

Expand All @@ -19,7 +18,7 @@ use tokio::io::AsyncWriteExt;
///
/// # Returns
/// - list of hentai ID to download
pub async fn get_hentai_id_list(downloadme_filepath: &std::path::Path, http_client: &reqwest::Client, nhentai_tag_search_url: &str, nhentai_tag: &Option<String>, db: &sqlx::sqlite::SqlitePool) -> Vec<u32>
pub async fn get_hentai_id_list(downloadme_filepath: &str, http_client: &reqwest::Client, nhentai_tag_search_url: &str, nhentai_tag: &Option<String>, db: &sqlx::sqlite::SqlitePool) -> Vec<u32>
{
let mut hentai_id_list: Vec<u32> = Vec::new(); // list of hentai id to download

Expand All @@ -31,14 +30,14 @@ pub async fn get_hentai_id_list(downloadme_filepath: &std::path::Path, http_clie
Ok(content) =>
{
hentai_id_list = content.lines().filter_map(|line| line.parse::<u32>().ok()).collect(); // String -> Vec<u32>, discard unparseable lines
log::info!("Loaded hentai ID list from {downloadme_filepath:?}.");
log::info!("Loaded hentai ID list from \"{downloadme_filepath}\".");
},
Err(e) => log::error!("Loading hentai ID list from {downloadme_filepath:?} failed with: {e}"),
Err(e) => log::warn!("Loading hentai ID list from \"{downloadme_filepath}\" failed with: {e}"),
};
}
else
{
log::info!("No hentai ID list found at {downloadme_filepath:?}.");
log::info!("No hentai ID list found at \"{downloadme_filepath}\".");
}
if !hentai_id_list.is_empty() // if hentai_id_list is not empty: work is done
{
Expand All @@ -59,29 +58,7 @@ pub async fn get_hentai_id_list(downloadme_filepath: &std::path::Path, http_clie
).await
{
Ok(o) => hentai_id_list = o,
Err(e) =>
{
match e
{
Error::Reqwest(e) => log::error!
(
"Downloading hentai \"{}\" metadata page 1 from \"{}\" failed with: {e}",
nhentai_tag_unwrapped,
e.url().map_or_else(|| "<unknown>", |o| o.as_str())
),
Error::ReqwestStatus {url, status} => log::error!
(
"Downloading hentai \"{}\" metadata page 1 from \"{url}\" failed with status code {status}.",
nhentai_tag_unwrapped,
),
Error::SerdeJson(e) => log::error!
(
"Saving hentai \"{}\" metadata page 1 in database failed with: {e}",
nhentai_tag_unwrapped,
),
_ => panic!("Unhandled error: {e}"),
};
}
Err(e) => log::error!("{e}"),
}
}
else // if nhentai_tag is not set: request manual user input
Expand All @@ -97,11 +74,11 @@ pub async fn get_hentai_id_list(downloadme_filepath: &std::path::Path, http_clie
{
match file.write_all(hentai_id_list.iter().map(|id| id.to_string()).collect::<Vec<String>>().join("\n").as_bytes()).await
{
Ok(_) => log::info!("Saved hentai ID list from tag search in {downloadme_filepath:?}."),
Err(e) => log::error!("Writing hentai ID list to {downloadme_filepath:?} failed with: {e}"),
Ok(_) => log::info!("Saved hentai ID list from tag search in {downloadme_filepath}."),
Err(e) => log::warn!("Writing hentai ID list to {downloadme_filepath} failed with: {e}"),
}
},
Err(e) => log::error!("Saving hentai ID list at {downloadme_filepath:?} failed with: {e}"),
Err(e) => log::warn!("Saving hentai ID list at {downloadme_filepath} failed with: {e}"),
}
#[cfg(not(target_family = "unix"))]
match tokio::fs::OpenOptions::new().create_new(true).write(true).open(downloadme_filepath).await
Expand All @@ -110,11 +87,11 @@ pub async fn get_hentai_id_list(downloadme_filepath: &std::path::Path, http_clie
{
match file.write_all(hentai_id_list.iter().map(|id| id.to_string()).collect::<Vec<String>>().join("\n").as_bytes()).await
{
Ok(_) => log::info!("Saved hentai ID list from tag search in {downloadme_filepath:?}."),
Err(e) => log::error!("Writing hentai ID list to {downloadme_filepath:?} failed with: {e}"),
Ok(_) => log::info!("Saved hentai ID list from tag search in {downloadme_filepath}."),
Err(e) => log::warn!("Writing hentai ID list to {downloadme_filepath} failed with: {e}"),
}
},
Err(e) => log::error!("Saving hentai ID list at {downloadme_filepath:?} failed with: {e}"),
Err(e) => log::warn!("Saving hentai ID list at {downloadme_filepath} failed with: {e}"),
}
log::debug!("{hentai_id_list:?}");
return hentai_id_list;
Expand Down
Loading

0 comments on commit 3a458ec

Please sign in to comment.