#walk #fast #scandir

scandir

A fast file tree scanner written in Rust

12 stable releases

Uses new Rust 2024

2.76.0 Apr 15, 2024
2.9.3 Mar 28, 2025
2.9.2 Jan 27, 2025
2.8.0 Oct 26, 2024
2.4.1 Feb 10, 2024

#70 in Machine learning

Download history 310/week @ 2025-01-27 25/week @ 2025-02-03 6/week @ 2025-02-10 4/week @ 2025-02-17 2/week @ 2025-02-24 3/week @ 2025-03-03 115/week @ 2025-03-24 19/week @ 2025-03-31 10/week @ 2025-04-07

144 downloads per month
Used in 2 crates

MIT and CC-PDDC licenses

75KB
2K SLoC

scandir

The Rust crate is called scandir and installable via cargo. On Linux it is 1.5 - 2.9 times faster and on Windows 1.5 - 5.4 time faster (see benchmarks).

If you are just interested in directory statistics you can use the Count.

scandir_rs contains following classes:

  • Count for determining statistics of a directory.
  • Walk for getting names of directory entries.
  • Scandir for getting detailed stats of directory entries.

For the API see:

Examples

Collect examples:

use scandir::Count;

// collect() starts the worker thread and waits until it has finished. The line below is blocking.
println!(Count::new("/usr")?.collect()?);
// Get extended statistics
println!(Count::new("/usr", return_type=ReturnType.Ext)?.collect()?);

The same, but asynchronously in background using a class instance:

use scandir::Count;

let mut instance = Count::new("/usr", return_type=ReturnType.Ext);
instance.start();  // Start scanning the directory
...
let values = instance.results();  // Returns the current statistics. Can be read at any time
...
if instance.busy() {  // Check if the task is still running.
...
instance.stop();  // If you want to cancel the task
...
instance.join();  // Wait for the instance to finish.
let mut instance = Count::new(&path)?;
instance.start()?;
loop {
    if !instance.busy() {
        break;
    }
    // Do something
    thread::sleep(Duration::from_millis(10));
}
// collect() immediately returns because the worker thread has already finished.
let statistics = instance.collect()?;

Walk example:

use scandir::Walk;

// Get basic file tree
println!(Walk::new("/usr")?.collect()?);
// Get file tree with extended file type identification. This is slower.
println!(Walk::new("/usr", return_type=ReturnType.Ext)?.collect()?);

If you want to have intermediate results, e.g. you want to show the progress to the user, the use the example below.

let mut instance = Walk::new(&path, None)?;
instance.start()?;
loop {
    if !instance.busy() {
        break;
    }
    let new_results = instance.results(true);
    // Do something
    thread::sleep(Duration::from_millis(10));
}
// collect() immediately returns because the worker thread has already finished.
let results = instance.collect()?;

Scandir example:

use scandir::Scandir;

// Get basic file metadata
println!(Scandir::new("/usr")?.collect()?);
// Get extended file metadata
println!(Scandir::new("/usr", return_type=ReturnType.Ext, None)?.collect()?);

If you want to have intermediate results, e.g. you want to show the progress to the user, the use the example below.

let mut instance = Scandir::new(&path, None)?;
instance.start()?;
loop {
    if !instance.busy() {
        break;
    }
    let new_results = instance.results(true);
    // Do something
    thread::sleep(Duration::from_millis(10));
}
// collect() immediately returns because the worker thread has already finished.
let results = instance.collect()?;

Dependencies

~2.3–3.5MB
~71K SLoC