diff --git a/pttodoer/src/main.rs b/pttodoer/src/main.rs index 0dda5a6..2925869 100644 --- a/pttodoer/src/main.rs +++ b/pttodoer/src/main.rs @@ -63,7 +63,7 @@ impl Flags { } } -#[derive(Debug)] +#[derive(Debug, PartialEq)] pub struct DB(Vec); impl DB { @@ -98,6 +98,10 @@ impl DB { Ok(DB(result)) } + fn new_empty() -> DB { + DB{0: vec![]} + } + pub fn incomplete(&self) -> Tasks { let mut result = Tasks::new(); for set in &self.0 { @@ -115,6 +119,19 @@ impl DB { } pub fn edit(&self) -> Result { + self._edit(|cwd: &String| { + std::process::Command::new("/bin/sh") + .current_dir(cwd) + .arg("-c") + .arg("vim -p ./*") + .spawn() + .expect("failed to start vim") + .wait() + .expect("failed to vim"); + }) + } + + fn _edit(&self, edit: impl Fn(&String)) -> Result { let d = TempDir::new(&TS::now().to_string()).expect("failed to create a temp dir"); for set in &self.0 { let base = set.file.split("/").last().unwrap().to_string(); @@ -123,19 +140,11 @@ impl DB { } loop { - std::process::Command::new("/bin/sh") - .current_dir(d.path()) - .arg("-c") - .arg("vim -p ./*") - .spawn() - .expect("failed to start vim") - .wait() - .expect("failed to vim"); + let cwd = d.path().display().to_string(); + edit(&cwd); let mut ok = true; - for set in &self.0 { - let base = set.file.split("/").last().unwrap().to_string(); - let f = d.path().join(base); - ok = ok && TasksAndMetadata::new(f.display().to_string()).is_ok(); + for f in std::fs::read_dir(&cwd).expect("failed to list edited files") { + ok = ok && TasksAndMetadata::new(f.expect("failed to list edited file").path().display().to_string()).is_ok(); } if ok { break; @@ -143,9 +152,10 @@ impl DB { } let mut result = vec![]; - for set in &self.0 { - let base = set.file.split("/").last().unwrap().to_string(); - let f = d.path().join(base); + for f in std::fs::read_dir(d.path()).expect("failed to list edited files") { + let f = f.expect("failed to list edited file"); + let base = f.path().display().to_string().split("/").last().unwrap().to_string(); + let set = match{ TODO find self.0.find(path.base(f)) OR init TasksAndMetadata{} } let edited = TasksAndMetadata::new(f.display().to_string()).expect("failed to read edited tasks"); @@ -208,9 +218,53 @@ impl DB { } #[cfg(test)] -mod test_taskss { +mod test_db { use super::*; + #[test] + fn edit_insert_empty() { + let db = new_test_db(0, 0); + let db_after = db._edit(|cwd| { + assert_eq!(0, std::fs::read_dir(cwd).expect("failed to ls cwd").collect::>().len()); + assert_ne!("", cwd); + + let mut f = std::fs::File::create(format!("{}/f", cwd)).expect("failed to open a file in cwd"); + f.write_all(b"f").expect("failed to write a file in cwd"); + + let mut g = std::fs::File::create(format!("{}/g", cwd)).expect("failed to open a file in cwd"); + g.write_all(b"g: h").expect("failed to write a file in cwd"); + }).expect("failed to not edit"); + assert_eq!(2, db.0.len()); + assert_eq!(1, db.0[0].tasks.len()); + assert_eq!(1, db.0[1].tasks.len()); + assert_ne!(db, db_after); + } + + #[test] + fn edit_noop_empty() { + let db = new_test_db(0, 0); + let db_after = db._edit(|_| {}).expect("failed to not edit"); + assert_eq!(0, db.0.len()); + assert_eq!(db, db_after); + } + + fn new_test_db(files: i32, tasks_per_file: i32) -> DB { + let mut db = DB::new_empty(); + + for i in 0..files { + let mut tasks = Tasks::new(); + for j in 0..tasks_per_file { + tasks.0.push(Task::from_string(format!("{{\"hello\": \"world[{}]\"}}", j))); + } + db.0.push(TasksAndMetadata::new_with( + format!("{}.yaml", i), + TS::now(), + tasks, + )); + } + db + } + #[test] fn read_dir_files() { let db = DB::new("./src/testdata/taskss.d/files.d".to_string()).expect("failed to construct from dir of files"); @@ -236,7 +290,7 @@ mod test_taskss { } } -#[derive(Debug, Clone)] +#[derive(Debug, Clone, PartialEq)] pub struct TasksAndMetadata { tasks: Tasks, file: String, @@ -329,7 +383,7 @@ fn file_version(file: String) -> Result { } } -#[derive(Debug, serde::Serialize, serde::Deserialize, Clone)] +#[derive(Debug, serde::Serialize, serde::Deserialize, Clone, PartialEq)] pub struct Tasks(Vec); impl Tasks {