use std::ffi::OsString;
use crate::{
fallible,
os::{Os, Target},
Arch, DesktopEnv, Language, Platform, Result,
};
macro_rules! report_message {
() => {
"Please report this issue at https://github.com/ardaku/whoami/issues"
};
}
const DEFAULT_USERNAME: &str = "Unknown";
const DEFAULT_HOSTNAME: &str = "LocalHost";
#[inline(always)]
pub fn arch() -> Arch {
Target::arch(Os).expect(concat!("arch() failed. ", report_message!()))
}
#[inline(always)]
pub fn username() -> String {
fallible::username().unwrap_or_else(|_| DEFAULT_USERNAME.to_lowercase())
}
#[inline(always)]
pub fn username_os() -> OsString {
fallible::username_os()
.unwrap_or_else(|_| DEFAULT_USERNAME.to_lowercase().into())
}
#[inline(always)]
pub fn realname() -> String {
fallible::realname()
.or_else(|_| fallible::username())
.unwrap_or_else(|_| DEFAULT_USERNAME.to_owned())
}
#[inline(always)]
pub fn realname_os() -> OsString {
fallible::realname_os()
.or_else(|_| fallible::username_os())
.unwrap_or_else(|_| DEFAULT_USERNAME.to_owned().into())
}
#[inline(always)]
pub fn devicename() -> String {
fallible::devicename()
.or_else(|_| fallible::hostname())
.unwrap_or_else(|_| DEFAULT_HOSTNAME.to_string())
}
#[inline(always)]
pub fn devicename_os() -> OsString {
fallible::devicename_os()
.or_else(|_| fallible::hostname().map(OsString::from))
.unwrap_or_else(|_| DEFAULT_HOSTNAME.to_string().into())
}
#[inline(always)]
#[deprecated(note = "use `fallible::hostname()` instead", since = "1.5.0")]
pub fn hostname() -> String {
let mut hostname = fallible::hostname()
.unwrap_or_else(|_| DEFAULT_HOSTNAME.to_lowercase());
hostname.make_ascii_lowercase();
hostname
}
#[inline(always)]
#[deprecated(note = "use `fallible::hostname()` instead", since = "1.5.0")]
pub fn hostname_os() -> OsString {
#[allow(deprecated)]
hostname().into()
}
#[inline(always)]
pub fn distro() -> String {
fallible::distro().unwrap_or_else(|_| format!("Unknown {}", platform()))
}
#[inline(always)]
#[deprecated(note = "use `distro()` instead", since = "1.5.0")]
pub fn distro_os() -> OsString {
fallible::distro()
.map(OsString::from)
.unwrap_or_else(|_| format!("Unknown {}", platform()).into())
}
#[inline(always)]
pub fn desktop_env() -> DesktopEnv {
Target::desktop_env(Os)
}
#[inline(always)]
pub fn platform() -> Platform {
Target::platform(Os)
}
#[inline(always)]
#[deprecated(note = "use `langs()` instead", since = "1.5.0")]
pub fn lang() -> impl Iterator<Item = String> {
let langs_vec = if let Ok(langs) = langs() {
langs
.map(|lang| lang.to_string().replace('/', "-"))
.collect()
} else {
["en-US".to_string()].to_vec()
};
langs_vec.into_iter()
}
#[inline(always)]
pub fn langs() -> Result<impl Iterator<Item = Language>> {
let langs = Target::langs(Os)?;
let langs = langs
.split(':')
.map(ToString::to_string)
.filter_map(|lang| {
let lang = lang
.split_terminator('.')
.next()
.unwrap_or_default()
.replace(|x| ['_', '-'].contains(&x), "/");
if lang == "C" {
return None;
}
Some(Language::__(Box::new(lang)))
});
Ok(langs.collect::<Vec<_>>().into_iter())
}