diff --git a/Cargo.lock b/Cargo.lock index da11bf8..4bef9bf 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -556,28 +556,21 @@ dependencies = [ ] [[package]] -name = "core-foundation" -version = "0.9.3" +name = "cpufeatures" +version = "0.2.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "194a7a9e6de53fa55116934067c844d9d749312f75c6f6d0980e8c252f8c2146" +checksum = "a17b76ff3a4162b0b27f354a0c87015ddad39d35f9c0c36607a3bdd175dde1f1" dependencies = [ - "core-foundation-sys", "libc", ] [[package]] -name = "core-foundation-sys" -version = "0.8.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e496a50fda8aacccc86d7529e2c1e0892dbd0f898a6b5645b5561b89c3210efa" - -[[package]] -name = "cpufeatures" -version = "0.2.9" +name = "crc32fast" +version = "1.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a17b76ff3a4162b0b27f354a0c87015ddad39d35f9c0c36607a3bdd175dde1f1" +checksum = "b540bd8bc810d3885c6ea91e2018302f68baba2129ab3e88f32389ee9370880d" dependencies = [ - "libc", + "cfg-if", ] [[package]] @@ -829,6 +822,16 @@ version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0ce7134b9999ecaf8bcd65542e436736ef32ddca1b3e06094cb6ec5755203b80" +[[package]] +name = "flate2" +version = "1.0.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "46303f565772937ffe1d394a4fac6f411c6013172fadde9dcdb1e147a086940e" +dependencies = [ + "crc32fast", + "miniz_oxide", +] + [[package]] name = "float-cmp" version = "0.9.0" @@ -900,12 +903,6 @@ dependencies = [ "syn", ] -[[package]] -name = "futures-sink" -version = "0.3.28" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f43be4fe21a13b9781a69afa4985b0f6ee0e1afab2c6f454a8cf30e2b2237b6e" - [[package]] name = "futures-task" version = "0.3.28" @@ -919,11 +916,8 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "26b01e40b772d54cf6c6d721c1d1abd0647a0106a12ecaa1c186273392a69533" dependencies = [ "futures-core", - "futures-io", "futures-macro", - "futures-sink", "futures-task", - "memchr", "pin-project-lite", "pin-utils", "slab", @@ -968,37 +962,12 @@ dependencies = [ "wasm-bindgen", ] -[[package]] -name = "h2" -version = "0.3.21" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "91fc23aa11be92976ef4729127f1a74adf36d8436f7816b185d18df956790833" -dependencies = [ - "bytes", - "fnv", - "futures-core", - "futures-sink", - "futures-util", - "http", - "indexmap 1.9.3", - "slab", - "tokio", - "tokio-util", - "tracing", -] - [[package]] name = "half" version = "1.8.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "eabb4a44450da02c90444cf74558da904edde8fb4e9035a9a6a4e15445af0bd7" -[[package]] -name = "hashbrown" -version = "0.12.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888" - [[package]] name = "hashbrown" version = "0.14.1" @@ -1108,7 +1077,6 @@ dependencies = [ "futures-channel", "futures-core", "futures-util", - "h2", "http", "http-body", "httparse", @@ -1122,20 +1090,6 @@ dependencies = [ "want", ] -[[package]] -name = "hyper-rustls" -version = "0.24.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8d78e1e73ec14cf7375674f74d7dde185c8206fd9dea6fb6295e8a98098aaa97" -dependencies = [ - "futures-util", - "http", - "hyper", - "rustls", - "tokio", - "tokio-rustls", -] - [[package]] name = "idna" version = "0.4.0" @@ -1146,16 +1100,6 @@ dependencies = [ "unicode-normalization", ] -[[package]] -name = "indexmap" -version = "1.9.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bd070e393353796e801d209ad339e89596eb4c8d430d18ede6a1cced8fafbd99" -dependencies = [ - "autocfg", - "hashbrown 0.12.3", -] - [[package]] name = "indexmap" version = "2.0.2" @@ -1163,7 +1107,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8adf3ddd720272c6ea8bf59463c04e0f93d0bbf7c5439b691bca2987e0270897" dependencies = [ "equivalent", - "hashbrown 0.14.1", + "hashbrown", ] [[package]] @@ -1205,12 +1149,6 @@ dependencies = [ "windows-sys 0.48.0", ] -[[package]] -name = "ipnet" -version = "2.8.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "28b29a3cd74f0f4598934efe3aeba42bae0eb4680554128851ebbecb02af14e6" - [[package]] name = "is-terminal" version = "0.4.9" @@ -1552,7 +1490,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e1d3afd2628e69da2be385eb6f2fd57c8ac7977ceeff6dc166ff1657b0e386a9" dependencies = [ "fixedbitset", - "indexmap 2.0.2", + "indexmap", ] [[package]] @@ -1909,48 +1847,6 @@ version = "0.8.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c08c74e62047bb2de4ff487b251e4a92e24f48745648451635cec7d591162d9f" -[[package]] -name = "reqwest" -version = "0.11.22" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "046cd98826c46c2ac8ddecae268eb5c2e58628688a5fc7a2643704a73faba95b" -dependencies = [ - "base64", - "bytes", - "encoding_rs", - "futures-core", - "futures-util", - "h2", - "http", - "http-body", - "hyper", - "hyper-rustls", - "ipnet", - "js-sys", - "log", - "mime", - "once_cell", - "percent-encoding", - "pin-project-lite", - "rustls", - "rustls-pemfile", - "serde", - "serde_json", - "serde_urlencoded", - "system-configuration", - "tokio", - "tokio-rustls", - "tokio-util", - "tower-service", - "url", - "wasm-bindgen", - "wasm-bindgen-futures", - "wasm-streams", - "web-sys", - "webpki-roots", - "winreg", -] - [[package]] name = "ring" version = "0.16.20" @@ -2017,15 +1913,6 @@ dependencies = [ "sct", ] -[[package]] -name = "rustls-pemfile" -version = "1.0.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2d3987094b1d07b653b7dfdc3f70ce9a1da9c51ac18c1b06b662e4f9a0e9f4b2" -dependencies = [ - "base64", -] - [[package]] name = "rustls-webpki" version = "0.101.6" @@ -2123,18 +2010,6 @@ dependencies = [ "serde", ] -[[package]] -name = "serde_urlencoded" -version = "0.7.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d3491c14715ca2294c4d6a88f15e84739788c1d030eed8c110436aafdaa2f3fd" -dependencies = [ - "form_urlencoded", - "itoa", - "ryu", - "serde", -] - [[package]] name = "sha1" version = "0.10.6" @@ -2264,27 +2139,6 @@ dependencies = [ "libc", ] -[[package]] -name = "system-configuration" -version = "0.5.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ba3a3adc5c275d719af8cb4272ea1c4a6d668a777f37e115f6d11ddbc1c8e0e7" -dependencies = [ - "bitflags 1.3.2", - "core-foundation", - "system-configuration-sys", -] - -[[package]] -name = "system-configuration-sys" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a75fb188eb626b924683e3b95e3a48e63551fcfb51949de2f06a9d91dbee93c9" -dependencies = [ - "core-foundation-sys", - "libc", -] - [[package]] name = "target-lexicon" version = "0.12.11" @@ -2410,7 +2264,6 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4f38200e3ef7995e5ef13baec2f432a6da0aa9ac495b2c0e8f3b7eec2c92d653" dependencies = [ "backtrace", - "bytes", "libc", "mio", "num_cpus", @@ -2432,30 +2285,6 @@ dependencies = [ "syn", ] -[[package]] -name = "tokio-rustls" -version = "0.24.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c28327cf380ac148141087fbfb9de9d7bd4e84ab5d2c28fbc911d753de8a7081" -dependencies = [ - "rustls", - "tokio", -] - -[[package]] -name = "tokio-util" -version = "0.7.9" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1d68074620f57a0b21594d9735eb2e98ab38b17f80d3fcb189fca266771ca60d" -dependencies = [ - "bytes", - "futures-core", - "futures-sink", - "pin-project-lite", - "tokio", - "tracing", -] - [[package]] name = "tower-service" version = "0.3.2" @@ -2567,6 +2396,24 @@ version = "0.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a156c684c91ea7d62626509bce3cb4e1d9ed5c4d978f7b4352658f96a4c26b4a" +[[package]] +name = "ureq" +version = "2.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f5ccd538d4a604753ebc2f17cd9946e89b77bf87f6a8e2309667c6f2e87855e3" +dependencies = [ + "base64", + "flate2", + "log", + "once_cell", + "rustls", + "rustls-webpki", + "serde", + "serde_json", + "url", + "webpki-roots", +] + [[package]] name = "url" version = "2.4.1" @@ -2719,19 +2566,6 @@ version = "0.2.87" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ca6ad05a4870b2bf5fe995117d3728437bd27d7cd5f06f13c17443ef369775a1" -[[package]] -name = "wasm-streams" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b4609d447824375f43e1ffbc051b50ad8f4b3ae8219680c94452ea05eb240ac7" -dependencies = [ - "futures-util", - "js-sys", - "wasm-bindgen", - "wasm-bindgen-futures", - "web-sys", -] - [[package]] name = "web-sys" version = "0.3.64" @@ -2911,16 +2745,6 @@ version = "0.48.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538" -[[package]] -name = "winreg" -version = "0.50.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "524e57b2c537c0f9b1e69f1965311ec12182b4122e45035b1508cd24d2adadb1" -dependencies = [ - "cfg-if", - "windows-sys 0.48.0", -] - [[package]] name = "yansi" version = "0.5.1" @@ -2933,7 +2757,7 @@ version = "0.4.1" dependencies = [ "cfg-if", "criterion", - "hashbrown 0.14.1", + "hashbrown", "home", "indoc", "itertools 0.11.0", @@ -2960,20 +2784,18 @@ dependencies = [ "clap_complete", "clap_mangen", "criterion", - "futures-util", "hex", "httpmock", "indicatif", "lazy_static", "predicates", - "reqwest", "serde", "serde_json", "sha1", "stringmetrics", "tempfile", "termcolor", - "tokio", + "ureq", "zspell", ] diff --git a/zspell-cli/Cargo.toml b/zspell-cli/Cargo.toml index 1f6037e..ce866f9 100644 --- a/zspell-cli/Cargo.toml +++ b/zspell-cli/Cargo.toml @@ -17,19 +17,17 @@ path = "src/main.rs" [dependencies] cfg-if = "1.0" clap = { version = "4.4.6", features = ["derive", "wrap_help"] } -futures-util = "0.3" hex = "0.4" indicatif = "0.17" # We opt to use rustls instead of linking openssl -reqwest = { version = "0.11", features = ["blocking", "stream", "rustls-tls"], default-features = false } serde = { version = "1.0.189", features = ["derive"] } serde_json = "1.0.107" sha1 = "0.10.6" stringmetrics = "2.2" termcolor = "1.3.0" -tokio = "1.33.0" anyhow = "1.0.75" zspell = { path = "../zspell", features = ["zspell-unstable"] } +ureq = { version = "2.8.0", features = ["json"] } [dev-dependencies] criterion = "0.5" diff --git a/zspell-cli/src/download.rs b/zspell-cli/src/download.rs index 8767fcd..7346f89 100644 --- a/zspell-cli/src/download.rs +++ b/zspell-cli/src/download.rs @@ -1,10 +1,11 @@ -//! Things required to download dictionaries +//! Things required to download dictionaries from wooorm's repository //! //! This is a work in progress; entire section is largely unfinished +// TODO: should this move to `zspell` under a feature? #![allow(unused)] // WIP -use std::cmp::min; +use std::cmp::{max, min}; use std::fs::{File, OpenOptions}; use std::io::{Read, Seek, Write}; use std::path::Path; @@ -12,9 +13,8 @@ use std::time::Duration; use anyhow::{bail, Context}; use cfg_if::cfg_if; -use futures_util::StreamExt; use indicatif::{ProgressBar, ProgressStyle}; -use reqwest::Client; +use serde::Deserialize; use serde_json::Value; use sha1::{Digest, Sha1}; @@ -25,6 +25,9 @@ const APP_USER_AGENT: &str = concat!(env!("CARGO_PKG_NAME"), "/", env!("CARGO_PK cfg_if! { if #[cfg(not(test))] { const ROOT_URL: &str = "https://api.github.com/repos/wooorm/dictionaries/contents/dictionaries"; + fn get_root_url() -> String { + ROOT_URL.to_owned() + } } else { use lazy_static::lazy_static; use httpmock::prelude::*; @@ -32,6 +35,10 @@ cfg_if! { lazy_static!{ static ref TEST_SERVER: MockServer = MockServer::start(); } + + fn get_root_url() -> String { + TEST_SERVER.url("/content/dictionaries") + } } } @@ -49,14 +56,14 @@ struct DownloadInfo { /// /// Implementation taken from the git help page, located here /// -fn calculate_git_hash(s: &str) -> [u8; 20] { - let mut tmp = String::from("blob "); - tmp.push_str(&s.len().to_string()); - tmp.push('\0'); - tmp.push_str(s); +fn calculate_git_hash(bytes: &[u8]) -> [u8; 20] { + let mut tmp = Vec::from(b"blob ".as_slice()); + tmp.extend_from_slice(bytes.len().to_string().as_bytes()); + tmp.push(b'\0'); + tmp.extend_from_slice(bytes); let mut hasher = Sha1::new(); - hasher.update(tmp.as_bytes()); + hasher.update(&tmp); let res: [u8; 20] = hasher.finalize().into(); res } @@ -84,61 +91,53 @@ fn calculate_git_hash_buf(mut reader: R, len: usize) -> anyhow::Result< Ok(res) } -/// Helper function for getting the root URL that we can "patch" for testing -fn get_root_url() -> String { - #[cfg(not(test))] - return ROOT_URL.to_owned(); - - #[cfg(test)] - return TEST_SERVER.url("/contents/dictionaries"); +/// Contents of a directory +#[derive(Debug, Deserialize)] +struct Tree(Vec); + +#[derive(Debug, Deserialize)] +struct Listing { + name: String, + path: String, + size: usize, + sha: Option, + url: String, + html_url: String, + download_url: Option, + git_url: String, + #[serde(rename = "type")] + ty: String, } /// Gather the URLs to download dictionary, affix, and license files from a client /// /// Only collects the URLs, does not download them. Uses [`get_root_url`] /// as a base then navigates one layer deeper. -async fn retrieve_urls(lang: &str, client: &Client) -> anyhow::Result { - let root_json: Value = client - .get(get_root_url()) - .send() - .await - .context("error while sending request")? - .text() - .await - .map(|txt| { - serde_json::from_str(&txt).context("error understanding server response at root") - })??; +fn retrieve_urls(lang: &str, agent: &ureq::Agent) -> anyhow::Result { + let tree: Tree = agent + .get(&get_root_url()) + .call() + .context("requesting root listing")? + .into_json()?; // Get the URL of the directory to download - let dir_url = root_json - .as_array() - .context("Data is incorrectly formatted")? + let dir_url = tree + .0 .iter() - .find(|x| x["name"] == lang && x["type"] == "dir") - .map(|x| &x["url"]) - .context("Unable to locate language")? - .as_str() - .context("Data is incorrectly formatted")?; + .find(|v| v.name == lang && v.ty == "dir") + .map(|v| &v.url) + .context("locating selected language")?; // Get the listing of that directory - let dir_json: Value = client + let dir_tree: Tree = agent .get(dir_url) - .send() - .await - .context("error while sending request")? - .text() - .await - .map(|txt| { - serde_json::from_str(&txt).context("error understanding server response at dir") - })??; - - let dir_listing = &dir_json - .as_array() - .context("error listing server directory")?; - - let affix = get_dl_url_from_tree(dir_listing, |s| s.ends_with(".aff"))?; - let dictionary = get_dl_url_from_tree(dir_listing, |s| s.ends_with(".dic"))?; - let license = get_dl_url_from_tree(dir_listing, |s| s.ends_with("license"))?; + .call() + .context("requesting dictionary listing")? + .into_json()?; + + let affix = get_dl_url_from_tree(&dir_tree, |s| s.ends_with(".aff"))?; + let dictionary = get_dl_url_from_tree(&dir_tree, |s| s.ends_with(".dic"))?; + let license = get_dl_url_from_tree(&dir_tree, |s| s.ends_with("license"))?; let res = DownloadInfo { affix, @@ -150,20 +149,21 @@ async fn retrieve_urls(lang: &str, client: &Client) -> anyhow::Result bool>(tree: &[Value], f: F) -> anyhow::Result { +/// Take in a file tree and locate one where the name matches the specified pattern +fn get_dl_url_from_tree bool>(tree: &Tree, f: F) -> anyhow::Result { let ctx_str = "could not locate a necessary file"; // Collect the SHA sum and download URL of a file let tmp = tree + .0 .iter() - .find(|x| x["name"].as_str().map(&f).unwrap_or(false)) - .map(|x| (x.get("sha"), x.get("download_url"))) + .find(|v| f(&v.name)) + .map(|v| (&v.sha, &v.download_url)) .context(ctx_str)?; let mut res = String::from("sha1$"); - res.push_str(tmp.0.context(ctx_str)?.as_str().context(ctx_str)?); + res.push_str(tmp.0.as_ref().context(ctx_str)?.as_str()); res.push('$'); - res.push_str(tmp.1.context(ctx_str)?.as_str().context(ctx_str)?); + res.push_str(tmp.1.as_ref().context(ctx_str)?.as_str()); Ok(res) } @@ -185,7 +185,7 @@ fn open_new_file(path: &Path, overwrite: bool) -> anyhow::Result { .read(true) .create(true) .open(path) - .context(format!("unable to open \"{fname}\" in \"{dir}\"")) + .context(format!("unable to open '{fname}' in '{dir}'")) } else { // Otherwise, use create_new to fail if it exists OpenOptions::new() @@ -193,46 +193,55 @@ fn open_new_file(path: &Path, overwrite: bool) -> anyhow::Result { .read(true) .create_new(true) .open(path) - .context(format!("file {fname} already exists in \"{dir}\"")) + .context(format!("file {fname} already exists in '{dir}'")) } } // Download a single file to the given path, and create a progress bar while -// doing so -async fn download_file_with_bar( +// doing so. +fn download_file_with_bar( path: &Path, overwrite: bool, - client: &Client, + agent: &ureq::Agent, url: &str, sha: &[u8], ) -> anyhow::Result<()> { + const CHUNK_SIZE: usize = 100; + let mut buffer = open_new_file(path, overwrite)?; + let resp = agent.get(url).call()?; - let res = client.get(url).send().await?; - let total_size = res.content_length().unwrap_or(100); + // Estimate content length for our buffer capacity & progress bar + let expected_len = match resp.header("Content-Length") { + Some(hdr) => hdr.parse().expect("can't parse number"), + None => 100, + }; + + let mut buf_len = 0usize; + let mut buffer: Vec = Vec::with_capacity(expected_len); + let mut reader = resp.into_reader().take(10_000_000); - let pb = ProgressBar::new(total_size); + let pb = ProgressBar::new(expected_len.try_into().unwrap()); pb.set_style(ProgressStyle::default_bar() .template("{msg}\n{spinner:.green} [{elapsed_precise}] [{bar:.cyan/blue}] {bytes}/{total_bytes} ({bytes_per_sec}, {eta})")? .progress_chars("#>-")); pb.set_message(format!("Downloading {url}")); - let mut finished_bytes: u64 = 0; - let mut stream = res.bytes_stream(); - - while let Some(item) = stream.next().await { - let chunk = item?; - buffer.write_all(&chunk)?; - - let new = min(finished_bytes + (chunk.len() as u64), total_size); - finished_bytes = new; - pb.set_position(new); + loop { + buffer.extend_from_slice(&[0; CHUNK_SIZE]); + let chunk = &mut buffer.as_mut_slice()[buf_len..buf_len + CHUNK_SIZE]; + let read_bytes = reader.read(chunk).expect("error reading stream"); + buf_len += read_bytes; + pb.set_length(max(read_bytes, expected_len).try_into().unwrap()); + pb.set_position(buf_len.try_into().unwrap()); + + if read_bytes == 0 { + break; + } } - let buf_len = buffer.stream_position().unwrap(); - buffer.rewind().context("error writing file").unwrap(); - - let hash = calculate_git_hash_buf(&buffer, buf_len.try_into()?).unwrap(); + buffer.truncate(buf_len); + let hash = calculate_git_hash(&buffer); if hash != sha { bail!("error downloading file; checksum failure"); @@ -244,19 +253,13 @@ async fn download_file_with_bar( } // TODO: make pub -async fn download_dict( - lang: &str, - dest: &Path, - overwrite: bool, - _manifest: &Path, -) -> anyhow::Result<()> { - let client = Client::builder() +fn download_dict(lang: &str, dest: &Path, overwrite: bool, _manifest: &Path) -> anyhow::Result<()> { + let client = ureq::builder() .timeout(Duration::from_secs(10)) .user_agent(APP_USER_AGENT) - .build() - .context("could not create HTTP client")?; + .build(); - let urls = retrieve_urls(lang, &client).await?; + let urls = retrieve_urls(lang, &client)?; let fnames = DownloadInfo { affix: format!("{lang}.aff"), @@ -265,14 +268,12 @@ async fn download_dict( lang: String::default(), }; - // We control these strings, unwrap should be safe // Want to split "sha$some_sha_hex$some_url" into (some_sha_hex, some_url) - fn split_url_sha(s: &str) -> (&str, &str) { - s.split_once('$') - .map(|x| x.1.split_once('$')) - .unwrap() - .unwrap() + let (sha_pfx, rest) = s.split_once('$').unwrap(); + assert_eq!(sha_pfx, "sha1"); + + rest.split_once('$').unwrap() } let info_aff = split_url_sha(urls.affix.as_str()); @@ -285,8 +286,7 @@ async fn download_dict( &client, info_aff.1, hex::decode(info_aff.0.as_bytes())?.as_slice(), - ) - .await?; + )?; download_file_with_bar( &dest.join(fnames.dictionary), @@ -294,8 +294,7 @@ async fn download_dict( &client, info_dic.1, hex::decode(info_dic.0.as_bytes())?.as_slice(), - ) - .await?; + )?; download_file_with_bar( &dest.join(fnames.license), @@ -303,8 +302,7 @@ async fn download_dict( &client, info_lic.1, hex::decode(info_lic.0.as_bytes())?.as_slice(), - ) - .await?; + )?; // Download each with progress bar // Hash each file @@ -329,19 +327,19 @@ mod tests { fn calculate_git_hash_ok() { // Use example from git help page assert_eq!( - calculate_git_hash("what is up, doc?"), + calculate_git_hash("what is up, doc?".as_bytes()), hex::decode("bd9dbf5aae1a3862dd1526723246b20206e5fc37") .unwrap() .as_slice() ) } - #[tokio::test] - async fn retreive_urls_ok() { + #[test] + fn retreive_urls_ok() { let mocks = mock_server_setup(); let client = make_test_client(); - let urls = retrieve_urls("de-AT", &client).await.unwrap(); + let urls = retrieve_urls("de-AT", &client).unwrap(); // SHA sums joined with files let expected = DownloadInfo { affix: format!( @@ -373,12 +371,12 @@ mod tests { assert_eq!(urls, expected); } - #[tokio::test] - async fn download_dict_ok() { + #[test] + fn download_dict_ok() { let mocks = mock_server_setup(); let dir = tempdir().unwrap(); - let res = download_dict("de-AT", dir.path(), false, &PathBuf::default()).await; + let res = download_dict("de-AT", dir.path(), false, &PathBuf::default()); println!("{res:?}"); res.unwrap(); @@ -476,11 +474,10 @@ mod test_mocks { } } - pub fn make_test_client() -> Client { - Client::builder() + pub fn make_test_client() -> ureq::Agent { + ureq::builder() .timeout(Duration::from_secs(5)) .user_agent(APP_USER_AGENT) .build() - .unwrap() } }