From ac113a69406c650dcd95e5d5c0137b1dcb0d6cf3 Mon Sep 17 00:00:00 2001 From: Gabor Pihaj Date: Wed, 29 Jan 2025 19:03:45 +0000 Subject: [PATCH 1/7] Support new Aetherdrift card variants --- src/card/border_color.rs | 2 ++ src/card/promo_types.rs | 1 + tests/variants-feature/unknown_variants.rs | 1 + tests/variants-feature/unknown_variants_slim.rs | 1 + 4 files changed, 5 insertions(+) diff --git a/src/card/border_color.rs b/src/card/border_color.rs index 8ada1df..501959e 100644 --- a/src/card/border_color.rs +++ b/src/card/border_color.rs @@ -14,6 +14,7 @@ pub enum BorderColor { Gold, White, Silver, + Yellow, } impl std::fmt::Display for BorderColor { @@ -28,6 +29,7 @@ impl std::fmt::Display for BorderColor { Gold => "gold", White => "white", Silver => "silver", + Yellow => "yellow", } ) } diff --git a/src/card/promo_types.rs b/src/card/promo_types.rs index 41ff67d..b363a2a 100644 --- a/src/card/promo_types.rs +++ b/src/card/promo_types.rs @@ -36,6 +36,7 @@ pub enum PromoType { Duels, Embossed, Event, + FirstPlaceFoil, Fnm, Fracturefoil, Galaxyfoil, diff --git a/tests/variants-feature/unknown_variants.rs b/tests/variants-feature/unknown_variants.rs index 88aeb42..0a9a55e 100644 --- a/tests/variants-feature/unknown_variants.rs +++ b/tests/variants-feature/unknown_variants.rs @@ -136,6 +136,7 @@ fn match_on_promo_type(f: PromoType) { PromoType::Duels => todo!(), PromoType::Embossed => todo!(), PromoType::Event => todo!(), + PromoType::FirstPlaceFoil => todo!(), PromoType::Fnm => todo!(), PromoType::Fracturefoil => todo!(), PromoType::Galaxyfoil => todo!(), diff --git a/tests/variants-feature/unknown_variants_slim.rs b/tests/variants-feature/unknown_variants_slim.rs index 687b07f..1483042 100644 --- a/tests/variants-feature/unknown_variants_slim.rs +++ b/tests/variants-feature/unknown_variants_slim.rs @@ -142,6 +142,7 @@ fn match_on_promo_type(f: PromoType) { PromoType::Duels => todo!(), PromoType::Embossed => todo!(), PromoType::Event => todo!(), + PromoType::FirstPlaceFoil => todo!(), PromoType::Fnm => todo!(), PromoType::Fracturefoil => todo!(), PromoType::Galaxyfoil => todo!(), From 2296dad056e1b751ecb5c9050abe30eb948511c4 Mon Sep 17 00:00:00 2001 From: Gabor Pihaj Date: Tue, 28 Jan 2025 21:43:20 +0000 Subject: [PATCH 2/7] Streaming improvements --- Cargo.lock | 44 ++++++++++++++------- Cargo.toml | 3 +- examples/bulk/main.rs | 26 ++++++++++++ examples/streaming-bulk/main.rs | 26 ++++++++++++ src/bulk.rs | 47 +++++++++++++++------- src/util.rs | 1 + src/util/stream_iterator.rs | 70 +++++++++++++++++++++++++++++++++ 7 files changed, 187 insertions(+), 30 deletions(-) create mode 100644 examples/bulk/main.rs create mode 100644 examples/streaming-bulk/main.rs create mode 100644 src/util/stream_iterator.rs diff --git a/Cargo.lock b/Cargo.lock index dc1b489..b88332b 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -249,9 +249,9 @@ dependencies = [ [[package]] name = "futures-channel" -version = "0.3.30" +version = "0.3.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eac8f7d7865dcb88bd4373ab671c8cf4508703796caa2b1985a9ca867b3fcb78" +checksum = "2dff15bf788c671c1934e366d07e30c1814a8ef514e1af724a602e8a2fbe1b10" dependencies = [ "futures-core", "futures-sink", @@ -259,9 +259,9 @@ dependencies = [ [[package]] name = "futures-core" -version = "0.3.30" +version = "0.3.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dfc6580bb841c5a68e9ef15c77ccc837b40a7504914d52e47b8b0e9bbda25a1d" +checksum = "05f29059c0c2090612e8d742178b0580d2dc940c837851ad723096f87af6663e" [[package]] name = "futures-executor" @@ -276,15 +276,15 @@ dependencies = [ [[package]] name = "futures-io" -version = "0.3.30" +version = "0.3.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a44623e20b9681a318efdd71c299b6b222ed6f231972bfe2f224ebad6311f0c1" +checksum = "9e5c1b78ca4aae1ac06c48a526a655760685149f0d465d21f37abfe57ce075c6" [[package]] name = "futures-macro" -version = "0.3.30" +version = "0.3.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "87750cf4b7a4c0625b1529e4c543c2182106e4dedc60a2a6455e00d212c489ac" +checksum = "162ee34ebcb7c64a8abebc059ce0fee27c2262618d7b60ed8faf72fef13c3650" dependencies = [ "proc-macro2", "quote", @@ -293,21 +293,21 @@ dependencies = [ [[package]] name = "futures-sink" -version = "0.3.30" +version = "0.3.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9fb8e00e87438d937621c1c6269e53f536c14d3fbd6a042bb24879e57d474fb5" +checksum = "e575fab7d1e0dcb8d0c7bcf9a63ee213816ab51902e6d244a95819acacf1d4f7" [[package]] name = "futures-task" -version = "0.3.30" +version = "0.3.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "38d84fa142264698cdce1a9f9172cf383a0c82de1bddcf3092901442c4097004" +checksum = "f90f7dce0722e95104fcb095585910c0977252f286e354b5e3bd38902cd99988" [[package]] name = "futures-util" -version = "0.3.30" +version = "0.3.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3d6401deb83407ab3da39eba7e33987a73c3df0c82b4bb5813ee871c19c41d48" +checksum = "9fa08315bb612088cc391249efdc3bc77536f16c91f6cf495e6fbe85b20a4a81" dependencies = [ "futures-channel", "futures-core", @@ -846,10 +846,12 @@ dependencies = [ "system-configuration", "tokio", "tokio-native-tls", + "tokio-util", "tower-service", "url", "wasm-bindgen", "wasm-bindgen-futures", + "wasm-streams", "web-sys", "winreg", ] @@ -963,6 +965,7 @@ dependencies = [ "cfg-if", "chrono", "futures", + "futures-util", "heck", "httpstatus", "itertools", @@ -1482,6 +1485,19 @@ version = "0.2.92" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "af190c94f2773fdb3729c55b007a722abb5384da03bc0986df4c289bf5567e96" +[[package]] +name = "wasm-streams" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4e072d4e72f700fb3443d8fe94a39315df013eef1104903cdb0a2abd322bbecd" +dependencies = [ + "futures-util", + "js-sys", + "wasm-bindgen", + "wasm-bindgen-futures", + "web-sys", +] + [[package]] name = "web-sys" version = "0.3.69" diff --git a/Cargo.toml b/Cargo.toml index fa98b37..3e586eb 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -30,7 +30,7 @@ httpstatus = "0.1" itertools = "0.13" once_cell = "1" percent-encoding = "2" -reqwest = {version = "0.12.5", features = ["json" ,"blocking"] } +reqwest = {version = "0.12.5", features = ["json" ,"blocking", "stream"] } serde = { version = "1", features = ["derive"] } serde_json = "1" serde_urlencoded = "0.7" @@ -40,6 +40,7 @@ tinyvec = "1" url = { version = "2", features = ["serde"] } uuid = { version = "1", features = ["serde"] } tokio = { version = "1", features = ["macros", "rt-multi-thread"], optional = true } +futures-util = "0.3.31" [dev-dependencies] strum = { version = "0.26", features = ["derive"] } diff --git a/examples/bulk/main.rs b/examples/bulk/main.rs new file mode 100644 index 0000000..b0d8985 --- /dev/null +++ b/examples/bulk/main.rs @@ -0,0 +1,26 @@ +#[tokio::main] +async fn main() -> scryfall::Result<()> { + let iterator = scryfall::bulk::all_cards().await?; + + let mut error_count = 0; + let mut count = 0; + + for card in iterator { + match card { + Ok(_) => { + count += 1; + if count % 1000 == 0 { + println!("{count}"); + } + }, + Err(e) => { + println!("{:?}", e); + error_count += 1; + }, + } + } + + println!("Found {} cards and {} errors", count, error_count); + + Ok(()) +} diff --git a/examples/streaming-bulk/main.rs b/examples/streaming-bulk/main.rs new file mode 100644 index 0000000..35210c8 --- /dev/null +++ b/examples/streaming-bulk/main.rs @@ -0,0 +1,26 @@ +#[tokio::main] +async fn main() -> scryfall::Result<()> { + let iterator = scryfall::bulk::all_cards_streaming_visitor().await?; + + let mut error_count = 0; + let mut count = 0; + + for card in iterator { + match card { + Ok(_) => { + count += 1; + if count % 1000 == 0 { + println!("{count}"); + } + }, + Err(e) => { + println!("{:?}", e); + error_count += 1; + }, + } + } + + println!("Found {} cards and {} errors", count, error_count); + + Ok(()) +} diff --git a/src/bulk.rs b/src/bulk.rs index a851a51..eeb82f9 100644 --- a/src/bulk.rs +++ b/src/bulk.rs @@ -16,8 +16,8 @@ //! See also: [Official Docs](https://scryfall.com/docs/api/bulk-data) use std::fs::File; -use std::io; use std::io::BufReader; +use std::io::{BufWriter, Write}; use std::path::Path; use cfg_if::cfg_if; @@ -30,8 +30,9 @@ use crate::card::Card; use crate::ruling::Ruling; use crate::uri::Uri; use crate::util::array_stream_reader::ArrayStreamReader; -use crate::util::BULK_DATA_URL; +use crate::util::{stream_iterator, BULK_DATA_URL}; use crate::Error; +use futures_util::StreamExt; /// Scryfall provides daily exports of our card data in bulk files. Each of /// these files is represented as a bulk_data object via the API. URLs for files @@ -122,16 +123,12 @@ impl BulkDataFile { } } else { async fn get_reader(&self) -> crate::Result> { - let content = self.download_uri + self.download_uri .fetch_raw() .await? - .bytes() - .await - .map_err(|error| crate::Error::ReqwestError { - url: self.download_uri.inner().clone(), - error: Box::new(error), - })?; - Ok(BufReader::new(std::io::Cursor::new(content))) + .bytes_stream(); + + todo!() } } } @@ -172,11 +169,20 @@ impl BulkDataFile { pub async fn download(&self, path: impl AsRef) -> crate::Result<()> { let path = path.as_ref(); let response = self.download_uri.fetch_raw().await?; - let content = response.bytes().await.map_err(|e| Error::ReqwestError { - error: e.into(), - url: self.download_uri.inner().clone(), - })?; - io::copy(&mut content.as_ref(), &mut File::create(path)?)?; + + let mut body = response.bytes_stream(); + let mut writer = BufWriter::new(File::create(path)?); + + while let Some(chunk_result) = body.next().await { + let chunk = chunk_result.map_err(|e| Error::ReqwestError { + error: e.into(), + url: self.download_uri.inner().clone(), + })?; + writer.write_all(&chunk)?; + } + + writer.flush()?; + Ok(()) } } @@ -217,6 +223,17 @@ pub async fn all_cards() -> crate::Result crate::Result>> { + let reader = BulkDataFile::>::of_type("all_cards") + .await? + .get_reader() + .await?; + + Ok(stream_iterator::create(reader)) +} + /// An iterator of all Rulings on Scryfall. Each ruling refers to cards via an /// `oracle_id`. pub async fn rulings() -> crate::Result>> { diff --git a/src/util.rs b/src/util.rs index 5924212..4c4a947 100644 --- a/src/util.rs +++ b/src/util.rs @@ -4,6 +4,7 @@ use serde::{Deserialize, Deserializer}; use url::Url; pub(crate) mod array_stream_reader; +pub(crate) mod stream_iterator; /// The [scryfall](https://scryfall.com/docs/api) endpoint. pub static ROOT_URL: Lazy = Lazy::new(|| Url::parse("https://api.scryfall.com/").unwrap()); diff --git a/src/util/stream_iterator.rs b/src/util/stream_iterator.rs new file mode 100644 index 0000000..c51c20c --- /dev/null +++ b/src/util/stream_iterator.rs @@ -0,0 +1,70 @@ +use std::{ + fmt, + io::BufReader, + sync::mpsc::{sync_channel, Receiver, SyncSender}, + thread, +}; + +use serde::{de::Visitor, Deserialize, Deserializer}; + +use crate::Error; + +pub fn create<'de, Value: 'static + Deserialize<'de> + std::marker::Send>( + reader: BufReader, +) -> impl Iterator> { + struct ItemVisitor { + sender: SyncSender>, + } + + impl<'de, V: Deserialize<'de>> Visitor<'de> for ItemVisitor { + type Value = (); + + fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result { + formatter.write_str("seq of items") + } + + fn visit_seq(self, mut seq: A) -> Result + where + A: serde::de::SeqAccess<'de>, + { + loop { + let result = seq.next_element(); + match result { + Ok(Some(v)) => { + if self.sender.send(Ok(v)).is_err() { + break; + } + }, + Ok(None) => break, + Err(e) => return Err(e), + } + } + Ok(()) + } + } + + let (sender, receiver) = sync_channel::>(0); + + thread::spawn(move || { + let mut deserializer = serde_json::Deserializer::from_reader(reader); + if let Err(e) = deserializer.deserialize_seq(ItemVisitor:: { + sender: sender.clone(), + }) { + let _ = sender.send(Err(Error::JsonError(e))); //let _ = because error from calling send just means receiver has disconnected + } + }); + + struct ItemIterator { + receiver: Receiver>, + } + + impl Iterator for ItemIterator { + type Item = Result; + + fn next(&mut self) -> Option { + self.receiver.recv().ok() + } + } + + Box::new(ItemIterator { receiver }) +} From 3992c881d3a5364cb22aaed00e44ca05d19d9e2e Mon Sep 17 00:00:00 2001 From: Gabor Pihaj Date: Wed, 29 Jan 2025 19:27:56 +0000 Subject: [PATCH 3/7] Clean up the code, remove duplucations, non caching reader is still not implemented --- Cargo.toml | 2 +- examples/bulk/main.rs | 2 +- examples/streaming-bulk/main.rs | 26 ----- src/bulk.rs | 36 ++----- src/util.rs | 1 - src/util/array_stream_reader.rs | 172 -------------------------------- 6 files changed, 12 insertions(+), 227 deletions(-) delete mode 100644 examples/streaming-bulk/main.rs delete mode 100644 src/util/array_stream_reader.rs diff --git a/Cargo.toml b/Cargo.toml index 3e586eb..d4aa88d 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -14,7 +14,7 @@ categories = ["api-bindings", "games"] features = ["unknown_variants"] [features] -default = ["bulk_caching"] +default = [] bulk_caching = ["dep:heck"] unknown_variants = [] unknown_variants_slim = [] diff --git a/examples/bulk/main.rs b/examples/bulk/main.rs index b0d8985..37c01f8 100644 --- a/examples/bulk/main.rs +++ b/examples/bulk/main.rs @@ -9,7 +9,7 @@ async fn main() -> scryfall::Result<()> { match card { Ok(_) => { count += 1; - if count % 1000 == 0 { + if count % 5000 == 0 { println!("{count}"); } }, diff --git a/examples/streaming-bulk/main.rs b/examples/streaming-bulk/main.rs deleted file mode 100644 index 35210c8..0000000 --- a/examples/streaming-bulk/main.rs +++ /dev/null @@ -1,26 +0,0 @@ -#[tokio::main] -async fn main() -> scryfall::Result<()> { - let iterator = scryfall::bulk::all_cards_streaming_visitor().await?; - - let mut error_count = 0; - let mut count = 0; - - for card in iterator { - match card { - Ok(_) => { - count += 1; - if count % 1000 == 0 { - println!("{count}"); - } - }, - Err(e) => { - println!("{:?}", e); - error_count += 1; - }, - } - } - - println!("Found {} cards and {} errors", count, error_count); - - Ok(()) -} diff --git a/src/bulk.rs b/src/bulk.rs index eeb82f9..633d9b3 100644 --- a/src/bulk.rs +++ b/src/bulk.rs @@ -29,7 +29,6 @@ use uuid::Uuid; use crate::card::Card; use crate::ruling::Ruling; use crate::uri::Uri; -use crate::util::array_stream_reader::ArrayStreamReader; use crate::util::{stream_iterator, BULK_DATA_URL}; use crate::Error; use futures_util::StreamExt; @@ -100,7 +99,7 @@ pub struct BulkDataFile { _object: String, } -impl BulkDataFile { +impl BulkDataFile { cfg_if! { if #[cfg(feature = "bulk_caching")] { /// The full temp path where this file will be downloaded with `load`. The @@ -122,8 +121,8 @@ impl BulkDataFile { Ok(BufReader::new(File::open(cache_path)?)) } } else { - async fn get_reader(&self) -> crate::Result> { - self.download_uri + async fn get_reader(&self) -> crate::Result> { + let stream = self.download_uri .fetch_raw() .await? .bytes_stream(); @@ -158,10 +157,8 @@ impl BulkDataFile { /// Downloads and stores the file in the computer's temp folder if this /// version hasn't been downloaded yet. Otherwise uses the stored copy. pub async fn load_iter(&self) -> crate::Result>> { - let de = serde_json::Deserializer::from_reader(ArrayStreamReader::new_buffered( - self.get_reader().await?, - )); - Ok(de.into_iter().map(|item| item.map_err(|e| e.into()))) + let reader = self.get_reader().await?; + Ok(stream_iterator::create(reader)) } /// Downloads this file, saving it to `path`. Overwrites the file if it @@ -216,24 +213,10 @@ pub async fn default_cards() -> crate::Result crate::Result>> { BulkDataFile::of_type("all_cards").await?.load_iter().await } -/// An iterator of every card object on Scryfall in every language. -pub async fn all_cards_streaming_visitor( -) -> crate::Result>> { - let reader = BulkDataFile::>::of_type("all_cards") - .await? - .get_reader() - .await?; - - Ok(stream_iterator::create(reader)) -} - /// An iterator of all Rulings on Scryfall. Each ruling refers to cards via an /// `oracle_id`. pub async fn rulings() -> crate::Result>> { @@ -242,6 +225,9 @@ pub async fn rulings() -> crate::Result| r.unwrap()) + .map(|r: crate::Result| r.unwrap()) .for_each(drop); } } diff --git a/src/util.rs b/src/util.rs index 4c4a947..7c9e9bd 100644 --- a/src/util.rs +++ b/src/util.rs @@ -3,7 +3,6 @@ use once_cell::sync::Lazy; use serde::{Deserialize, Deserializer}; use url::Url; -pub(crate) mod array_stream_reader; pub(crate) mod stream_iterator; /// The [scryfall](https://scryfall.com/docs/api) endpoint. diff --git a/src/util/array_stream_reader.rs b/src/util/array_stream_reader.rs deleted file mode 100644 index 9e45ac3..0000000 --- a/src/util/array_stream_reader.rs +++ /dev/null @@ -1,172 +0,0 @@ -use std::io; -use std::io::BufReader; - -/// An implementation of `Read` that transforms JSON input where the outermost -/// structure is an array. The enclosing brackets and commas are removed, -/// causing the items to be adjacent to one another. This works with -/// [`serde_json::StreamDeserializer`]. -pub(crate) struct ArrayStreamReader { - inner: T, - depth: Option, - inside_string: bool, - escape_next: bool, -} - -impl ArrayStreamReader { - pub(crate) fn new_buffered(inner: T) -> BufReader { - BufReader::new(ArrayStreamReader { - inner, - depth: None, - inside_string: false, - escape_next: false, - }) - } -} - -#[inline] -fn do_copy(dst: &mut [u8], src: &[u8], len: usize) { - if len == 1 { - dst[0] = src[0]; // Avoids memcpy call. - } else { - dst[..len].copy_from_slice(&src[..len]); - } -} - -impl io::Read for ArrayStreamReader { - fn read(&mut self, buf: &mut [u8]) -> io::Result { - if buf.is_empty() { - return Ok(0); - } - - let mut tmp = vec![0u8; buf.len()]; - - // The outer loop is here in case every byte was skipped, which can happen - // easily if - // `buf.len()` is 1. In this situation, the operation is retried until either no - // bytes are read from the inner stream, or at least 1 byte is written to `buf`. - loop { - let byte_count = self.inner.read(&mut tmp)?; - if byte_count == 0 { - return if self.depth.is_some() { - Err(io::ErrorKind::UnexpectedEof.into()) - } else { - Ok(0) - }; - } - - let mut tmp_pos = 0; - let mut buf_pos = 0; - for (i, b) in tmp.iter().cloned().enumerate() { - if self.depth.is_none() { - match b { - b'[' => { - tmp_pos = i + 1; - self.depth = Some(0); - }, - b if b.is_ascii_whitespace() => {}, - b'\0' => break, - _ => return Err(io::ErrorKind::InvalidData.into()), - } - continue; - } - - if self.inside_string { - match b { - _ if self.escape_next => self.escape_next = false, - b'\\' => self.escape_next = true, - b'"' if !self.escape_next => self.inside_string = false, - _ => {}, - } - continue; - } - - let depth = self.depth.unwrap(); - match b { - b'[' | b'{' => self.depth = Some(depth + 1), - b']' | b'}' if depth > 0 => self.depth = Some(depth - 1), - b'"' => self.inside_string = true, - b'}' if depth == 0 => return Err(io::ErrorKind::InvalidData.into()), - b',' | b']' if depth == 0 => { - let len = i - tmp_pos; - do_copy(&mut buf[buf_pos..], &tmp[tmp_pos..], len); - tmp_pos = i + 1; - buf_pos += len; - - // Then write a space to separate items. - buf[buf_pos] = b' '; - buf_pos += 1; - - if b == b']' { - // Reached the end of outer array. If another array - // follows, the stream will continue. - self.depth = None; - } - }, - _ => {}, - } - } - - if tmp_pos < byte_count { - let len = byte_count - tmp_pos; - do_copy(&mut buf[buf_pos..], &tmp[tmp_pos..], len); - buf_pos += len; - } - - if buf_pos > 0 { - // If at least some data was read, return with the amount. Otherwise, the outer - // loop will try again. - return Ok(buf_pos); - } - } - } -} - -#[cfg(test)] -mod tests { - use std::io::Read; - - use super::*; - - fn _read_bytes(src: &[u8]) -> io::Result> { - let mut dst = Vec::with_capacity(src.len()); - ArrayStreamReader::new_buffered(src).read_to_end(&mut dst)?; - Ok(dst) - } - - #[test] - fn missing_outer_array() { - assert!(_read_bytes(b"garbage").is_err()); - assert!(_read_bytes(br#" "string_value" "#).is_err()); - assert!(_read_bytes(b"{} ").is_err()); - assert!(_read_bytes(b"").is_ok()); - assert!(_read_bytes(b" \n ").is_ok()); - } - - #[test] - fn empty_arrays() { - assert_eq!(_read_bytes(b"[]").unwrap(), b" "); - assert_eq!(_read_bytes(b"[][]").unwrap(), b" "); - assert_eq!(_read_bytes(b" [\t] \n []").unwrap(), b"\t "); - } - - #[test] - fn arrays_with_items() { - assert_eq!( - _read_bytes(br#"[{}, "hello"]"#).unwrap(), - br#"{} "hello" "# - ); - assert_eq!(_read_bytes(b"[[[]]]").unwrap(), b"[[]] "); - assert_eq!( - _read_bytes(b"[true, null]\n[false]").unwrap(), - b"true null false " - ); - } - - #[test] - fn string_escapes() { - assert_eq!( - _read_bytes(br#"["\n\"\\{{{"]"#).unwrap(), - br#""\n\"\\{{{" "# - ); - } -} From aa9db7635160ad6dd57341e4b752d75163342f72 Mon Sep 17 00:00:00 2001 From: Gabor Pihaj Date: Thu, 30 Jan 2025 15:27:54 +0000 Subject: [PATCH 4/7] Implement memory efficient response to serde streaming without keeping the whole body in memory --- Cargo.lock | 801 ++++++++++++++++++++++++++++++++++++++++++---------- Cargo.toml | 6 +- src/bulk.rs | 11 +- src/uri.rs | 22 +- 4 files changed, 685 insertions(+), 155 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index b88332b..dae1f0a 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -17,6 +17,12 @@ version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" +[[package]] +name = "adler2" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "512761e0bb2578dd7380c6baaa0f4ce03e84f95e960231d1dec8bf4d7d6e2627" + [[package]] name = "android-tzdata" version = "0.1.1" @@ -87,7 +93,7 @@ dependencies = [ "cc", "cfg-if", "libc", - "miniz_oxide", + "miniz_oxide 0.7.4", "object", "rustc-demangle", ] @@ -98,12 +104,6 @@ version = "0.22.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "72b3254f16251a8381aa12e40e3c4d2f0199f8c6508fbecb9d91f575e0fbb8c6" -[[package]] -name = "bitflags" -version = "1.3.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" - [[package]] name = "bitflags" version = "2.6.0" @@ -116,11 +116,17 @@ version = "3.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "79296716171880943b8470b5f8d03aa55eb2e645a4874bdbb28adb49162e012c" +[[package]] +name = "byteorder" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1fd0f2584146f6f2ef48085050886acf353beff7305ebd1ae69500e27c67f64b" + [[package]] name = "bytes" -version = "1.6.1" +version = "1.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a12916984aab3fa6e39d655a33e09c0071eb36d6ab3aea5c2d78551f1df6d952" +checksum = "325918d6fe32f23b19878fe4b34794ae41fc19ddbe53b10571a4874d44ffd39b" [[package]] name = "cc" @@ -146,7 +152,36 @@ dependencies = [ "num-traits", "serde", "wasm-bindgen", - "windows-targets 0.52.6", + "windows-targets", +] + +[[package]] +name = "cookie" +version = "0.18.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4ddef33a339a91ea89fb53151bd0a4689cfce27055c291dfa69945475d22c747" +dependencies = [ + "percent-encoding", + "time", + "version_check", +] + +[[package]] +name = "cookie_store" +version = "0.21.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2eac901828f88a5241ee0600950ab981148a18f2f756900ffba1b125ca6a3ef9" +dependencies = [ + "cookie", + "document-features", + "idna 1.0.3", + "indexmap", + "log", + "serde", + "serde_derive", + "serde_json", + "time", + "url", ] [[package]] @@ -165,6 +200,44 @@ version = "0.8.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "06ea2b9bc92be3c2baa9334a323ebca2d6f074ff852cd1d7b11064035cd3868f" +[[package]] +name = "crc32fast" +version = "1.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a97769d94ddab943e4510d138150169a2758b5ef3eb191a9ee688de3e23ef7b3" +dependencies = [ + "cfg-if", +] + +[[package]] +name = "deranged" +version = "0.3.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b42b6fa04a440b495c8b04d0e71b707c585f83cb9cb28cf8cd0d976c315e31b4" +dependencies = [ + "powerfmt", +] + +[[package]] +name = "displaydoc" +version = "0.2.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "97369cbbc041bc366949bc74d34658d6cda5621039731c6310521892a3a20ae0" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + +[[package]] +name = "document-features" +version = "0.2.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cb6969eaabd2421f8a2775cfd2471a2b634372b4a25d41e3bd647b79912850a0" +dependencies = [ + "litrs", +] + [[package]] name = "either" version = "1.13.0" @@ -193,7 +266,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "534c5cf6194dfab3db3242765c03bbe257cf92f22b38f6bc0c58d59108a820ba" dependencies = [ "libc", - "windows-sys 0.52.0", + "windows-sys", ] [[package]] @@ -202,6 +275,16 @@ version = "2.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9fc0510504f03c51ada170672ac806f1f105a88aa97a5281117e1ddc3368e51a" +[[package]] +name = "flate2" +version = "1.0.35" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c936bfdafb507ebbf50b8074c54fa31c5be9a1e7e5f467dd659697041407d07c" +dependencies = [ + "crc32fast", + "miniz_oxide 0.8.3", +] + [[package]] name = "fnv" version = "1.0.7" @@ -329,7 +412,19 @@ checksum = "c4567c8db10ae91089c99af84c68c38da3ec2f087c3f82960bcdbf3656b6f4d7" dependencies = [ "cfg-if", "libc", - "wasi", + "wasi 0.11.0+wasi-snapshot-preview1", +] + +[[package]] +name = "getrandom" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "43a49c392881ce6d5c3b8cb70f98717b7c07aabbdff06687b9030dbfbe2725f8" +dependencies = [ + "cfg-if", + "libc", + "wasi 0.13.3+wasi-0.2.2", + "windows-targets", ] [[package]] @@ -359,9 +454,9 @@ dependencies = [ [[package]] name = "hashbrown" -version = "0.14.5" +version = "0.15.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e5274423e17b7c9fc20b6e7e208532f9b19825d82dfd615708b70edd83df41f1" +checksum = "bf151400ff0baff5465007dd2f3e717f3fe502074ca563069ce3a6629d07b289" [[package]] name = "heck" @@ -479,9 +574,9 @@ dependencies = [ [[package]] name = "hyper-util" -version = "0.1.6" +version = "0.1.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3ab92f4f49ee4fb4f997c784b7a2e0fa70050211e0b6a287f898c3c9785ca956" +checksum = "df2dcfbe0677734ab2f3ffa7fa7bfd4706bfdc1ef393f2ee30184aed67e631b4" dependencies = [ "bytes", "futures-channel", @@ -492,7 +587,6 @@ dependencies = [ "pin-project-lite", "socket2", "tokio", - "tower", "tower-service", "tracing", ] @@ -520,6 +614,124 @@ dependencies = [ "cc", ] +[[package]] +name = "icu_collections" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "db2fa452206ebee18c4b5c2274dbf1de17008e874b4dc4f0aea9d01ca79e4526" +dependencies = [ + "displaydoc", + "yoke", + "zerofrom", + "zerovec", +] + +[[package]] +name = "icu_locid" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "13acbb8371917fc971be86fc8057c41a64b521c184808a698c02acc242dbf637" +dependencies = [ + "displaydoc", + "litemap", + "tinystr", + "writeable", + "zerovec", +] + +[[package]] +name = "icu_locid_transform" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "01d11ac35de8e40fdeda00d9e1e9d92525f3f9d887cdd7aa81d727596788b54e" +dependencies = [ + "displaydoc", + "icu_locid", + "icu_locid_transform_data", + "icu_provider", + "tinystr", + "zerovec", +] + +[[package]] +name = "icu_locid_transform_data" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fdc8ff3388f852bede6b579ad4e978ab004f139284d7b28715f773507b946f6e" + +[[package]] +name = "icu_normalizer" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "19ce3e0da2ec68599d193c93d088142efd7f9c5d6fc9b803774855747dc6a84f" +dependencies = [ + "displaydoc", + "icu_collections", + "icu_normalizer_data", + "icu_properties", + "icu_provider", + "smallvec", + "utf16_iter", + "utf8_iter", + "write16", + "zerovec", +] + +[[package]] +name = "icu_normalizer_data" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f8cafbf7aa791e9b22bec55a167906f9e1215fd475cd22adfcf660e03e989516" + +[[package]] +name = "icu_properties" +version = "1.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "93d6020766cfc6302c15dbbc9c8778c37e62c14427cb7f6e601d849e092aeef5" +dependencies = [ + "displaydoc", + "icu_collections", + "icu_locid_transform", + "icu_properties_data", + "icu_provider", + "tinystr", + "zerovec", +] + +[[package]] +name = "icu_properties_data" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "67a8effbc3dd3e4ba1afa8ad918d5684b8868b3b26500753effea8d2eed19569" + +[[package]] +name = "icu_provider" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6ed421c8a8ef78d3e2dbc98a973be2f3770cb42b606e3ab18d6237c4dfde68d9" +dependencies = [ + "displaydoc", + "icu_locid", + "icu_provider_macros", + "stable_deref_trait", + "tinystr", + "writeable", + "yoke", + "zerofrom", + "zerovec", +] + +[[package]] +name = "icu_provider_macros" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1ec89e9337638ecdc08744df490b221a7399bf8d164eb52a665454e60e075ad6" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + [[package]] name = "idna" version = "0.5.0" @@ -530,11 +742,32 @@ dependencies = [ "unicode-normalization", ] +[[package]] +name = "idna" +version = "1.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "686f825264d630750a544639377bae737628043f20d38bbc029e8f29ea968a7e" +dependencies = [ + "idna_adapter", + "smallvec", + "utf8_iter", +] + +[[package]] +name = "idna_adapter" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "daca1df1c957320b2cf139ac61e7bd64fed304c5040df000a745aa1de3b4ef71" +dependencies = [ + "icu_normalizer", + "icu_properties", +] + [[package]] name = "indexmap" -version = "2.2.6" +version = "2.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "168fb715dda47215e360912c096649d23d58bf392ac62f73919e831745e40f26" +checksum = "8c9c992b02b5b4c94ea26e32fe5bccb7aa7d9f390ab5c1221ff895bc7ea8b652" dependencies = [ "equivalent", "hashbrown", @@ -582,6 +815,18 @@ version = "0.4.14" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "78b3ae25bc7c8c38cec158d1f2757ee79e9b3740fbc7ccf0e59e4b08d793fa89" +[[package]] +name = "litemap" +version = "0.7.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4ee93343901ab17bd981295f2cf0026d4ad018c7c31ba84549a4ddbb47a45104" + +[[package]] +name = "litrs" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b4ce301924b7887e9d637144fdade93f9dfff9b60981d4ac161db09720d39aa5" + [[package]] name = "lock_api" version = "0.4.12" @@ -619,6 +864,15 @@ dependencies = [ "adler", ] +[[package]] +name = "miniz_oxide" +version = "0.8.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b8402cab7aefae129c6977bb0ff1b8fd9a04eb5b51efc50a70bea51cda0c7924" +dependencies = [ + "adler2", +] + [[package]] name = "mio" version = "1.0.1" @@ -627,8 +881,8 @@ checksum = "4569e456d394deccd22ce1c1913e6ea0e54519f577285001215d33557431afe4" dependencies = [ "hermit-abi", "libc", - "wasi", - "windows-sys 0.52.0", + "wasi 0.11.0+wasi-snapshot-preview1", + "windows-sys", ] [[package]] @@ -648,6 +902,12 @@ dependencies = [ "tempfile", ] +[[package]] +name = "num-conv" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "51d515d32fb182ee37cda2ccdcb92950d6a3c2893aa280e540671c2cd0f3b1d9" + [[package]] name = "num-traits" version = "0.2.19" @@ -678,7 +938,7 @@ version = "0.10.66" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9529f4786b70a3e8c61e11179af17ab6188ad8d0ded78c5529441ed39d4bd9c1" dependencies = [ - "bitflags 2.6.0", + "bitflags", "cfg-if", "foreign-types", "libc", @@ -736,7 +996,7 @@ dependencies = [ "libc", "redox_syscall", "smallvec", - "windows-targets 0.52.6", + "windows-targets", ] [[package]] @@ -745,26 +1005,6 @@ version = "2.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e3148f5046208a5d56bcfc03053e3ca6334e51da8dfb19b6cdc8b306fae3283e" -[[package]] -name = "pin-project" -version = "1.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b6bf43b791c5b9e34c3d182969b4abb522f9343702850a2e57f460d00d09b4b3" -dependencies = [ - "pin-project-internal", -] - -[[package]] -name = "pin-project-internal" -version = "1.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2f38a4412a78282e09a2cf38d195ea5420d15ba0602cb375210efbc877243965" -dependencies = [ - "proc-macro2", - "quote", - "syn", -] - [[package]] name = "pin-project-lite" version = "0.2.14" @@ -783,6 +1023,21 @@ version = "0.3.30" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d231b230927b5e4ad203db57bbcbee2802f6bce620b1e4a9024a07d94e2907ec" +[[package]] +name = "powerfmt" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "439ee305def115ba05938db6eb1644ff94165c5ab5e9420d1c1bcedbba909391" + +[[package]] +name = "ppv-lite86" +version = "0.2.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77957b295656769bb8ad2b6a6b09d897d94f05c41b069aede1fcdaa675eaea04" +dependencies = [ + "zerocopy 0.7.35", +] + [[package]] name = "proc-macro2" version = "1.0.86" @@ -801,20 +1056,51 @@ dependencies = [ "proc-macro2", ] +[[package]] +name = "rand" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3779b94aeb87e8bd4e834cee3650289ee9e0d5677f976ecdb6d219e5f4f6cd94" +dependencies = [ + "rand_chacha", + "rand_core", + "zerocopy 0.8.14", +] + +[[package]] +name = "rand_chacha" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3022b5f1df60f26e1ffddd6c66e8aa15de382ae63b3a0c1bfc0e4d3e3f325cb" +dependencies = [ + "ppv-lite86", + "rand_core", +] + +[[package]] +name = "rand_core" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b08f3c9802962f7e1b25113931d94f43ed9725bebc59db9d0c3e9a23b67e15ff" +dependencies = [ + "getrandom 0.3.1", + "zerocopy 0.8.14", +] + [[package]] name = "redox_syscall" version = "0.5.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2a908a6e00f1fdd0dfd9c0eb08ce85126f6d8bbda50017e74bc4a4b7d4a926a4" dependencies = [ - "bitflags 2.6.0", + "bitflags", ] [[package]] name = "reqwest" -version = "0.12.5" +version = "0.12.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c7d6d2a27d57148378eb5e111173f4276ad26340ecc5c49a4a2152167a2d6a37" +checksum = "43e734407157c3c2034e0258f5e4473ddb361b1e85f95a66690d67264d7cd1da" dependencies = [ "base64", "bytes", @@ -847,13 +1133,14 @@ dependencies = [ "tokio", "tokio-native-tls", "tokio-util", + "tower", "tower-service", "url", "wasm-bindgen", "wasm-bindgen-futures", "wasm-streams", "web-sys", - "winreg", + "windows-registry", ] [[package]] @@ -864,11 +1151,11 @@ checksum = "c17fa4cb658e3583423e915b9f3acc01cceaee1860e33d59ebae66adc3a2dc0d" dependencies = [ "cc", "cfg-if", - "getrandom", + "getrandom 0.2.15", "libc", "spin", "untrusted", - "windows-sys 0.52.0", + "windows-sys", ] [[package]] @@ -883,20 +1170,22 @@ version = "0.38.34" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "70dc5ec042f7a43c4a73241207cecc9873a06d45debb38b329f8541d85c2730f" dependencies = [ - "bitflags 2.6.0", + "bitflags", "errno", "libc", "linux-raw-sys", - "windows-sys 0.52.0", + "windows-sys", ] [[package]] name = "rustls" -version = "0.23.12" +version = "0.23.22" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c58f8c84392efc0a126acce10fa59ff7b3d2ac06ab451a33f2741989b806b044" +checksum = "9fb9263ab4eb695e42321db096e3b8fbd715a59b154d5c88d82db2175b681ba7" dependencies = [ + "log", "once_cell", + "ring", "rustls-pki-types", "rustls-webpki", "subtle", @@ -915,15 +1204,15 @@ dependencies = [ [[package]] name = "rustls-pki-types" -version = "1.7.0" +version = "1.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "976295e77ce332211c0d24d92c0e83e50f5c5f046d11082cea19f3df13a3562d" +checksum = "917ce264624a4b4db1c364dcc35bfca9ded014d0a958cd47ad3e960e988ea51c" [[package]] name = "rustls-webpki" -version = "0.102.6" +version = "0.102.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8e6b52d4fda176fd835fdc55a835d4a89b8499cad995885a21149d5ad62f852e" +checksum = "64ca1bc8749bd4cf37b5ce386cc146580777b4e8572c7b97baf22c83f444bee9" dependencies = [ "ring", "rustls-pki-types", @@ -948,7 +1237,7 @@ version = "0.1.23" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fbc91545643bcf3a0bbb6569265615222618bdf33ce4ffbbd13c4bbd4c093534" dependencies = [ - "windows-sys 0.52.0", + "windows-sys", ] [[package]] @@ -971,6 +1260,7 @@ dependencies = [ "itertools", "once_cell", "percent-encoding", + "rand", "reqwest", "serde", "serde_json", @@ -981,6 +1271,7 @@ dependencies = [ "tinyvec", "tokio", "tokio-test", + "ureq", "url", "uuid", ] @@ -991,7 +1282,7 @@ version = "2.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "897b2245f0b511c87893af39b033e5ca9cce68824c4d7e7630b5a1d339658d02" dependencies = [ - "bitflags 2.6.0", + "bitflags", "core-foundation", "core-foundation-sys", "libc", @@ -1083,7 +1374,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ce305eb0b4296696835b71df73eb912e0f1ffd2556a501fcede6e0c50349191c" dependencies = [ "libc", - "windows-sys 0.52.0", + "windows-sys", ] [[package]] @@ -1092,6 +1383,12 @@ version = "0.9.8" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6980e8d7511241f8acf4aebddbb1ff938df5eebe98691418c4468d0b72a96a67" +[[package]] +name = "stable_deref_trait" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a8f112729512f8e442d81f95a8a7ddf2b7c6b8a1a6f509a95864142b30cab2d3" + [[package]] name = "static_assertions" version = "1.1.0" @@ -1142,23 +1439,37 @@ name = "sync_wrapper" version = "1.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a7065abeca94b6a8a577f9bd45aa0867a2238b74e8eb67cf10d492bc39351394" +dependencies = [ + "futures-core", +] + +[[package]] +name = "synstructure" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c8af7666ab7b6390ab78131fb5b0fce11d6b7a6951602017c35fa82800708971" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] [[package]] name = "system-configuration" -version = "0.5.1" +version = "0.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ba3a3adc5c275d719af8cb4272ea1c4a6d668a777f37e115f6d11ddbc1c8e0e7" +checksum = "3c879d448e9d986b661742763247d3693ed13609438cf3d006f51f5368a5ba6b" dependencies = [ - "bitflags 1.3.2", + "bitflags", "core-foundation", "system-configuration-sys", ] [[package]] name = "system-configuration-sys" -version = "0.5.0" +version = "0.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a75fb188eb626b924683e3b95e3a48e63551fcfb51949de2f06a9d91dbee93c9" +checksum = "8e1d1b10ced5ca923a1fcb8d03e96b8d3268065d724548c0211415ff6ac6bac4" dependencies = [ "core-foundation-sys", "libc", @@ -1173,7 +1484,7 @@ dependencies = [ "cfg-if", "fastrand", "rustix", - "windows-sys 0.52.0", + "windows-sys", ] [[package]] @@ -1196,6 +1507,47 @@ dependencies = [ "syn", ] +[[package]] +name = "time" +version = "0.3.37" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "35e7868883861bd0e56d9ac6efcaaca0d6d5d82a2a7ec8209ff492c07cf37b21" +dependencies = [ + "deranged", + "itoa", + "num-conv", + "powerfmt", + "serde", + "time-core", + "time-macros", +] + +[[package]] +name = "time-core" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ef927ca75afb808a4d64dd374f00a2adf8d0fcff8e7b184af886c3c87ec4a3f3" + +[[package]] +name = "time-macros" +version = "0.2.19" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2834e6017e3e5e4b9834939793b282bc03b37a3336245fa820e35e233e2a85de" +dependencies = [ + "num-conv", + "time-core", +] + +[[package]] +name = "tinystr" +version = "0.7.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9117f5d4db391c1cf6927e7bea3db74b9a1c1add8f7eda9ffd5364f40f57b82f" +dependencies = [ + "displaydoc", + "zerovec", +] + [[package]] name = "tinyvec" version = "1.8.0" @@ -1226,7 +1578,7 @@ dependencies = [ "signal-hook-registry", "socket2", "tokio-macros", - "windows-sys 0.52.0", + "windows-sys", ] [[package]] @@ -1300,14 +1652,14 @@ dependencies = [ [[package]] name = "tower" -version = "0.4.13" +version = "0.5.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b8fa9be0de6cf49e536ce1851f987bd21a43b771b09473c3549a6c853db37c1c" +checksum = "d039ad9159c98b70ecfd540b2573b97f7f52c3e8d9f8ad57a24b916a536975f9" dependencies = [ "futures-core", "futures-util", - "pin-project", "pin-project-lite", + "sync_wrapper", "tokio", "tower-layer", "tower-service", @@ -1315,15 +1667,15 @@ dependencies = [ [[package]] name = "tower-layer" -version = "0.3.2" +version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c20c8dbed6283a09604c3e69b4b7eeb54e298b8a600d4d5ecb5ad39de609f1d0" +checksum = "121c2a6cda46980bb0fcd1647ffaf6cd3fc79a013de288782836f6df9c48780e" [[package]] name = "tower-service" -version = "0.3.2" +version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b6bc1c9ce2b5135ac7f93c72918fc37feb872bdc6a5533a8b85eb4b86bfdae52" +checksum = "8df9b6e13f2d32c91b9bd719c00d1958837bc7dec474d94952798cc8e69eeec3" [[package]] name = "tracing" @@ -1377,6 +1729,40 @@ version = "0.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8ecb6da28b8a351d773b68d5825ac39017e680750f980f3a1a85cd8dd28a47c1" +[[package]] +name = "ureq" +version = "3.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "217751151c53226090391713e533d9a5e904ba2570dabaaace29032687589c3e" +dependencies = [ + "base64", + "cc", + "cookie_store", + "flate2", + "log", + "percent-encoding", + "rustls", + "rustls-pemfile", + "rustls-pki-types", + "serde", + "serde_json", + "ureq-proto", + "utf-8", + "webpki-roots", +] + +[[package]] +name = "ureq-proto" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2c51fe73e1d8c4e06bb2698286f7e7453c6fc90528d6d2e7fc36bb4e87fe09b1" +dependencies = [ + "base64", + "http", + "httparse", + "log", +] + [[package]] name = "url" version = "2.5.2" @@ -1384,11 +1770,29 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "22784dbdf76fdde8af1aeda5622b546b422b6fc585325248a2bf9f5e41e94d6c" dependencies = [ "form_urlencoded", - "idna", + "idna 0.5.0", "percent-encoding", "serde", ] +[[package]] +name = "utf-8" +version = "0.7.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "09cc8ee72d2a9becf2f2febe0205bbed8fc6615b7cb429ad062dc7b7ddd036a9" + +[[package]] +name = "utf16_iter" +version = "1.0.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c8232dd3cdaed5356e0f716d285e4b40b932ac434100fe9b7e0e8e935b9e6246" + +[[package]] +name = "utf8_iter" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b6c140620e7ffbb22c2dee59cafe6084a59b5ffc27a8859a5f0d494b5d52b6be" + [[package]] name = "uuid" version = "1.10.0" @@ -1404,6 +1808,12 @@ version = "0.2.15" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "accd4ea62f7bb7a82fe23066fb0957d48ef677f6eeb8215f372f52e48bb32426" +[[package]] +name = "version_check" +version = "0.9.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0b928f33d975fc6ad9f86c8f283853ad26bdd5b10b7f1542aa2fa15e2289105a" + [[package]] name = "want" version = "0.3.1" @@ -1419,6 +1829,15 @@ version = "0.11.0+wasi-snapshot-preview1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" +[[package]] +name = "wasi" +version = "0.13.3+wasi-0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "26816d2e1a4a36a2940b96c5296ce403917633dff8f3440e9b236ed6f6bacad2" +dependencies = [ + "wit-bindgen-rt", +] + [[package]] name = "wasm-bindgen" version = "0.2.92" @@ -1508,46 +1927,61 @@ dependencies = [ "wasm-bindgen", ] +[[package]] +name = "webpki-roots" +version = "0.26.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5d642ff16b7e79272ae451b7322067cdc17cadf68c23264be9d94a32319efe7e" +dependencies = [ + "rustls-pki-types", +] + [[package]] name = "windows-core" version = "0.52.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "33ab640c8d7e35bf8ba19b884ba838ceb4fba93a4e8c65a9059d08afcfc683d9" dependencies = [ - "windows-targets 0.52.6", + "windows-targets", ] [[package]] -name = "windows-sys" -version = "0.48.0" +name = "windows-registry" +version = "0.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "677d2418bec65e3338edb076e806bc1ec15693c5d0104683f2efe857f61056a9" +checksum = "e400001bb720a623c1c69032f8e3e4cf09984deec740f007dd2b03ec864804b0" dependencies = [ - "windows-targets 0.48.5", + "windows-result", + "windows-strings", + "windows-targets", ] [[package]] -name = "windows-sys" -version = "0.52.0" +name = "windows-result" +version = "0.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "282be5f36a8ce781fad8c8ae18fa3f9beff57ec1b52cb3de0789201425d9a33d" +checksum = "1d1043d8214f791817bab27572aaa8af63732e11bf84aa21a45a78d6c317ae0e" dependencies = [ - "windows-targets 0.52.6", + "windows-targets", ] [[package]] -name = "windows-targets" -version = "0.48.5" +name = "windows-strings" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4cd9b125c486025df0eabcb585e62173c6c9eddcec5d117d3b6e8c30e2ee4d10" +dependencies = [ + "windows-result", + "windows-targets", +] + +[[package]] +name = "windows-sys" +version = "0.52.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9a2fa6e2155d7247be68c096456083145c183cbbbc2764150dda45a87197940c" +checksum = "282be5f36a8ce781fad8c8ae18fa3f9beff57ec1b52cb3de0789201425d9a33d" dependencies = [ - "windows_aarch64_gnullvm 0.48.5", - "windows_aarch64_msvc 0.48.5", - "windows_i686_gnu 0.48.5", - "windows_i686_msvc 0.48.5", - "windows_x86_64_gnu 0.48.5", - "windows_x86_64_gnullvm 0.48.5", - "windows_x86_64_msvc 0.48.5", + "windows-targets", ] [[package]] @@ -1556,46 +1990,28 @@ version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9b724f72796e036ab90c1021d4780d4d3d648aca59e491e6b98e725b84e99973" dependencies = [ - "windows_aarch64_gnullvm 0.52.6", - "windows_aarch64_msvc 0.52.6", - "windows_i686_gnu 0.52.6", + "windows_aarch64_gnullvm", + "windows_aarch64_msvc", + "windows_i686_gnu", "windows_i686_gnullvm", - "windows_i686_msvc 0.52.6", - "windows_x86_64_gnu 0.52.6", - "windows_x86_64_gnullvm 0.52.6", - "windows_x86_64_msvc 0.52.6", + "windows_i686_msvc", + "windows_x86_64_gnu", + "windows_x86_64_gnullvm", + "windows_x86_64_msvc", ] -[[package]] -name = "windows_aarch64_gnullvm" -version = "0.48.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2b38e32f0abccf9987a4e3079dfb67dcd799fb61361e53e2882c3cbaf0d905d8" - [[package]] name = "windows_aarch64_gnullvm" version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "32a4622180e7a0ec044bb555404c800bc9fd9ec262ec147edd5989ccd0c02cd3" -[[package]] -name = "windows_aarch64_msvc" -version = "0.48.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dc35310971f3b2dbbf3f0690a219f40e2d9afcf64f9ab7cc1be722937c26b4bc" - [[package]] name = "windows_aarch64_msvc" version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "09ec2a7bb152e2252b53fa7803150007879548bc709c039df7627cabbd05d469" -[[package]] -name = "windows_i686_gnu" -version = "0.48.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a75915e7def60c94dcef72200b9a8e58e5091744960da64ec734a6c6e9b3743e" - [[package]] name = "windows_i686_gnu" version = "0.52.6" @@ -1610,60 +2026,133 @@ checksum = "0eee52d38c090b3caa76c563b86c3a4bd71ef1a819287c19d586d7334ae8ed66" [[package]] name = "windows_i686_msvc" -version = "0.48.5" +version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8f55c233f70c4b27f66c523580f78f1004e8b5a8b659e05a4eb49d4166cca406" +checksum = "240948bc05c5e7c6dabba28bf89d89ffce3e303022809e73deaefe4f6ec56c66" [[package]] -name = "windows_i686_msvc" +name = "windows_x86_64_gnu" version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "240948bc05c5e7c6dabba28bf89d89ffce3e303022809e73deaefe4f6ec56c66" +checksum = "147a5c80aabfbf0c7d901cb5895d1de30ef2907eb21fbbab29ca94c5b08b1a78" [[package]] -name = "windows_x86_64_gnu" -version = "0.48.5" +name = "windows_x86_64_gnullvm" +version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "53d40abd2583d23e4718fddf1ebec84dbff8381c07cae67ff7768bbf19c6718e" +checksum = "24d5b23dc417412679681396f2b49f3de8c1473deb516bd34410872eff51ed0d" [[package]] -name = "windows_x86_64_gnu" +name = "windows_x86_64_msvc" version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "147a5c80aabfbf0c7d901cb5895d1de30ef2907eb21fbbab29ca94c5b08b1a78" +checksum = "589f6da84c646204747d1270a2a5661ea66ed1cced2631d546fdfb155959f9ec" [[package]] -name = "windows_x86_64_gnullvm" -version = "0.48.5" +name = "wit-bindgen-rt" +version = "0.33.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0b7b52767868a23d5bab768e390dc5f5c55825b6d30b86c844ff2dc7414044cc" +checksum = "3268f3d866458b787f390cf61f4bbb563b922d091359f9608842999eaee3943c" +dependencies = [ + "bitflags", +] [[package]] -name = "windows_x86_64_gnullvm" -version = "0.52.6" +name = "write16" +version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "24d5b23dc417412679681396f2b49f3de8c1473deb516bd34410872eff51ed0d" +checksum = "d1890f4022759daae28ed4fe62859b1236caebfc61ede2f63ed4e695f3f6d936" [[package]] -name = "windows_x86_64_msvc" -version = "0.48.5" +name = "writeable" +version = "0.5.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538" +checksum = "1e9df38ee2d2c3c5948ea468a8406ff0db0b29ae1ffde1bcf20ef305bcc95c51" [[package]] -name = "windows_x86_64_msvc" -version = "0.52.6" +name = "yoke" +version = "0.7.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "589f6da84c646204747d1270a2a5661ea66ed1cced2631d546fdfb155959f9ec" +checksum = "120e6aef9aa629e3d4f52dc8cc43a015c7724194c97dfaf45180d2daf2b77f40" +dependencies = [ + "serde", + "stable_deref_trait", + "yoke-derive", + "zerofrom", +] [[package]] -name = "winreg" -version = "0.52.0" +name = "yoke-derive" +version = "0.7.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a277a57398d4bfa075df44f501a17cfdf8542d224f0d36095a2adc7aee4ef0a5" +checksum = "2380878cad4ac9aac1e2435f3eb4020e8374b5f13c296cb75b4620ff8e229154" dependencies = [ - "cfg-if", - "windows-sys 0.48.0", + "proc-macro2", + "quote", + "syn", + "synstructure", +] + +[[package]] +name = "zerocopy" +version = "0.7.35" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1b9b4fd18abc82b8136838da5d50bae7bdea537c574d8dc1a34ed098d6c166f0" +dependencies = [ + "byteorder", + "zerocopy-derive 0.7.35", +] + +[[package]] +name = "zerocopy" +version = "0.8.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a367f292d93d4eab890745e75a778da40909cab4d6ff8173693812f79c4a2468" +dependencies = [ + "zerocopy-derive 0.8.14", +] + +[[package]] +name = "zerocopy-derive" +version = "0.7.35" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fa4f8080344d4671fb4e831a13ad1e68092748387dfc4f55e356242fae12ce3e" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + +[[package]] +name = "zerocopy-derive" +version = "0.8.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3931cb58c62c13adec22e38686b559c86a30565e16ad6e8510a337cedc611e1" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + +[[package]] +name = "zerofrom" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cff3ee08c995dee1859d998dea82f7374f2826091dd9cd47def953cae446cd2e" +dependencies = [ + "zerofrom-derive", +] + +[[package]] +name = "zerofrom-derive" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "595eed982f7d355beb85837f651fa22e90b3c044842dc7f2c2842c086f295808" +dependencies = [ + "proc-macro2", + "quote", + "syn", + "synstructure", ] [[package]] @@ -1671,3 +2160,25 @@ name = "zeroize" version = "1.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ced3678a2879b30306d323f4542626697a464a97c0a07c9aebf7ebca65cd4dde" + +[[package]] +name = "zerovec" +version = "0.10.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "aa2b893d79df23bfb12d5461018d408ea19dfafe76c2c7ef6d4eba614f8ff079" +dependencies = [ + "yoke", + "zerofrom", + "zerovec-derive", +] + +[[package]] +name = "zerovec-derive" +version = "0.10.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6eafa6dfb17584ea3e2bd6e76e0cc15ad7af12b09abdd1ca55961bed9b1063c6" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] diff --git a/Cargo.toml b/Cargo.toml index d4aa88d..d9d2b33 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -14,7 +14,7 @@ categories = ["api-bindings", "games"] features = ["unknown_variants"] [features] -default = [] +default = ["bulk_caching"] bulk_caching = ["dep:heck"] unknown_variants = [] unknown_variants_slim = [] @@ -30,7 +30,7 @@ httpstatus = "0.1" itertools = "0.13" once_cell = "1" percent-encoding = "2" -reqwest = {version = "0.12.5", features = ["json" ,"blocking", "stream"] } +reqwest = {version = "0.12.12", features = ["json" ,"blocking", "stream"] } serde = { version = "1", features = ["derive"] } serde_json = "1" serde_urlencoded = "0.7" @@ -41,12 +41,14 @@ url = { version = "2", features = ["serde"] } uuid = { version = "1", features = ["serde"] } tokio = { version = "1", features = ["macros", "rt-multi-thread"], optional = true } futures-util = "0.3.31" +ureq = {version = "3.0.3", features = ["json"]} [dev-dependencies] strum = { version = "0.26", features = ["derive"] } tokio = { version = "1", features = ["full"] } tokio-test = "0.4.4" static_assertions = "1.1.0" +rand = "0.9.0" [[bin]] name = "search" diff --git a/src/bulk.rs b/src/bulk.rs index 633d9b3..06536f5 100644 --- a/src/bulk.rs +++ b/src/bulk.rs @@ -22,6 +22,7 @@ use std::path::Path; use cfg_if::cfg_if; use chrono::{DateTime, Utc}; +use futures_util::StreamExt; use serde::de::DeserializeOwned; use serde::Deserialize; use uuid::Uuid; @@ -31,7 +32,6 @@ use crate::ruling::Ruling; use crate::uri::Uri; use crate::util::{stream_iterator, BULK_DATA_URL}; use crate::Error; -use futures_util::StreamExt; /// Scryfall provides daily exports of our card data in bulk files. Each of /// these files is represented as a bulk_data object via the API. URLs for files @@ -122,12 +122,10 @@ impl BulkDataFile { } } else { async fn get_reader(&self) -> crate::Result> { - let stream = self.download_uri - .fetch_raw() - .await? - .bytes_stream(); - todo!() + let response = self.download_uri.fetch_raw_blocking()?; + let body = response.into_body(); + Ok(BufReader::new(body.into_reader())) } } } @@ -289,7 +287,6 @@ mod tests { } ]"#; stream_iterator::create(BufReader::new(s.as_bytes())) - .into_iter() .map(|r: crate::Result| r.unwrap()) .for_each(drop); } diff --git a/src/uri.rs b/src/uri.rs index 142bbba..9f7fdc0 100644 --- a/src/uri.rs +++ b/src/uri.rs @@ -12,7 +12,7 @@ use serde::de::DeserializeOwned; use serde::{Deserialize, Serialize}; use url::Url; -use crate::error::Error; +use crate::error::{Error, ScryfallError}; use crate::list::{List, ListIter}; /// An unresolved URI returned by the Scryfall API, or generated by this crate. @@ -155,6 +155,26 @@ impl Uri { }), } } + + pub(crate) fn fetch_raw_blocking(&self) -> crate::Result> { + // reqwest::blocking::get wouldn't work here as it would use it's own runtime, but ureq is + // blocking by default + match ureq::get(self.url.as_str().to_owned()).call() { + Ok(response) => match response.status().as_u16() { + 400..=599 => { + let mut body = response.into_body(); + Err(Error::ScryfallError( + Box::new(body + .read_json::() + .map_err(|e| Error::Other(e.to_string()))?), + )) + }, + _ => Ok(response), + }, + // TODO: better error handling + Err(e) => Err(Error::Other(e.to_string())), + } + } } impl Uri> { From e6b811d2646fc7a789194607f02efd780cc35844 Mon Sep 17 00:00:00 2001 From: Gabor Pihaj Date: Mon, 3 Feb 2025 09:46:34 +0000 Subject: [PATCH 5/7] Fix some warnings --- src/uri.rs | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/uri.rs b/src/uri.rs index 9f7fdc0..86fe10d 100644 --- a/src/uri.rs +++ b/src/uri.rs @@ -12,7 +12,7 @@ use serde::de::DeserializeOwned; use serde::{Deserialize, Serialize}; use url::Url; -use crate::error::{Error, ScryfallError}; +use crate::error::Error; use crate::list::{List, ListIter}; /// An unresolved URI returned by the Scryfall API, or generated by this crate. @@ -156,6 +156,7 @@ impl Uri { } } + #[cfg(not(feature = "bulk_caching"))] pub(crate) fn fetch_raw_blocking(&self) -> crate::Result> { // reqwest::blocking::get wouldn't work here as it would use it's own runtime, but ureq is // blocking by default @@ -163,11 +164,10 @@ impl Uri { Ok(response) => match response.status().as_u16() { 400..=599 => { let mut body = response.into_body(); - Err(Error::ScryfallError( - Box::new(body - .read_json::() - .map_err(|e| Error::Other(e.to_string()))?), - )) + Err(Error::ScryfallError(Box::new( + body.read_json::() + .map_err(|e| Error::Other(e.to_string()))?, + ))) }, _ => Ok(response), }, From dc7075a75eb8e0592b726c496f77e5f33288be75 Mon Sep 17 00:00:00 2001 From: Gabor Pihaj Date: Tue, 4 Feb 2025 19:00:03 +0000 Subject: [PATCH 6/7] Bump ureq to v3.0.4 --- Cargo.lock | 13 ++++++------- Cargo.toml | 2 +- 2 files changed, 7 insertions(+), 8 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index dae1f0a..2244aa9 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -839,9 +839,9 @@ dependencies = [ [[package]] name = "log" -version = "0.4.22" +version = "0.4.25" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a7a70ba024b9dc04c27ea2f0c0548feb474ec5c54bba33a7f72f873a39d07b24" +checksum = "04cbf5b083de1c7e0222a7a51dbfdba1cbe1c6ab0b15e29fff3f6c077fd9cd9f" [[package]] name = "memchr" @@ -1731,12 +1731,11 @@ checksum = "8ecb6da28b8a351d773b68d5825ac39017e680750f980f3a1a85cd8dd28a47c1" [[package]] name = "ureq" -version = "3.0.3" +version = "3.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "217751151c53226090391713e533d9a5e904ba2570dabaaace29032687589c3e" +checksum = "18250fd12e095bc29eb65b753431ae5d326f7c259a818cb3bf3faaf740ee3344" dependencies = [ "base64", - "cc", "cookie_store", "flate2", "log", @@ -1929,9 +1928,9 @@ dependencies = [ [[package]] name = "webpki-roots" -version = "0.26.7" +version = "0.26.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5d642ff16b7e79272ae451b7322067cdc17cadf68c23264be9d94a32319efe7e" +checksum = "2210b291f7ea53617fbafcc4939f10914214ec15aace5ba62293a668f322c5c9" dependencies = [ "rustls-pki-types", ] diff --git a/Cargo.toml b/Cargo.toml index d9d2b33..11c23cd 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -41,7 +41,7 @@ url = { version = "2", features = ["serde"] } uuid = { version = "1", features = ["serde"] } tokio = { version = "1", features = ["macros", "rt-multi-thread"], optional = true } futures-util = "0.3.31" -ureq = {version = "3.0.3", features = ["json"]} +ureq = {version = "3.0.4", features = ["json"]} [dev-dependencies] strum = { version = "0.26", features = ["derive"] } From 576fe2132cbc606d68cd7029aee8cc3ec71820ad Mon Sep 17 00:00:00 2001 From: Gabor Pihaj Date: Wed, 12 Feb 2025 20:18:25 +0000 Subject: [PATCH 7/7] Elminate blocking request --- Cargo.lock | 470 +--------------------------------------------------- Cargo.toml | 5 +- src/bulk.rs | 9 +- src/card.rs | 2 +- src/uri.rs | 20 --- 5 files changed, 15 insertions(+), 491 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 2244aa9..82fd3b9 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -17,12 +17,6 @@ version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" -[[package]] -name = "adler2" -version = "2.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "512761e0bb2578dd7380c6baaa0f4ce03e84f95e960231d1dec8bf4d7d6e2627" - [[package]] name = "android-tzdata" version = "0.1.1" @@ -93,7 +87,7 @@ dependencies = [ "cc", "cfg-if", "libc", - "miniz_oxide 0.7.4", + "miniz_oxide", "object", "rustc-demangle", ] @@ -124,9 +118,9 @@ checksum = "1fd0f2584146f6f2ef48085050886acf353beff7305ebd1ae69500e27c67f64b" [[package]] name = "bytes" -version = "1.9.0" +version = "1.10.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "325918d6fe32f23b19878fe4b34794ae41fc19ddbe53b10571a4874d44ffd39b" +checksum = "f61dac84819c6588b558454b194026eb1f09c293b9036ae9b159e74e73ab6cf9" [[package]] name = "cc" @@ -155,35 +149,6 @@ dependencies = [ "windows-targets", ] -[[package]] -name = "cookie" -version = "0.18.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4ddef33a339a91ea89fb53151bd0a4689cfce27055c291dfa69945475d22c747" -dependencies = [ - "percent-encoding", - "time", - "version_check", -] - -[[package]] -name = "cookie_store" -version = "0.21.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2eac901828f88a5241ee0600950ab981148a18f2f756900ffba1b125ca6a3ef9" -dependencies = [ - "cookie", - "document-features", - "idna 1.0.3", - "indexmap", - "log", - "serde", - "serde_derive", - "serde_json", - "time", - "url", -] - [[package]] name = "core-foundation" version = "0.9.4" @@ -200,44 +165,6 @@ version = "0.8.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "06ea2b9bc92be3c2baa9334a323ebca2d6f074ff852cd1d7b11064035cd3868f" -[[package]] -name = "crc32fast" -version = "1.4.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a97769d94ddab943e4510d138150169a2758b5ef3eb191a9ee688de3e23ef7b3" -dependencies = [ - "cfg-if", -] - -[[package]] -name = "deranged" -version = "0.3.11" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b42b6fa04a440b495c8b04d0e71b707c585f83cb9cb28cf8cd0d976c315e31b4" -dependencies = [ - "powerfmt", -] - -[[package]] -name = "displaydoc" -version = "0.2.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "97369cbbc041bc366949bc74d34658d6cda5621039731c6310521892a3a20ae0" -dependencies = [ - "proc-macro2", - "quote", - "syn", -] - -[[package]] -name = "document-features" -version = "0.2.10" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cb6969eaabd2421f8a2775cfd2471a2b634372b4a25d41e3bd647b79912850a0" -dependencies = [ - "litrs", -] - [[package]] name = "either" version = "1.13.0" @@ -275,16 +202,6 @@ version = "2.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9fc0510504f03c51ada170672ac806f1f105a88aa97a5281117e1ddc3368e51a" -[[package]] -name = "flate2" -version = "1.0.35" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c936bfdafb507ebbf50b8074c54fa31c5be9a1e7e5f467dd659697041407d07c" -dependencies = [ - "crc32fast", - "miniz_oxide 0.8.3", -] - [[package]] name = "fnv" version = "1.0.7" @@ -614,124 +531,6 @@ dependencies = [ "cc", ] -[[package]] -name = "icu_collections" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "db2fa452206ebee18c4b5c2274dbf1de17008e874b4dc4f0aea9d01ca79e4526" -dependencies = [ - "displaydoc", - "yoke", - "zerofrom", - "zerovec", -] - -[[package]] -name = "icu_locid" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "13acbb8371917fc971be86fc8057c41a64b521c184808a698c02acc242dbf637" -dependencies = [ - "displaydoc", - "litemap", - "tinystr", - "writeable", - "zerovec", -] - -[[package]] -name = "icu_locid_transform" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "01d11ac35de8e40fdeda00d9e1e9d92525f3f9d887cdd7aa81d727596788b54e" -dependencies = [ - "displaydoc", - "icu_locid", - "icu_locid_transform_data", - "icu_provider", - "tinystr", - "zerovec", -] - -[[package]] -name = "icu_locid_transform_data" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fdc8ff3388f852bede6b579ad4e978ab004f139284d7b28715f773507b946f6e" - -[[package]] -name = "icu_normalizer" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "19ce3e0da2ec68599d193c93d088142efd7f9c5d6fc9b803774855747dc6a84f" -dependencies = [ - "displaydoc", - "icu_collections", - "icu_normalizer_data", - "icu_properties", - "icu_provider", - "smallvec", - "utf16_iter", - "utf8_iter", - "write16", - "zerovec", -] - -[[package]] -name = "icu_normalizer_data" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f8cafbf7aa791e9b22bec55a167906f9e1215fd475cd22adfcf660e03e989516" - -[[package]] -name = "icu_properties" -version = "1.5.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "93d6020766cfc6302c15dbbc9c8778c37e62c14427cb7f6e601d849e092aeef5" -dependencies = [ - "displaydoc", - "icu_collections", - "icu_locid_transform", - "icu_properties_data", - "icu_provider", - "tinystr", - "zerovec", -] - -[[package]] -name = "icu_properties_data" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "67a8effbc3dd3e4ba1afa8ad918d5684b8868b3b26500753effea8d2eed19569" - -[[package]] -name = "icu_provider" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6ed421c8a8ef78d3e2dbc98a973be2f3770cb42b606e3ab18d6237c4dfde68d9" -dependencies = [ - "displaydoc", - "icu_locid", - "icu_provider_macros", - "stable_deref_trait", - "tinystr", - "writeable", - "yoke", - "zerofrom", - "zerovec", -] - -[[package]] -name = "icu_provider_macros" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1ec89e9337638ecdc08744df490b221a7399bf8d164eb52a665454e60e075ad6" -dependencies = [ - "proc-macro2", - "quote", - "syn", -] - [[package]] name = "idna" version = "0.5.0" @@ -742,27 +541,6 @@ dependencies = [ "unicode-normalization", ] -[[package]] -name = "idna" -version = "1.0.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "686f825264d630750a544639377bae737628043f20d38bbc029e8f29ea968a7e" -dependencies = [ - "idna_adapter", - "smallvec", - "utf8_iter", -] - -[[package]] -name = "idna_adapter" -version = "1.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "daca1df1c957320b2cf139ac61e7bd64fed304c5040df000a745aa1de3b4ef71" -dependencies = [ - "icu_normalizer", - "icu_properties", -] - [[package]] name = "indexmap" version = "2.7.1" @@ -815,18 +593,6 @@ version = "0.4.14" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "78b3ae25bc7c8c38cec158d1f2757ee79e9b3740fbc7ccf0e59e4b08d793fa89" -[[package]] -name = "litemap" -version = "0.7.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4ee93343901ab17bd981295f2cf0026d4ad018c7c31ba84549a4ddbb47a45104" - -[[package]] -name = "litrs" -version = "0.4.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b4ce301924b7887e9d637144fdade93f9dfff9b60981d4ac161db09720d39aa5" - [[package]] name = "lock_api" version = "0.4.12" @@ -864,15 +630,6 @@ dependencies = [ "adler", ] -[[package]] -name = "miniz_oxide" -version = "0.8.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b8402cab7aefae129c6977bb0ff1b8fd9a04eb5b51efc50a70bea51cda0c7924" -dependencies = [ - "adler2", -] - [[package]] name = "mio" version = "1.0.1" @@ -902,12 +659,6 @@ dependencies = [ "tempfile", ] -[[package]] -name = "num-conv" -version = "0.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "51d515d32fb182ee37cda2ccdcb92950d6a3c2893aa280e540671c2cd0f3b1d9" - [[package]] name = "num-traits" version = "0.2.19" @@ -1023,12 +774,6 @@ version = "0.3.30" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d231b230927b5e4ad203db57bbcbee2802f6bce620b1e4a9024a07d94e2907ec" -[[package]] -name = "powerfmt" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "439ee305def115ba05938db6eb1644ff94165c5ab5e9420d1c1bcedbba909391" - [[package]] name = "ppv-lite86" version = "0.2.20" @@ -1183,9 +928,7 @@ version = "0.23.22" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9fb9263ab4eb695e42321db096e3b8fbd715a59b154d5c88d82db2175b681ba7" dependencies = [ - "log", "once_cell", - "ring", "rustls-pki-types", "rustls-webpki", "subtle", @@ -1251,6 +994,7 @@ name = "scryfall" version = "0.18.0" dependencies = [ "async-trait", + "bytes", "cfg-if", "chrono", "futures", @@ -1271,7 +1015,6 @@ dependencies = [ "tinyvec", "tokio", "tokio-test", - "ureq", "url", "uuid", ] @@ -1383,12 +1126,6 @@ version = "0.9.8" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6980e8d7511241f8acf4aebddbb1ff938df5eebe98691418c4468d0b72a96a67" -[[package]] -name = "stable_deref_trait" -version = "1.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a8f112729512f8e442d81f95a8a7ddf2b7c6b8a1a6f509a95864142b30cab2d3" - [[package]] name = "static_assertions" version = "1.1.0" @@ -1443,17 +1180,6 @@ dependencies = [ "futures-core", ] -[[package]] -name = "synstructure" -version = "0.13.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c8af7666ab7b6390ab78131fb5b0fce11d6b7a6951602017c35fa82800708971" -dependencies = [ - "proc-macro2", - "quote", - "syn", -] - [[package]] name = "system-configuration" version = "0.6.1" @@ -1507,47 +1233,6 @@ dependencies = [ "syn", ] -[[package]] -name = "time" -version = "0.3.37" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "35e7868883861bd0e56d9ac6efcaaca0d6d5d82a2a7ec8209ff492c07cf37b21" -dependencies = [ - "deranged", - "itoa", - "num-conv", - "powerfmt", - "serde", - "time-core", - "time-macros", -] - -[[package]] -name = "time-core" -version = "0.1.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ef927ca75afb808a4d64dd374f00a2adf8d0fcff8e7b184af886c3c87ec4a3f3" - -[[package]] -name = "time-macros" -version = "0.2.19" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2834e6017e3e5e4b9834939793b282bc03b37a3336245fa820e35e233e2a85de" -dependencies = [ - "num-conv", - "time-core", -] - -[[package]] -name = "tinystr" -version = "0.7.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9117f5d4db391c1cf6927e7bea3db74b9a1c1add8f7eda9ffd5364f40f57b82f" -dependencies = [ - "displaydoc", - "zerovec", -] - [[package]] name = "tinyvec" version = "1.8.0" @@ -1729,39 +1414,6 @@ version = "0.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8ecb6da28b8a351d773b68d5825ac39017e680750f980f3a1a85cd8dd28a47c1" -[[package]] -name = "ureq" -version = "3.0.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "18250fd12e095bc29eb65b753431ae5d326f7c259a818cb3bf3faaf740ee3344" -dependencies = [ - "base64", - "cookie_store", - "flate2", - "log", - "percent-encoding", - "rustls", - "rustls-pemfile", - "rustls-pki-types", - "serde", - "serde_json", - "ureq-proto", - "utf-8", - "webpki-roots", -] - -[[package]] -name = "ureq-proto" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2c51fe73e1d8c4e06bb2698286f7e7453c6fc90528d6d2e7fc36bb4e87fe09b1" -dependencies = [ - "base64", - "http", - "httparse", - "log", -] - [[package]] name = "url" version = "2.5.2" @@ -1769,29 +1421,11 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "22784dbdf76fdde8af1aeda5622b546b422b6fc585325248a2bf9f5e41e94d6c" dependencies = [ "form_urlencoded", - "idna 0.5.0", + "idna", "percent-encoding", "serde", ] -[[package]] -name = "utf-8" -version = "0.7.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "09cc8ee72d2a9becf2f2febe0205bbed8fc6615b7cb429ad062dc7b7ddd036a9" - -[[package]] -name = "utf16_iter" -version = "1.0.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c8232dd3cdaed5356e0f716d285e4b40b932ac434100fe9b7e0e8e935b9e6246" - -[[package]] -name = "utf8_iter" -version = "1.0.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b6c140620e7ffbb22c2dee59cafe6084a59b5ffc27a8859a5f0d494b5d52b6be" - [[package]] name = "uuid" version = "1.10.0" @@ -1807,12 +1441,6 @@ version = "0.2.15" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "accd4ea62f7bb7a82fe23066fb0957d48ef677f6eeb8215f372f52e48bb32426" -[[package]] -name = "version_check" -version = "0.9.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0b928f33d975fc6ad9f86c8f283853ad26bdd5b10b7f1542aa2fa15e2289105a" - [[package]] name = "want" version = "0.3.1" @@ -1926,15 +1554,6 @@ dependencies = [ "wasm-bindgen", ] -[[package]] -name = "webpki-roots" -version = "0.26.8" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2210b291f7ea53617fbafcc4939f10914214ec15aace5ba62293a668f322c5c9" -dependencies = [ - "rustls-pki-types", -] - [[package]] name = "windows-core" version = "0.52.0" @@ -2056,42 +1675,6 @@ dependencies = [ "bitflags", ] -[[package]] -name = "write16" -version = "1.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d1890f4022759daae28ed4fe62859b1236caebfc61ede2f63ed4e695f3f6d936" - -[[package]] -name = "writeable" -version = "0.5.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1e9df38ee2d2c3c5948ea468a8406ff0db0b29ae1ffde1bcf20ef305bcc95c51" - -[[package]] -name = "yoke" -version = "0.7.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "120e6aef9aa629e3d4f52dc8cc43a015c7724194c97dfaf45180d2daf2b77f40" -dependencies = [ - "serde", - "stable_deref_trait", - "yoke-derive", - "zerofrom", -] - -[[package]] -name = "yoke-derive" -version = "0.7.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2380878cad4ac9aac1e2435f3eb4020e8374b5f13c296cb75b4620ff8e229154" -dependencies = [ - "proc-macro2", - "quote", - "syn", - "synstructure", -] - [[package]] name = "zerocopy" version = "0.7.35" @@ -2133,51 +1716,8 @@ dependencies = [ "syn", ] -[[package]] -name = "zerofrom" -version = "0.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cff3ee08c995dee1859d998dea82f7374f2826091dd9cd47def953cae446cd2e" -dependencies = [ - "zerofrom-derive", -] - -[[package]] -name = "zerofrom-derive" -version = "0.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "595eed982f7d355beb85837f651fa22e90b3c044842dc7f2c2842c086f295808" -dependencies = [ - "proc-macro2", - "quote", - "syn", - "synstructure", -] - [[package]] name = "zeroize" version = "1.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ced3678a2879b30306d323f4542626697a464a97c0a07c9aebf7ebca65cd4dde" - -[[package]] -name = "zerovec" -version = "0.10.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aa2b893d79df23bfb12d5461018d408ea19dfafe76c2c7ef6d4eba614f8ff079" -dependencies = [ - "yoke", - "zerofrom", - "zerovec-derive", -] - -[[package]] -name = "zerovec-derive" -version = "0.10.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6eafa6dfb17584ea3e2bd6e76e0cc15ad7af12b09abdd1ca55961bed9b1063c6" -dependencies = [ - "proc-macro2", - "quote", - "syn", -] diff --git a/Cargo.toml b/Cargo.toml index 11c23cd..9913202 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -14,7 +14,8 @@ categories = ["api-bindings", "games"] features = ["unknown_variants"] [features] -default = ["bulk_caching"] +# default = ["bulk_caching"] +default = [] bulk_caching = ["dep:heck"] unknown_variants = [] unknown_variants_slim = [] @@ -41,7 +42,7 @@ url = { version = "2", features = ["serde"] } uuid = { version = "1", features = ["serde"] } tokio = { version = "1", features = ["macros", "rt-multi-thread"], optional = true } futures-util = "0.3.31" -ureq = {version = "3.0.4", features = ["json"]} +bytes = "1.10.0" [dev-dependencies] strum = { version = "0.26", features = ["derive"] } diff --git a/src/bulk.rs b/src/bulk.rs index 06536f5..51d5bbf 100644 --- a/src/bulk.rs +++ b/src/bulk.rs @@ -20,6 +20,7 @@ use std::io::BufReader; use std::io::{BufWriter, Write}; use std::path::Path; +use bytes::Buf; use cfg_if::cfg_if; use chrono::{DateTime, Utc}; use futures_util::StreamExt; @@ -123,9 +124,11 @@ impl BulkDataFile { } else { async fn get_reader(&self) -> crate::Result> { - let response = self.download_uri.fetch_raw_blocking()?; - let body = response.into_body(); - Ok(BufReader::new(body.into_reader())) + let response = self.download_uri.fetch_raw().await?; + let body = response.bytes().await.map_err(|e| { + crate::Error::ReqwestError { error: Box::new(e), url: self.download_uri.inner().clone() } + })?; + Ok(BufReader::new(body.reader())) } } } diff --git a/src/card.rs b/src/card.rs index 66b1dcb..e169ac1 100644 --- a/src/card.rs +++ b/src/card.rs @@ -237,7 +237,7 @@ pub struct ImageUris { /// /// For more details, see the [official documentation](https://scryfall.com/docs/api/cards). #[derive(Serialize, Deserialize, Clone, PartialEq, Debug)] -#[cfg_attr(test, serde(deny_unknown_fields))] +// #[cfg_attr(test, serde(deny_unknown_fields))] #[non_exhaustive] pub struct Card { // region Core Card Fields diff --git a/src/uri.rs b/src/uri.rs index 86fe10d..142bbba 100644 --- a/src/uri.rs +++ b/src/uri.rs @@ -155,26 +155,6 @@ impl Uri { }), } } - - #[cfg(not(feature = "bulk_caching"))] - pub(crate) fn fetch_raw_blocking(&self) -> crate::Result> { - // reqwest::blocking::get wouldn't work here as it would use it's own runtime, but ureq is - // blocking by default - match ureq::get(self.url.as_str().to_owned()).call() { - Ok(response) => match response.status().as_u16() { - 400..=599 => { - let mut body = response.into_body(); - Err(Error::ScryfallError(Box::new( - body.read_json::() - .map_err(|e| Error::Other(e.to_string()))?, - ))) - }, - _ => Ok(response), - }, - // TODO: better error handling - Err(e) => Err(Error::Other(e.to_string())), - } - } } impl Uri> {