A pure-Rust crate for determining user home directories via environment variables in a platform independent manner with no external dependencies.
Check HOME
on Unix and USERPROFILE
on Windows.
env_home is a general purpose crate for determining the current user home directory via environment variables.
It can be used as drop-in replacement for
std::env::home_dir
(deprecated)
from the rust standard library.
Unlike std::env::home_dir
this crate only looks at environment variables
and does attempt to fallback on platform specific APIs. As a result implementation
of env_home_dir
is very simple with no dependencies on other crates.
This functionality is comparable to Golang's os.UserHomeDir() or Python's Path.home().
The API of this crate is a single function env_home_dir
which attempts to fetch a user's home directory from environment variables
in a platform independent way supporting Windows and Unix (Linux/MacOS/BSD/WSL, etc).
Platform | Environment Variable | Example |
---|---|---|
MacOS, Linux or other Unix | HOME |
/home/user |
Windows Subsystem for Linux (WSL) | HOME |
/home/user |
Windows Native | USERPROFILE |
C:\\Users\\user |
Others (WASM, etc) | N/A | None |
- If the environment variable is unset,
None
is returned. - If the environment variable is set to an empty string,
None
is returned. - On non-unix / non-windows platforms (like WASM) that don't implement
a home directory
None
will be returned. - If the environment variable is set to a non-empty string, the value is returned as a
PathBuf
.
That's it.
If you need a more full-service crate consider using the dirs crate.
cargo add env_home
Crate exports a single function env_home_dir
that returns Option<PathBuf>
use env_home::env_home_dir as home_dir;
fn main() {
match home_dir() {
Some(path) => eprintln!("User home directory: {}", path.display()),
None => eprintln!("No home found. HOME/USERPROFILE not set or empty"),
}
}
See the std::path::PathBuf documentation
for more information on how to use PathBuf
objects.
env_home_dir returns None
instead of ""
when HOME
or USERPROFILE
is set to an empty string.
I believe
std::env::home_dir
was trying to be too smart. It calls Platform specific APIs like
(GetUserProfileDirectoryW
on Windows or getpwuid_r on Unix
as a fallback when HOME
or USERPROFILE
environment variables are not set.
We just give up and return None
.
This crate exists because the behavior of
home_dir
provided by the standard library may be unexpected on Windows.
And thus was
deprecated
and has remained broken / unfixed since Rust 1.29.0 (Sept 2018).
Although many projects have switched from std::env::home_dir
to home::home_dir
provided
by the home crate because it was maintained by the cargo team
and thus presumably more "official". The Cargo team has clarified that the home
crate is
not intended for general use:
"the cargo team doesn't want to take on the maintenance of home as a general-purpose crate for the community" [...] "we are thinking of documenting that home is not intended for anything but use inside of cargo and rustup, and suggest people use some other crate instead." source
As a result the home
crate refuses to compile for WASM target and they have have no plans to fix this.
env_home crate implements a fallback no-op which returns None
on non-windows / non-unix platforms like WASM.
Using std::env::set_var to alter your environment at runtime is unsafe in multi-threaded applications. Full stop. It may result in random panics or undefined behavior. You have have been warned.
Bonus: cargo runs tests in parallel threads by-default, so even if you app is not multi-threaded
if you have tests that invoke std::env::set_var
be sure to set RUST_TEST_THREADS=1
or use cargo test -- --test-threads=1
or your tests may intermittently panic and fail.
See rust-lang/rust#27970 and Setenv is not Thread Safe and C Doesn't Want to Fix It for more.
Copyright (c) 2024 Peter Tripp
This project is licensed under the MIT License or Apache License, Version 2.0 at your option.