use crate::error::{Error, Result};
pub fn resolve_optional_base_path(base_path: Option<&str>) -> Option<&str> {
base_path.and_then(|value| (!value.trim().is_empty()).then_some(value.trim()))
}
pub fn join_remote_path(base_path: Option<&str>, path: &str) -> Result<String> {
let path = path.trim();
if path.is_empty() {
return Err(Error::validation_invalid_argument(
"path",
"Path cannot be empty",
None,
None,
));
}
if path.starts_with('/') {
return Ok(path.to_string());
}
let Some(base) = resolve_optional_base_path(base_path) else {
return Err(Error::config_missing_key("base_path", None));
};
if base.ends_with('/') {
Ok(format!("{}{}", base, path))
} else {
Ok(format!("{}/{}", base, path))
}
}
pub fn join_remote_child(base_path: Option<&str>, dir: &str, child: &str) -> Result<String> {
let dir_path = join_remote_path(base_path, dir)?;
let child = child.trim();
if child.is_empty() {
return Err(Error::validation_invalid_argument(
"child",
"Child path cannot be empty",
None,
None,
));
}
if dir_path.ends_with('/') {
Ok(format!("{}{}", dir_path, child))
} else {
Ok(format!("{}/{}", dir_path, child))
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn join_remote_path_allows_absolute_paths_without_base() {
assert_eq!(
join_remote_path(None, "/var/log/syslog").unwrap(),
"/var/log/syslog"
);
}
#[test]
fn join_remote_path_rejects_relative_paths_without_base() {
assert!(join_remote_path(None, "file.json").is_err());
}
#[test]
fn join_remote_path_joins_relative_paths() {
assert_eq!(
join_remote_path(Some("/var/www/site"), "file.json").unwrap(),
"/var/www/site/file.json"
);
assert_eq!(
join_remote_path(Some("/var/www/site/"), "file.json").unwrap(),
"/var/www/site/file.json"
);
}
#[test]
fn join_remote_child_appends_child() {
assert_eq!(
join_remote_child(Some("/var/www/site"), "logs", "error.log").unwrap(),
"/var/www/site/logs/error.log"
);
assert_eq!(
join_remote_child(Some("/var/www/site"), "/var/log", "syslog").unwrap(),
"/var/log/syslog"
);
}
#[test]
fn resolve_optional_base_path_trims_and_rejects_empty() {
assert_eq!(
resolve_optional_base_path(Some(" /var/www ")),
Some("/var/www")
);
assert_eq!(resolve_optional_base_path(Some(" ")), None);
assert_eq!(resolve_optional_base_path(None), None);
}
}