use crate::Fmt;
use path_clean::PathClean;
use std::path::{Path, PathBuf};
pub fn get_available_path(base_path: &Path, is_directory: bool) -> String {
if !base_path.exists() {
return base_path.to_string_lossy().into_owned();
}
let mut i = 1;
let parent = base_path.parent().unwrap_or_else(|| Path::new(""));
let file_name = base_path
.file_stem()
.and_then(|s| s.to_str())
.unwrap_or("");
let ext = base_path
.extension()
.and_then(|s| s.to_str())
.unwrap_or("");
let orig_name = base_path
.file_name()
.and_then(|s| s.to_str())
.unwrap_or("");
loop {
let new_name = if is_directory || ext.is_empty() {
format!("{}({})", orig_name, i)
} else {
format!("{}({}).{}", file_name, i, ext)
};
let new_path = parent.join(&new_name);
if !new_path.exists() {
return new_path.to_string_lossy().into_owned();
}
i += 1;
}
}
pub fn get_default_output(inputs: &[String], input_fmt: Option<Fmt>) -> String {
if inputs.is_empty() {
return get_available_path(&PathBuf::from("archive.zip"), false);
}
if inputs.len() == 1 {
let input_path = Path::new(&inputs[0]).clean();
if let Some(fmt) = input_fmt {
let mut dir_name = input_path
.file_name()
.map(|s| s.to_string_lossy().into_owned())
.unwrap_or_else(|| "archive".to_string());
for ext in fmt.extensions() {
if dir_name.ends_with(ext) {
dir_name = dir_name[..dir_name.len() - ext.len()].to_string();
break;
}
}
let mut base_output = input_path
.parent()
.unwrap_or_else(|| Path::new(""))
.join(dir_name);
if base_output.as_os_str().is_empty() {
base_output = PathBuf::from("archive");
}
return get_available_path(&base_output, true);
}
}
let first_input = Path::new(&inputs[0]).clean();
let parent = first_input.parent().unwrap_or_else(|| Path::new(""));
let base_name = if inputs.len() > 1 {
parent
.file_name()
.map(|s| s.to_string_lossy().into_owned())
.unwrap_or_else(|| "archive".to_string())
} else {
if first_input.is_dir() {
first_input
.file_name()
.map(|s| s.to_string_lossy().into_owned())
.unwrap_or_else(|| "archive".to_string())
} else {
let stem = first_input
.file_stem()
.map(|s| s.to_string_lossy().into_owned())
.unwrap_or_default();
if stem.is_empty() || stem.starts_with('.') {
parent
.file_name()
.map(|s| s.to_string_lossy().into_owned())
.unwrap_or_else(|| "archive".to_string())
} else {
stem
}
}
};
let final_base_name = if base_name.is_empty() {
"archive".to_string()
} else {
base_name
};
let base_output = parent.join(format!("{}.zip", final_base_name));
get_available_path(&base_output, false)
}