diff --git a/src/api/fanbox.rs b/src/api/fanbox.rs index 21b8738..daaea2d 100644 --- a/src/api/fanbox.rs +++ b/src/api/fanbox.rs @@ -3,9 +3,12 @@ use std::path::PathBuf; use log::error; use reqwest::header; use reqwest_middleware::RequestBuilder; -use serde::{ de::DeserializeOwned, Deserialize, Serialize }; +use serde::{de::DeserializeOwned, Deserialize, Serialize}; -use crate::{ config::Config, fanbox::{Creator, FollowingCreator, Post, PostListItem, SupportingCreator} }; +use crate::{ + config::Config, + fanbox::{Creator, FollowingCreator, Post, PostListItem, SupportingCreator}, +}; use super::ArchiveClient; @@ -25,10 +28,7 @@ impl FanboxClient { pub fn new(config: &Config) -> Self { let inner = ArchiveClient::new(config); let session = config.session(); - Self { - inner, - session, - } + Self { inner, session } } fn wrap_request(&self, builder: RequestBuilder) -> RequestBuilder { @@ -72,43 +72,54 @@ impl FanboxClient { let response = request.send().await.expect("Failed to send request"); let mut file = tokio::fs::File::create(path).await.unwrap(); - self.inner.download(response, &mut file).await.expect("Failed to download file"); + self.inner + .download(response, &mut file) + .await + .expect("Failed to download file"); Ok(()) } pub async fn get_supporting_creators( - &self + &self, ) -> Result> { let url = "https://api.fanbox.cc/plan.listSupporting"; let list: APIListSupportingCreator = self - .fetch(url).await + .fetch(url) + .await .expect("Failed to get supporting authors"); Ok(list) } pub async fn get_following_creators( - &self + &self, ) -> Result> { let url = "https://api.fanbox.cc/creator.listFollowing"; let list: APIListFollowingCreator = self - .fetch(url).await + .fetch(url) + .await .expect("Failed to get following authors"); Ok(list) } pub async fn get_posts( &self, - creator: &Creator + creator: &Creator, ) -> Result> { - let url = format!("https://api.fanbox.cc/post.paginateCreator?creatorId={}", creator.id()); + let url = format!( + "https://api.fanbox.cc/post.paginateCreator?creatorId={}", + creator.id() + ); let urls: APIListCreatorPaginate = self.fetch(&url).await.expect("Failed to get post list"); let mut tasks = Vec::new(); for url in urls { let client = self.clone(); let future = async move { - client.fetch::(&url).await.expect("Failed to get post") + client + .fetch::(&url) + .await + .expect("Failed to get post") }; tasks.push(tokio::spawn(future)); } diff --git a/src/api/mod.rs b/src/api/mod.rs index 79693e9..47aa3ed 100644 --- a/src/api/mod.rs +++ b/src/api/mod.rs @@ -1,11 +1,14 @@ pub mod fanbox; -use std::sync::Arc; -use reqwest::{ Client, Response }; -use reqwest_middleware::{ ClientBuilder, ClientWithMiddleware }; -use reqwest_retry::{ policies::ExponentialBackoff, RetryTransientMiddleware }; -use tokio::{ fs::File, sync::{ Semaphore, SemaphorePermit } }; use futures::StreamExt; +use reqwest::{Client, Response}; +use reqwest_middleware::{ClientBuilder, ClientWithMiddleware}; +use reqwest_retry::{policies::ExponentialBackoff, RetryTransientMiddleware}; +use std::sync::Arc; +use tokio::{ + fs::File, + sync::{Semaphore, SemaphorePermit}, +}; use crate::{ config::Config, diff --git a/src/config/mod.rs b/src/config/mod.rs index 3cf49c5..c5bd5ec 100644 --- a/src/config/mod.rs +++ b/src/config/mod.rs @@ -1,7 +1,7 @@ pub mod save_type; -use clap::{ arg, Parser }; -use clap_verbosity_flag::{ InfoLevel, Verbosity }; +use clap::{arg, Parser}; +use clap_verbosity_flag::{InfoLevel, Verbosity}; use dotenv::dotenv; use save_type::SaveType; use std::path::PathBuf; @@ -46,8 +46,7 @@ impl Config { } /// Create a logger with the configured verbosity level pub fn init_logger(&self) -> () { - env_logger::Builder - ::new() + env_logger::Builder::new() .filter_level(self.verbose.log_level_filter()) .format_target(false) .init(); diff --git a/src/creator/mod.rs b/src/creator/mod.rs index 72b7d90..51a39be 100644 --- a/src/creator/mod.rs +++ b/src/creator/mod.rs @@ -1,11 +1,11 @@ -use std::{ collections::HashSet, error::Error, ops::Deref }; +use std::{collections::HashSet, error::Error, ops::Deref}; use chrono::{DateTime, Utc}; use log::info; -use post_archiver::{ Author, AuthorId, FileMetaId, Link }; -use rusqlite::{ params, Connection, OptionalExtension }; +use post_archiver::{Author, AuthorId, FileMetaId, Link}; +use rusqlite::{params, Connection, OptionalExtension}; -use crate::{ api::fanbox::FanboxClient, config::Config, fanbox::Creator }; +use crate::{api::fanbox::FanboxClient, config::Config, fanbox::Creator}; pub async fn get_creators(config: &Config) -> Result, Box> { let accepts = config.accepts(); @@ -52,7 +52,10 @@ pub fn display_creators(creators: &Vec) { fee_width = creator.fee().to_string().len().max(fee_width); } - info!("+-{:-) { pub fn sync_creators( conn: &mut Connection, - creators: Vec + creators: Vec, ) -> Result, Box> { let mut list = vec![]; let tx = conn.transaction().unwrap(); @@ -80,19 +83,18 @@ pub fn sync_creators( let mut get_alias_stmt = tx.prepare("SELECT target FROM author_alias WHERE source = ?")?; let mut get_author_stmt = tx.prepare("SELECT * FROM authors WHERE id = ?")?; let mut update_author_stmt = tx.prepare("UPDATE authors SET links = ? WHERE id = ?")?; - let mut insert_author_stmt = tx.prepare( - "INSERT INTO authors (name,links) VALUES (?,?) RETURNING *" - )?; - let mut insert_alias_stmt = tx.prepare( - "INSERT INTO author_alias (source,target) VALUES (?,?)" - )?; + let mut insert_author_stmt = + tx.prepare("INSERT INTO authors (name,links) VALUES (?,?) RETURNING *")?; + let mut insert_alias_stmt = + tx.prepare("INSERT INTO author_alias (source,target) VALUES (?,?)")?; for creator in creators { let alias = format!("fanbox:{}", creator.id()); let link = || Link::new("fanbox", &format!("https://{}.fanbox.cc/", creator.id())); - let author = match - get_alias_stmt.query_row([&alias], |row| row.get::<_, u32>(0)).optional()? + let author = match get_alias_stmt + .query_row([&alias], |row| row.get::<_, u32>(0)) + .optional()? { Some(id) => { // it should be safe to unwrap here @@ -113,12 +115,19 @@ pub fn sync_creators( author } None => { - info!(" + Add new creator {} -> `{}`", creator.id(), creator.name()); + info!( + " + Add new creator {} -> `{}`", + creator.id(), + creator.name() + ); let name = creator.name(); let link = link(); let links = serde_json::to_string(&[link])?; - let author = insert_author_stmt.query_row(params![name, links], row_to_author)?; - insert_alias_stmt.execute(params![alias, author.id.raw()]).unwrap(); + let author = + insert_author_stmt.query_row(params![name, links], row_to_author)?; + insert_alias_stmt + .execute(params![alias, author.id.raw()]) + .unwrap(); author } }; @@ -129,9 +138,8 @@ pub fn sync_creators( let name: String = row.get("name")?; let links: String = row.get("links")?; - let links: Vec = serde_json - ::from_str(&links) - .expect("Author links is not valid JSON"); + let links: Vec = + serde_json::from_str(&links).expect("Author links is not valid JSON"); let thumb: Option = row.get("id")?; let thumb: Option = thumb.map(FileMetaId::new); @@ -174,4 +182,4 @@ impl Deref for SyncedCreator { fn deref(&self) -> &Self::Target { &self.creator } -} \ No newline at end of file +} diff --git a/src/fanbox/common.rs b/src/fanbox/common.rs index 3e8b2ed..fe1d210 100644 --- a/src/fanbox/common.rs +++ b/src/fanbox/common.rs @@ -2,7 +2,6 @@ use std::hash::Hash; use serde::{Deserialize, Serialize}; - #[derive(Deserialize, Serialize, Debug, Clone, Hash)] #[serde(rename_all = "camelCase")] pub struct User { @@ -29,4 +28,4 @@ pub enum PostType { Article, Video, Entry, -} \ No newline at end of file +} diff --git a/src/fanbox/creator/following.rs b/src/fanbox/creator/following.rs index dd90f50..88ed1ac 100644 --- a/src/fanbox/creator/following.rs +++ b/src/fanbox/creator/following.rs @@ -4,7 +4,6 @@ use crate::fanbox::common::{PostType, User}; use super::Creator; - #[derive(Deserialize, Serialize, Debug, Clone, Hash)] #[serde(rename_all = "camelCase")] pub struct FollowingCreator { @@ -40,4 +39,4 @@ pub struct ProfileItem { ty: PostType, image_url: String, thumbnail_url: String, -} \ No newline at end of file +} diff --git a/src/fanbox/creator/supporting.rs b/src/fanbox/creator/supporting.rs index a8a5bde..d9bccb4 100644 --- a/src/fanbox/creator/supporting.rs +++ b/src/fanbox/creator/supporting.rs @@ -4,7 +4,6 @@ use crate::fanbox::common::User; use super::Creator; - #[derive(Deserialize, Serialize, Debug, Clone, Hash)] #[serde(rename_all = "camelCase")] pub struct SupportingCreator { @@ -27,4 +26,4 @@ impl From for Creator { fee: creator.fee, } } -} \ No newline at end of file +} diff --git a/src/fanbox/mod.rs b/src/fanbox/mod.rs index 285d6f8..444e9f6 100644 --- a/src/fanbox/mod.rs +++ b/src/fanbox/mod.rs @@ -4,4 +4,4 @@ pub mod post; pub use common::*; pub use creator::*; -pub use post::*; \ No newline at end of file +pub use post::*; diff --git a/src/fanbox/post/body.rs b/src/fanbox/post/body.rs index 9836db6..408943f 100644 --- a/src/fanbox/post/body.rs +++ b/src/fanbox/post/body.rs @@ -5,7 +5,6 @@ use serde::{Deserialize, Serialize}; use super::PostListItem; - #[derive(Deserialize, Serialize, Debug, Clone, Hash)] #[serde(rename_all = "camelCase", tag = "type")] pub struct PostBody { @@ -20,7 +19,6 @@ pub struct PostBody { pub url_embed_map: Option>, } - #[derive(Deserialize, Serialize, Debug, Clone, Hash)] #[serde(rename_all = "snake_case", tag = "type")] pub enum PostBlock { @@ -33,25 +31,15 @@ pub enum PostBlock { styles: Option>, }, #[serde(rename_all = "camelCase")] - Image { - image_id: String, - }, + Image { image_id: String }, #[serde(rename_all = "camelCase")] - File { - file_id: String, - }, + File { file_id: String }, #[serde(rename_all = "camelCase")] - Embed { - embed_id: String, - }, + Embed { embed_id: String }, #[serde(rename_all = "camelCase")] - UrlEmbed { - url_embed_id: String, - }, + UrlEmbed { url_embed_id: String }, #[serde(rename_all = "camelCase")] - Video { - video_id: String, - }, + Video { video_id: String }, } #[derive(Deserialize, Serialize, Debug, Clone, Hash)] @@ -146,13 +134,10 @@ pub enum PostTextEmbed { #[serde(rename = "html.card")] HtmlCard { id: String, html: String }, #[serde(rename = "fanbox.post", rename_all = "camelCase")] - FanboxPost { - id: String, - post_info: PostListItem, - }, + FanboxPost { id: String, post_info: PostListItem }, Default { id: String, url: String, host: String, }, -} \ No newline at end of file +} diff --git a/src/fanbox/post/item.rs b/src/fanbox/post/item.rs index ea54608..a14e052 100644 --- a/src/fanbox/post/item.rs +++ b/src/fanbox/post/item.rs @@ -3,7 +3,6 @@ use serde::{Deserialize, Serialize}; use crate::fanbox::User; - #[derive(Deserialize, Serialize, Debug, Clone, Hash)] #[serde(rename_all = "camelCase")] pub struct PostListItem { @@ -32,4 +31,4 @@ pub struct PostListItem { pub enum Cover { CoverImage { url: String }, PostImage { url: String }, -} \ No newline at end of file +} diff --git a/src/fanbox/post/mod.rs b/src/fanbox/post/mod.rs index 9b56fae..77e73ef 100644 --- a/src/fanbox/post/mod.rs +++ b/src/fanbox/post/mod.rs @@ -4,8 +4,8 @@ pub mod item; pub use super::{PostType, User}; use chrono::{DateTime, Utc}; -pub use item::*; pub use body::*; +pub use item::*; use serde::{Deserialize, Serialize}; @@ -64,4 +64,4 @@ pub struct PostShort { id: String, title: String, published_datetime: DateTime, -} \ No newline at end of file +}