Shortening a path

Is there a crate that has functionality of shortening a path, that is:
/home/user/some_very_long_name/some_very_long_name_1/some_very_long_name_2,
shortens it to for example:
/home/../some_very_long_name_2

It's not clear how you arrived at the short path. What algorithm do you have in mind? The two paths you quoted don't seem equivalent.

This is just example, general idea is to have it shortened.

I agree that it would be helpful to have more context.


If you have a "long" path and want to obtain an equivalent path that is relative to a particular directory, you can use diff_paths from Manishearth's pathdiff crate. For example:

let path_relative_to_dir = pathdiff::path_diffs(long_path, dir);

Note however that path_relative_to_dir will not necessarily be shorter than long_path.

In general, canonicalizing a path is a lossy process. I would be interested in learning why you want to shorten a path.

For display to a human?

Ah, I believe I misunderstood the question. Here's a couple crates that "shorten" paths for display (e.g., in a shell prompt):

Crates like these typically shorten intermediate directory names to the first character. If you would rather retain the first and last components as you suggested, you might be better off writing your own function. Here's how I would do it:

use std::{ffi::OsStr, iter, path::{Path, PathBuf}};

fn shorten_path(path: impl AsRef<Path>) -> PathBuf {
    let mut components = path.as_ref().iter();
    let first = components.next();
    let last = components.last();
    
    first.into_iter()
        .chain(iter::once(OsStr::new("..")))
        .chain(last)
        .collect()
}

Though I would recommend replacing .. with something else to avoid confusion.

2 Likes

Yes