use std::path::PathBuf; use std::sync::OnceLock;
#[allow(non_upper_case_globals)]
static POWERLINE_ROOT_CELL: OnceLock<PathBuf> = OnceLock::new();
#[allow(non_upper_case_globals)]
static BINDINGS_DIRECTORY_CELL: OnceLock<PathBuf> = OnceLock::new();
#[allow(non_upper_case_globals)]
static TMUX_CONFIG_DIRECTORY_CELL: OnceLock<PathBuf> = OnceLock::new();
#[allow(non_upper_case_globals)]
static DEFAULT_SYSTEM_CONFIG_DIR_CELL: OnceLock<Option<PathBuf>> = OnceLock::new();
#[allow(non_snake_case)]
pub fn POWERLINE_ROOT() -> &'static PathBuf {
POWERLINE_ROOT_CELL.get_or_init(|| {
std::env::current_exe()
.ok()
.and_then(|p| p.parent().and_then(|p| p.parent()).map(PathBuf::from))
.unwrap_or_else(|| PathBuf::from("."))
})
}
#[allow(non_snake_case)]
pub fn BINDINGS_DIRECTORY() -> &'static PathBuf {
BINDINGS_DIRECTORY_CELL.get_or_init(|| {
POWERLINE_ROOT().join("powerline").join("bindings")
})
}
#[allow(non_snake_case)]
pub fn TMUX_CONFIG_DIRECTORY() -> &'static PathBuf {
TMUX_CONFIG_DIRECTORY_CELL.get_or_init(|| {
let default = BINDINGS_DIRECTORY().join("tmux");
if default.join("powerline-base.conf").exists() {
return default;
}
const BUNDLED: &[(&str, &str)] = &[
(
"powerline-base.conf",
include_str!("bindings/tmux/powerline-base.conf"),
),
(
"powerline.conf",
include_str!("bindings/tmux/powerline.conf"),
),
(
"powerline_tmux_1.7_plus.conf",
include_str!("bindings/tmux/powerline_tmux_1.7_plus.conf"),
),
(
"powerline_tmux_1.8.conf",
include_str!("bindings/tmux/powerline_tmux_1.8.conf"),
),
(
"powerline_tmux_1.8_minus.conf",
include_str!("bindings/tmux/powerline_tmux_1.8_minus.conf"),
),
(
"powerline_tmux_1.8_plus.conf",
include_str!("bindings/tmux/powerline_tmux_1.8_plus.conf"),
),
(
"powerline_tmux_1.9_plus.conf",
include_str!("bindings/tmux/powerline_tmux_1.9_plus.conf"),
),
(
"powerline_tmux_2.1_plus.conf",
include_str!("bindings/tmux/powerline_tmux_2.1_plus.conf"),
),
];
let cache = std::env::var_os("XDG_CACHE_HOME")
.map(PathBuf::from)
.or_else(|| std::env::var_os("HOME").map(|h| PathBuf::from(h).join(".cache")))
.unwrap_or_else(std::env::temp_dir)
.join("powerliners")
.join("tmux");
if std::fs::create_dir_all(&cache).is_ok() {
for (name, content) in BUNDLED {
let target = cache.join(name);
let _ = std::fs::write(&target, content);
}
}
if cache.join("powerline-base.conf").exists() {
return cache;
}
default
})
}
#[allow(non_snake_case)]
pub fn DEFAULT_SYSTEM_CONFIG_DIR() -> &'static Option<PathBuf> {
DEFAULT_SYSTEM_CONFIG_DIR_CELL.get_or_init(|| None) }
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn config_constants_are_consistent() {
let root = POWERLINE_ROOT();
let bindings = BINDINGS_DIRECTORY();
let tmux = TMUX_CONFIG_DIRECTORY();
let system = DEFAULT_SYSTEM_CONFIG_DIR();
assert_eq!(bindings, &root.join("powerline").join("bindings"));
let s = tmux.to_string_lossy();
assert!(
s.ends_with("/tmux") || s.ends_with("\\tmux"),
"TMUX_CONFIG_DIRECTORY should end with /tmux, got {}",
s
);
assert!(system.is_none());
}
}