From a7213ed931f2504902c3d7378d4423a9984f8635 Mon Sep 17 00:00:00 2001 From: Stefan Kreutz Date: Mon, 19 Dec 2022 18:02:18 +0100 Subject: Add recursive SHA256 example application --- examples/.gitignore | 2 ++ examples/Cargo.toml | 3 ++ examples/recursive-sha256/Cargo.toml | 10 +++++++ examples/recursive-sha256/src/main.rs | 55 +++++++++++++++++++++++++++++++++++ 4 files changed, 70 insertions(+) create mode 100644 examples/.gitignore create mode 100644 examples/Cargo.toml create mode 100644 examples/recursive-sha256/Cargo.toml create mode 100644 examples/recursive-sha256/src/main.rs (limited to 'examples') diff --git a/examples/.gitignore b/examples/.gitignore new file mode 100644 index 0000000..4fffb2f --- /dev/null +++ b/examples/.gitignore @@ -0,0 +1,2 @@ +/target +/Cargo.lock diff --git a/examples/Cargo.toml b/examples/Cargo.toml new file mode 100644 index 0000000..4f10fc3 --- /dev/null +++ b/examples/Cargo.toml @@ -0,0 +1,3 @@ +[workspace] +members = ["*"] +exclude = ["target"] diff --git a/examples/recursive-sha256/Cargo.toml b/examples/recursive-sha256/Cargo.toml new file mode 100644 index 0000000..38ed665 --- /dev/null +++ b/examples/recursive-sha256/Cargo.toml @@ -0,0 +1,10 @@ +[package] +name = "example-recursive-sha256" +version = "0.1.0" +edition = "2021" +publish = false + +[dependencies] +parseq = { path = "../.." } +sha2 = "0.10.6" +walkdir = "2.3.2" diff --git a/examples/recursive-sha256/src/main.rs b/examples/recursive-sha256/src/main.rs new file mode 100644 index 0000000..6fcbbfa --- /dev/null +++ b/examples/recursive-sha256/src/main.rs @@ -0,0 +1,55 @@ +//! Print the SHA256 sum of each regular file in the current directory recursively. + +use std::{fs::File, path::PathBuf}; + +use parseq::ParallelIterator; +use sha2::{Digest, Sha256}; +use walkdir::WalkDir; + +fn main() { + WalkDir::new(".") + .sort_by_file_name() + .into_iter() + .filter_map(|entry| match entry { + Ok(entry) if entry.file_type().is_file() => Some(Ok(entry.into_path())), + Ok(_) => None, + Err(err) => Some(Err(Error::WalkdirError(err))), + }) + .map_parallel(|item| { + item.and_then(|path| { + let mut file = + File::open(&path).map_err(|err| Error::IoError(path.clone(), err))?; + let mut hasher = Sha256::new(); + std::io::copy(&mut file, &mut hasher) + .map_err(|err| Error::IoError(path.clone(), err))?; + Ok((path, hasher.finalize())) + }) + }) + .for_each(|item| match item { + Ok((path, hash)) => println!("{:x} {}", hash, path.display()), + Err(err) => eprintln!("{err}"), + }); +} + +#[derive(Debug)] +enum Error { + WalkdirError(walkdir::Error), + IoError(PathBuf, std::io::Error), +} + +impl std::error::Error for Error {} + +impl std::fmt::Display for Error { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + match self { + Error::WalkdirError(err) => { + if let Some(path) = err.path() { + write!(f, "{}: {}", path.display(), err) + } else { + write!(f, "{err}") + } + } + Error::IoError(path, err) => write!(f, "{}: {}", path.display(), err), + } + } +} -- cgit v1.2.3