From efc97800b2622e9ba5f69e48d8f1595caba0ca7d Mon Sep 17 00:00:00 2001 From: Joscha Date: Sat, 8 Jan 2022 04:11:55 +0100 Subject: [PATCH] Remove empty logs --- src/files.rs | 28 ++++++++++++++++++++++------ src/files/format.rs | 27 +++++++++++++++++++-------- 2 files changed, 41 insertions(+), 14 deletions(-) diff --git a/src/files.rs b/src/files.rs index 007ad63..98b0f94 100644 --- a/src/files.rs +++ b/src/files.rs @@ -28,6 +28,11 @@ struct LoadedFile { file: File, /// Whether this file has been changed. dirty: bool, + /// Commands that have been removed and are to be skipped during formatting. + /// + /// They are not directly removed from the list of commands in order not to + /// change other commands' indices. + removed: HashSet, } impl LoadedFile { @@ -37,6 +42,7 @@ impl LoadedFile { cs_id, file, dirty: false, + removed: HashSet::new(), } } } @@ -292,7 +298,7 @@ impl Files { fn save_file(file: &LoadedFile) -> Result<()> { // TODO Sort commands within file - let formatted = format!("{}", file.file); + let formatted = file.file.format(&file.removed); if file.file.contents == formatted { println!("Unchanged file {:?}", file.name); } else { @@ -382,6 +388,12 @@ impl Files { file.dirty = true; } + fn remove(&mut self, source: Source) { + let file = &mut self.files[source.file]; + file.removed.insert(source.command); + file.dirty = true; + } + /// Add a [`Done`] statement to the task identified by `source`. /// /// Returns whether the addition was successful. It can fail if the entry @@ -399,11 +411,15 @@ impl Files { pub fn set_log(&mut self, date: NaiveDate, desc: Vec) { if let Some(source) = self.logs.get(&date).cloned() { - self.modify(source, |command| match command { - Command::Log(log) => log.desc = desc, - _ => unreachable!(), - }); - } else { + if desc.is_empty() { + self.remove(source); + } else { + self.modify(source, |command| match command { + Command::Log(log) => log.desc = desc, + _ => unreachable!(), + }); + } + } else if !desc.is_empty() { let file = self .latest_log_before(date) .or_else(|| self.latest_log()) diff --git a/src/files/format.rs b/src/files/format.rs index 4274a2a..ddc37fc 100644 --- a/src/files/format.rs +++ b/src/files/format.rs @@ -1,3 +1,4 @@ +use std::collections::HashSet; use std::fmt; use chrono::Datelike; @@ -317,21 +318,31 @@ impl fmt::Display for Log { } } -impl fmt::Display for File { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - for i in 0..self.commands.len() { - let curr = &self.commands[i]; - let next = self.commands.get(i + 1); +impl File { + pub fn format(&self, removed: &HashSet) -> String { + let mut result = String::new(); - write!(f, "{}", curr)?; + let commands = self + .commands + .iter() + .enumerate() + .filter(|(i, _)| !removed.contains(i)) + .map(|(_, c)| c) + .collect::>(); + + for i in 0..commands.len() { + let curr = commands[i]; + let next = commands.get(i + 1).copied(); + + result.push_str(&format!("{}", curr)); match (curr, next) { (Command::Include(_), Some(Command::Include(_))) => {} (_, None) => {} - _ => writeln!(f)?, + _ => result.push('\n'), } } - Ok(()) + result } }