Skip to content

Instantly share code, notes, and snippets.

@devnote-dev
Last active October 5, 2023 01:42
Show Gist options
  • Save devnote-dev/e8388919ad85dd9a1619b462e7c4a608 to your computer and use it in GitHub Desktop.
Save devnote-dev/e8388919ad85dd9a1619b462e7c4a608 to your computer and use it in GitHub Desktop.

Revisions

  1. devnote-dev renamed this gist Oct 5, 2023. 1 changed file with 0 additions and 0 deletions.
    File renamed without changes.
  2. devnote-dev created this gist Oct 5, 2023.
    82 changes: 82 additions & 0 deletions main.rs
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,82 @@
    // Bigstat
    // (c) 2023 Devonte W <https://github.com/devnote-dev>
    //
    // Dependencies:
    // bytesize = "1.3.0"
    // fibers = "0.1"
    // futures = "0.1"

    use bytesize::ByteSize;
    use fibers::{Executor, Spawn, ThreadPoolExecutor};
    use futures::future::err;
    use std::{env, fs, path::Path, process::exit};

    fn recurse_dir<P: AsRef<Path>>(p: P) -> (u64, u64) {
    let dir = fs::read_dir(p);
    if dir.is_err() {
    return (0, 0);
    }

    let mut files: u64 = 0;
    let mut size: u64 = 0;

    for path in dir.unwrap() {
    let entry = path.unwrap();
    let meta = entry.metadata().unwrap();

    if meta.is_file() {
    files += 1;
    size += meta.len();
    } else if meta.is_dir() {
    let (f, s) = recurse_dir(entry.path());
    files += f;
    size += s;
    }
    }

    (files, size)
    }

    fn main() {
    let args = env::args();
    if args.len() == 1 {
    eprintln!("err: no directories specified");
    exit(1);
    }

    let mut paths = Vec::new();
    for arg in args.skip(1) {
    if fs::metadata(&arg).is_ok() {
    paths.push(arg);
    } else {
    println!("warn: path {arg} not found")
    }
    }

    if paths.is_empty() {
    exit(1);
    }

    let executor = ThreadPoolExecutor::new().unwrap();

    for path in paths {
    let meta = fs::metadata(&path).unwrap();

    if meta.is_file() {
    println!("{}: {}", &path, ByteSize(meta.len()));
    continue;
    }

    if meta.is_dir() {
    executor.handle().spawn(futures::lazy(move || {
    let (files, size) = recurse_dir(&path);
    println!("{}: {} ({} files)", &path, ByteSize(size), files);

    Ok(())
    }));
    }
    }

    executor.handle().spawn(futures::lazy(|| err::<(), ()>(())));
    executor.run().unwrap();
    }