use std::fs;
use std::path::{Path, PathBuf};
use std::time::SystemTime;
use crate::{cli, config};
use super::file_ops::compute_blake3_hash;
use std::sync::Arc;
#[derive(Debug, Clone)]
pub struct FileInfo {
pub path: Arc<Path>,
pub mtime: SystemTime,
pub size: u64,
pub blake3_hash: Option<[u8; 32]>,
}
impl FileInfo {
pub fn from_path(path: &Path, compute_hash: bool) -> std::io::Result<Self> {
let metadata = fs::metadata(path)?;
let blake3_hash = if compute_hash && metadata.is_file() {
Some(compute_blake3_hash(path)?)
} else {
None
};
Ok(FileInfo {
path: Arc::from(path), mtime: metadata.modified()?,
size: metadata.len(),
blake3_hash,
})
}
pub fn is_newer_than(&self, target: &Self) -> bool {
self.mtime > target.mtime || self.size != target.size
}
pub fn content_eq(&self, other: &Self) -> bool {
self.size == other.size && self.blake3_hash == other.blake3_hash
}
}
#[derive(Debug, Clone)]
pub struct SyncParameters {
pub source: PathBuf,
pub target: PathBuf,
pub dry_run: bool,
pub checksum: bool,
pub excludes: Vec<String>,
pub delete_extra: bool,
pub delete_excludes: Vec<String>,
pub detail: bool,
}
impl From<&cli::Command> for SyncParameters {
fn from(cmd: &cli::Command) -> Self {
match cmd {
cli::Command::Sync {
source,
target,
dry_run,
checksum,
delete,
exclude,
delete_exclude,
detail,
} => Self {
source: source.clone(),
target: target.clone(),
dry_run: *dry_run,
checksum: *checksum,
excludes: exclude.clone(),
delete_extra: *delete,
delete_excludes: delete_exclude.clone(),
detail: *detail,
},
cli::Command::Run {
name: _,
config: _,
dry_run,
checksum,
detail,
} => {
Self {
source: PathBuf::new(),
target: PathBuf::new(),
dry_run: *dry_run,
checksum: *checksum,
excludes: Vec::new(),
delete_extra: false,
delete_excludes: Vec::new(),
detail: *detail,
}
}
cli::Command::Watch {
name: _,
config: _,
delay: _,
checksum,
dry_run,
detail,
} => Self {
source: PathBuf::new(),
target: PathBuf::new(),
dry_run: *dry_run,
checksum: *checksum,
excludes: Vec::new(),
delete_extra: false,
delete_excludes: Vec::new(),
detail: *detail,
}
}
}
}
impl From<&config::SyncTask> for SyncParameters {
fn from(task: &config::SyncTask) -> Self {
Self {
source: task.source.clone(),
target: task.target.clone(),
dry_run: false, checksum: false, excludes: task.exclude.clone(),
delete_extra: task.delete_extra,
delete_excludes: task.delete_extra_exclude.clone(),
detail: false,
}
}
}