Skip to content

Commit

Permalink
test: file monitoring
Browse files Browse the repository at this point in the history
  • Loading branch information
Teajey committed Nov 29, 2023
1 parent fcfbecc commit acf4a08
Show file tree
Hide file tree
Showing 2 changed files with 202 additions and 0 deletions.
31 changes: 31 additions & 0 deletions .github/workflows/rust.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
name: Rust

on:
push:
branches: ["main"]
pull_request:
branches: ["main"]

env:
CARGO_TERM_COLOR: always
RUST_FLAGS: "-Dwarnings"

jobs:
test:
runs-on: ubuntu-20.04

steps:
- uses: actions/checkout@v3
- name: Cache
uses: actions/[email protected]
with:
path: |
~/.cargo
target
key: build-${{ runner.os }}
restore-keys: |
build-${{ runner.os }}
- name: Lint
run: cargo clippy --all-targets
- name: Test
run: cargo test
171 changes: 171 additions & 0 deletions src/frontmatter_file/keeper.rs
Original file line number Diff line number Diff line change
Expand Up @@ -156,3 +156,174 @@ impl notify::EventHandler for ArcMutex {
}
}

#[cfg(test)]
mod test {
use std::io::Write;

use camino::Utf8PathBuf;
use notify::{EventHandler, RecursiveMode, Watcher};

use super::{ArcMutex, Keeper};

struct TestFile {
path: Utf8PathBuf,
}

impl TestFile {
fn generate(&self) -> std::io::Result<()> {
let _ = std::fs::File::create(&self.path)?;
Ok(())
}

fn write<T: std::fmt::Display>(&self, str: T) -> std::io::Result<()> {
let mut file = std::fs::OpenOptions::new()
.write(true)
.append(true)
.open(&self.path)?;

write!(file, "{str}")?;

Ok(())
}

fn delete(&self) -> std::io::Result<()> {
std::fs::remove_file(&self.path)
}
}

impl Drop for TestFile {
fn drop(&mut self) {
if self.path.exists() {
std::fs::remove_file(&self.path).unwrap();
}
}
}

#[test]
#[allow(clippy::too_many_lines)]
fn file_monitoring() {
let test_file_name = "test.md";
let wd = Utf8PathBuf::try_from(std::env::temp_dir()).unwrap();
let test_file_path = wd.join(test_file_name);
let test_file = TestFile {
path: test_file_path,
};
let keeper = ArcMutex::new(Keeper::new(&wd).unwrap());

let (tx, rx) = std::sync::mpsc::channel();

let mut keeper_mut = keeper.clone();
let tx_clone = tx.clone();
let mut watcher =
notify::recommended_watcher(move |event: Result<notify::Event, notify::Error>| {
match event {
Ok(event) => {
keeper_mut.handle_event(Ok(event.clone()));
tx_clone.send(Ok(event)).unwrap();
}
Err(err) => {
keeper_mut.handle_event(Err(err));
tx_clone.send(Err(())).unwrap();
}
}
})
.unwrap();

watcher
.watch(wd.as_std_path(), RecursiveMode::NonRecursive)
.unwrap();

{
let keeper = keeper.0.as_ref().lock().unwrap();
let file = keeper.files().find(|file| file.name() == test_file_name);
assert!(file.is_none());
}

test_file.generate().unwrap();

let event = rx.recv().unwrap().unwrap();
pretty_assertions::assert_eq!(
notify::EventKind::Create(notify::event::CreateKind::File),
event.kind,
"Expecting a file create event"
);

let first_line = "Just call me Mark!\n";
test_file.write(first_line).unwrap();

let event = rx.recv().unwrap().unwrap();
pretty_assertions::assert_eq!(
notify::EventKind::Create(notify::event::CreateKind::File),
event.kind,
"Expecting a file create event"
);

let event = rx.recv().unwrap().unwrap();
pretty_assertions::assert_eq!(
notify::EventKind::Modify(notify::event::ModifyKind::Data(
notify::event::DataChange::Content
)),
event.kind,
"Expecting a content modification event"
);

{
let keeper = keeper.0.as_ref().lock().unwrap();
let file = keeper
.files()
.find(|file| file.name() == test_file_name)
.expect("Keeper should have file now");
assert_eq!(first_line, file.body);
}

let second_line = "I'm a markdown file!\n";
test_file.write(second_line).unwrap();

let event = rx.recv().unwrap().unwrap();
pretty_assertions::assert_eq!(
notify::EventKind::Create(notify::event::CreateKind::File),
event.kind,
"Expecting a create event"
);

let event = rx.recv().unwrap().unwrap();
pretty_assertions::assert_eq!(
notify::EventKind::Modify(notify::event::ModifyKind::Data(
notify::event::DataChange::Content
)),
event.kind,
"Expecting a content modification event"
);

{
let keeper = keeper.0.as_ref().lock().unwrap();
let file = keeper
.files()
.find(|file| file.name() == test_file_name)
.unwrap();
assert_eq!([first_line, second_line].join(""), file.body);
}

test_file.delete().unwrap();

let event = rx.recv().unwrap().unwrap();
pretty_assertions::assert_eq!(
notify::EventKind::Create(notify::event::CreateKind::File),
event.kind,
"Expecting a create event"
);

let event = rx.recv().unwrap().unwrap();
pretty_assertions::assert_eq!(
notify::EventKind::Remove(notify::event::RemoveKind::File),
event.kind,
"Expecting a file delete event"
);

{
let keeper = keeper.0.as_ref().lock().unwrap();
let file = keeper.files().find(|file| file.name() == test_file_name);
assert!(file.is_none());
}
}
}

0 comments on commit acf4a08

Please sign in to comment.