diff options
| -rw-r--r-- | src/main.rs | 26 | ||||
| -rw-r--r-- | src/models.rs | 22 |
2 files changed, 15 insertions, 33 deletions
diff --git a/src/main.rs b/src/main.rs index 30f08ff..626427d 100644 --- a/src/main.rs +++ b/src/main.rs @@ -4,7 +4,7 @@ mod models; use anyhow::{Context, Result}; use clap::Parser; use http_client::build_authenticated_client; -use models::{Chapter, EpubResponse, FileEntry, Paginated, SearchResponse}; +use models::{Chapter, EpubResponse, FileEntry, Paginated, SearchResult}; use reqwest::Client; /// Download and generate an EPUB from Safari Books Online. @@ -22,21 +22,7 @@ struct Args { preserve_log: bool, } -/// Fetches book metadata from the search endpoint. -async fn fetch_metadata(client: &Client, bookid: &str) -> Result<SearchResponse> { - let url = format!("https://learning.oreilly.com/api/v2/search/?query={bookid}&limit=1"); - let response = client - .get(&url) - .send() - .await? - .error_for_status()? - .json::<SearchResponse>() - .await - .context("Failed to deserialize Search API response.")?; - Ok(response) -} - -/// Fetches EPUB structural data (like the chapters URL) +/// Fetches EPUB structural data (like the chapters URL). async fn fetch_epub_data(client: &Client, bookid: &str) -> Result<EpubResponse> { let url = format!("https://learning.oreilly.com/api/v2/epubs/urn:orm:book:{bookid}/"); let response = client @@ -92,8 +78,12 @@ async fn main() -> Result<()> { println!("Fetching book metadata..."); // Fetch from the search API. - let search_data = fetch_metadata(&client, &args.bookid).await?; - if let Some(book) = search_data.results.first() { + let search_url = format!( + "https://learning.oreilly.com/api/v2/search/?query={}", + args.bookid + ); + let search_data: Vec<SearchResult> = fetch_all_pages(&client, search_url).await?; + if let Some(book) = search_data.first() { println!("\n--- Book Found ---"); println!("Title: {}", book.title); println!("Authors: {}", book.authors.join(", ")); diff --git a/src/models.rs b/src/models.rs index 174b983..843744d 100644 --- a/src/models.rs +++ b/src/models.rs @@ -1,12 +1,13 @@ use serde::Deserialize; -// --- Models for the Search API --- - -#[derive(Debug, Deserialize)] -pub struct SearchResponse { - pub results: Vec<SearchResult>, +/// Generic Model for paginated API. +#[derive(Debug, serde::Deserialize)] +pub struct Paginated<T> { + pub next: Option<String>, + pub results: Vec<T>, } +/// Model for the Search API. #[derive(Debug, Deserialize)] pub struct SearchResult { pub title: String, @@ -15,8 +16,7 @@ pub struct SearchResult { pub cover_url: String, } -// --- Models for the EPUB API --- - +/// Model for the EPUB API. #[derive(Debug, Deserialize)] pub struct EpubResponse { pub publication_date: String, @@ -24,14 +24,6 @@ pub struct EpubResponse { pub files: String, // This is a URL to the resource files } -// --- Generic Model for paginated API --- - -#[derive(Debug, serde::Deserialize)] -pub struct Paginated<T> { - pub next: Option<String>, - pub results: Vec<T>, -} - /// Model for chapters API. #[derive(Debug, Deserialize)] pub struct Chapter { |
