diff --git a/src/nex.rs b/src/nex.rs index eac2c48..cd2146c 100644 --- a/src/nex.rs +++ b/src/nex.rs @@ -68,8 +68,7 @@ impl Nex { }) } - // Sync the Snac post with the Nex entry - // * @TODO apply the post time to the files + // Sync Snac post with Nex entry pub fn sync( &self, name: &str, @@ -130,11 +129,12 @@ impl Nex { // if this meta file exists and has timestamp changed, also cleanup attachment files to update let mut s = PathBuf::from(&d); s.push(".state"); - let state = updated.unwrap_or(published).to_string(); + let timestamp = updated.unwrap_or(published); + let state = timestamp.to_string(); if !fs::read_to_string(&s).is_ok_and(|this| this == state) { fs::remove_dir_all(&d)?; fs::create_dir_all(&d)?; - fs::write(&s, state)? + save(&s, timestamp.into(), state.as_bytes())? } else { if let Some(ref mut i) = index { if let Some(ref a) = attachments { @@ -159,52 +159,55 @@ impl Nex { } else { Change::Created }; - fs::write( + save( &f, - self.template.build( - updated, - content, - link, - tags, - attachments.map(|a| { - let mut b = Vec::with_capacity(a.len()); - for (n, (name, media_type, source)) in a.into_iter().enumerate() { - b.push(( - match source { - Source::Url(url) => url, - Source::File(from) => { - let to = attachment::filepath(&d, &from, n); - let uri = format!( - "{}/{}", - d.file_name().unwrap().to_string_lossy(), - to.file_name().unwrap().to_string_lossy() - ); - self.attachment.sync(&from, &to).unwrap(); - if let Some(ref mut i) = index { - i.push(to); + timestamp.into(), + self.template + .build( + updated, + content, + link, + tags, + attachments.map(|a| { + let mut b = Vec::with_capacity(a.len()); + for (n, (name, media_type, source)) in a.into_iter().enumerate() { + b.push(( + match source { + Source::Url(url) => url, + Source::File(from) => { + let to = attachment::filepath(&d, &from, n); + let uri = format!( + "{}/{}", + d.file_name().unwrap().to_string_lossy(), + to.file_name().unwrap().to_string_lossy() + ); + self.attachment.sync(&from, &to, timestamp.into()).unwrap(); + if let Some(ref mut i) = index { + i.push(to); + } + uri } - uri - } - }, - { - let mut alt = Vec::with_capacity(2); - if !name.is_empty() { - alt.push(name) - } - if !media_type.is_empty() { - alt.push(format!("({media_type})")) - } - if alt.is_empty() { - None - } else { - Some(alt.join(" ")) - } - }, - )) - } - b - }), - ), + }, + { + let mut alt = Vec::with_capacity(2); + if !name.is_empty() { + alt.push(name) + } + if !media_type.is_empty() { + alt.push(format!("({media_type})")) + } + if alt.is_empty() { + None + } else { + Some(alt.join(" ")) + } + }, + )) + } + b + }), + ) + .as_bytes(), )?; // move all paths processed to cleanup ignore @@ -263,3 +266,12 @@ impl Nex { self.is_cleanup } } + +/// Wrapper function to change time updated for new file, according to the Snac time. +fn save(path: &PathBuf, modified: std::time::SystemTime, data: &[u8]) -> Result<()> { + use std::io::Write; + let mut f = fs::File::create(path)?; + f.write_all(data)?; + f.set_modified(modified)?; // it's important to call after write + Ok(()) +} diff --git a/src/nex/attachment.rs b/src/nex/attachment.rs index 18006d9..47c7d83 100644 --- a/src/nex/attachment.rs +++ b/src/nex/attachment.rs @@ -1,5 +1,8 @@ use anyhow::{Result, bail}; -use std::path::{Path, PathBuf}; +use std::{ + path::{Path, PathBuf}, + time::SystemTime, +}; pub enum Attachment { Copy, @@ -20,11 +23,12 @@ impl Attachment { None => Self::Disabled, }) } - pub fn sync(&self, source: &PathBuf, target: &PathBuf) -> Result<()> { + pub fn sync(&self, source: &PathBuf, target: &PathBuf, modified: SystemTime) -> Result<()> { use std::{fs, os}; match self { Attachment::Copy => { fs::copy(source, target)?; + fs::File::open(target)?.set_modified(modified)?; #[cfg(any(target_os = "linux", target_os = "macos"))] { use std::{fs::Permissions, os::unix::fs::PermissionsExt};