From 7079ed2c19c22fca7d3247bcbd61a3e6b2765325 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fe=CC=81lix=20Saparelli?= Date: Sun, 6 Dec 2015 13:34:59 +1300 Subject: [PATCH] Replace Walker by WalkDir Fixes #31 Might help with #17 and #21 --- Cargo.toml | 2 +- src/inotify/mod.rs | 39 +++++++++++------------- src/poll.rs | 75 ++++++++++++++++------------------------------ 3 files changed, 44 insertions(+), 72 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index 0894e7db..3754f3f5 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -35,7 +35,7 @@ libc = "*" log = "*" time = "*" filetime = "*" -walker = "^1.0.0" +walkdir = "^0.1" [target.x86_64-unknown-linux-gnu.dependencies] inotify = "^0.1" diff --git a/src/inotify/mod.rs b/src/inotify/mod.rs index be6e5f2a..dca745f2 100644 --- a/src/inotify/mod.rs +++ b/src/inotify/mod.rs @@ -1,10 +1,10 @@ extern crate inotify as inotify_sys; extern crate libc; -extern crate walker; +extern crate walkdir; use mio::{self, EventLoop}; use self::inotify_sys::wrapper::{self, INotify, Watch}; -use self::walker::Walker; +use self::walkdir::WalkDir; use std::collections::HashMap; use std::fs::metadata; use std::path::{Path, PathBuf}; @@ -83,28 +83,23 @@ impl mio::Handler for INotifyHandler { impl INotifyHandler { fn add_watch_recursively(&mut self, path: PathBuf) -> Result<(), Error> { - let is_dir = match metadata(path.as_ref() as &Path) { - Ok(m) => m.is_dir(), + match metadata(path.as_ref() as &Path) { Err(e) => return Err(Error::Io(e)), - }; - if is_dir { - match Walker::new(path.as_ref()) { - Ok(dir) => { - for entry in dir { - match entry { - Ok(entry) => { - let path = entry.path(); - try!(self.add_watch(path)); - }, - Err(e) => return Err(Error::Io(e)), - } - } - self.add_watch(path) - }, - Err(e) => Err(Error::Io(e)) + Ok(m) => match m.is_dir() { + false => return self.add_watch(path), + true => {} + } + } + + for entry in WalkDir::new(path).follow_links(true) + .into_iter().filter_map(|e| e.ok()) { + match entry { + Err(e) => return Err(Error::Io(e)), + Ok(entry) => { + let path = entry.path(); + try!(self.add_watch(path)); + } } - } else { - self.add_watch(path) } } diff --git a/src/poll.rs b/src/poll.rs index a26c9ec5..dc920cdf 100644 --- a/src/poll.rs +++ b/src/poll.rs @@ -5,11 +5,11 @@ use std::fs; use std::thread; use super::{Error, Event, op, Watcher}; use std::path::{Path, PathBuf}; -use self::walker::Walker; +use self::walkdir::WalkDir; use filetime::FileTime; -extern crate walker; +extern crate walkdir; pub struct PollWatcher { tx: Sender, @@ -90,54 +90,31 @@ impl PollWatcher { } // TODO: more efficient implementation where the dir tree is cached? - match Walker::new(watch) { - Err(e) => { - let _ = tx.send(Event { - path: Some(watch.clone()), - op: Err(Error::Io(e)) - }); - continue - }, - Ok(iter) => { - for entry in iter { - match entry { - Ok(entry) => { - let path = entry.path(); - - match fs::metadata(&path) { - Err(e) => { - let _ = tx.send(Event { - path: Some(path.clone()), - op: Err(Error::Io(e)) - }); - continue - }, - Ok(stat) => { - let modified = - FileTime::from_last_modification_time(&stat) - .seconds(); - - match mtimes.insert(path.clone(), modified) { - None => continue, // First run - Some(old) => { - if modified > old { - let _ = tx.send(Event { - path: Some(path.clone()), - op: Ok(op::WRITE) - }); - continue - } - } - } - } + for entry in WalkDir::new(watch).follow_links(true) + .into_iter().filter_map(|e| e.ok()) { + let path = entry.path(); + + match fs::metadata(&path) { + Err(e) => { + let _ = tx.send(Event { + path: Some(path.to_path_buf()), + op: Err(Error::Io(e)) + }); + continue + }, + Ok(stat) => { + let modified = FileTime::from_last_modification_time(&stat).seconds(); + match mtimes.insert(path.clone().to_path_buf(), modified) { + None => continue, // First run + Some(old) => { + if modified > old { + let _ = tx.send(Event { + path: Some(path.to_path_buf()), + op: Ok(op::WRITE) + }); + continue } - }, - Err(e) => { - let _ = tx.send(Event { - path: Some(watch.clone()), - op: Err(Error::Io(e)) - }); - }, + } } } }