use indexmap::IndexMap;
use log::error;
use std::process::exit;
use crate::cli::Config;
use crate::gps::base::GpsResolutionProvider;
use crate::gps::gpsenum::GpsResolutionProviderImpl;
use crate::gps::nominatim::Nominatim;
use crate::organizer::CopyStrategy;
use crate::organizer::MoveStrategy;
use crate::organizer::OrganizationMode;
use crate::organizer::OrganizationStrategy;
use crate::organizer::SymlinksStrategy;
use crate::{errors::ClineupError, placeholders::Placeholder};
use path_clean::{clean, PathClean};
use std::path::Path;
use std::path::PathBuf;
pub fn is_there_a_exif_placeholder(
placeholders: &IndexMap<String, IndexMap<String, Placeholder>>,
) -> bool {
let mut is_there_a_date_placeholder = false;
for _placeholders in placeholders.values() {
for _placeholder in _placeholders.values() {
if _placeholder.is_exif_related() {
is_there_a_date_placeholder = true;
break;
}
}
}
is_there_a_date_placeholder
}
pub fn is_there_a_metadata_placeholder(
placeholders: &IndexMap<String, IndexMap<String, Placeholder>>,
) -> bool {
let mut is_there_a_metadata_placeholder = false;
for _placeholders in placeholders.values() {
for _placeholder in _placeholders.values() {
if _placeholder.is_os_related() {
is_there_a_metadata_placeholder = true;
break;
}
}
}
is_there_a_metadata_placeholder
}
pub fn is_there_a_location_placeholder(
placeholders: &IndexMap<String, IndexMap<String, Placeholder>>,
) -> bool {
let mut is_there_a_location_placeholder = false;
for _placeholders in placeholders.values() {
for _placeholder in _placeholders.values() {
if _placeholder.is_location_related() {
is_there_a_location_placeholder = true;
break;
}
}
}
is_there_a_location_placeholder
}
pub fn print_error<T>(e: ClineupError) -> T {
error!("{e}");
exit(1)
}
pub fn get_full_format_path(
folder_format: Option<&String>,
filename_format: Option<&String>,
) -> Option<String> {
let mut full_format: Option<PathBuf> = None;
if let Some(_folder_format) = folder_format {
let mut _full_format = Path::new(&_folder_format).to_path_buf().clean();
if let Some(_filename_format) = filename_format {
_full_format = _full_format.join(_filename_format);
full_format = Some(_full_format);
} else {
_full_format = _full_format.join("{%original_filename}");
full_format = Some(_full_format);
}
} else if let Some(_filename_format) = filename_format {
full_format = Some(Path::new(&_filename_format).to_path_buf().clean());
}
full_format.map(|path| path.to_string_lossy().to_string())
}
pub fn get_reverse_geocoding(config: &Config) -> Option<Box<dyn GpsResolutionProvider>> {
match &config.reverse_geocoding {
Some(provider) => match provider {
GpsResolutionProviderImpl::Nominatim => {
if config.nominatim_email.is_none() {
println!("Nominatim email is required when using Nominatim as a reverse geocoding provider.");
exit(1)
}
Some(Box::new(Nominatim::new(
config.nominatim_email.clone().unwrap(),
)))
}
},
None => None,
}
}
pub fn get_organization_strategy(
strategy: Option<&OrganizationMode>,
) -> Option<Box<dyn OrganizationStrategy>> {
match strategy {
Some(org_mode) => match org_mode {
OrganizationMode::Copy => Some(Box::new(CopyStrategy::new())),
OrganizationMode::Symlinks => Some(Box::new(SymlinksStrategy::new())),
OrganizationMode::Move => Some(Box::new(MoveStrategy::new())),
},
None => None,
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn test_get_full_format_path() {
assert_eq!(get_full_format_path(None, None), None);
assert_eq!(
get_full_format_path(Some(&String::from("path/to/folder")), None),
Some(String::from("path/to/folder/{%original_filename}"))
);
assert_eq!(
get_full_format_path(None, Some(&String::from("file.txt"))),
Some(String::from("file.txt"))
);
assert_eq!(
get_full_format_path(
Some(&String::from("path/to/folder")),
Some(&String::from("file.txt"))
),
Some(String::from("path/to/folder/file.txt"))
);
assert_eq!(
get_full_format_path(None, Some(&String::from("%original_filename"))),
Some(String::from("%original_filename"))
);
assert_eq!(
get_full_format_path(
Some(&String::from("path/to/folder")),
Some(&String::from("%original_filename"))
),
Some(String::from("path/to/folder/%original_filename"))
);
}
#[test]
fn test_get_organization_strategy_copy() {
let strategy = OrganizationMode::Copy;
let result = get_organization_strategy(Some(&strategy));
assert!(result.is_some());
}
#[test]
fn test_get_organization_strategy_symlinks() {
let strategy = OrganizationMode::Symlinks;
let result = get_organization_strategy(Some(&strategy));
assert!(result.is_some());
}
#[test]
fn test_get_organization_strategy_move() {
let strategy = OrganizationMode::Move;
let result = get_organization_strategy(Some(&strategy));
assert!(result.is_some());
}
#[test]
fn test_get_organization_strategy_none() {
let result = get_organization_strategy(None);
assert!(result.is_none());
}
}