-
Notifications
You must be signed in to change notification settings - Fork 1.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat(watcher): add support for poll watcher #21290
base: master
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -152,6 +152,23 @@ pub struct RootOpts { | |
#[arg(short, long, env = "VECTOR_WATCH_CONFIG")] | ||
pub watch_config: bool, | ||
|
||
/// Method for watching config | ||
/// | ||
/// By default `vector` use `inotify` which is recommended for linux based system | ||
/// `poll` watcher can be used where inotify not work. ie, attaching config using NFS | ||
#[arg(long, default_value = "inotify", env = "VECTOR_WATCH_METHOD")] | ||
pub watch_config_method: WatchConfigMethod, | ||
|
||
/// poll for changes in configuration file on given interval | ||
/// | ||
/// This config is only applicable if poll is enabled in `--watch-config-method` | ||
#[arg( | ||
long, | ||
env = "VECTOR_WATCH_CONFIG_POLL_INTERVAL_SECONDS", | ||
default_value = "30" | ||
)] | ||
pub watch_config_poll_interval_seconds: NonZeroU64, | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think we should update this documentation to explain the polling watcher and when to use it https://vector.dev/docs/administration/management/#automatic-reloading-on-configuration-change But first lets see what maintainers think about documenting this |
||
|
||
/// Set the internal log rate limit | ||
#[arg( | ||
short, | ||
|
@@ -354,6 +371,14 @@ pub enum LogFormat { | |
Json, | ||
} | ||
|
||
#[derive(clap::ValueEnum, Debug, Clone, Copy, PartialEq, Eq)] | ||
pub enum WatchConfigMethod { | ||
/// recommended for linux based systems | ||
Inotify, | ||
/// works for EFS/NFS like network storage systems | ||
Poll, | ||
} | ||
|
||
pub fn handle_config_errors(errors: Vec<String>) -> exitcode::ExitCode { | ||
for error in errors { | ||
error!(message = "Configuration error.", %error); | ||
|
Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
@@ -1,10 +1,13 @@ | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
use std::{path::PathBuf, time::Duration}; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
use std::{ | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
path::{Path, PathBuf}, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
time::Duration, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
}; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
use std::{ | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
sync::mpsc::{channel, Receiver}, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
thread, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
}; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
use notify::{recommended_watcher, EventKind, RecommendedWatcher, RecursiveMode, Watcher}; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
use notify::{recommended_watcher, EventKind, RecursiveMode}; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
use crate::Error; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -19,11 +22,56 @@ const CONFIG_WATCH_DELAY: std::time::Duration = std::time::Duration::from_secs(1 | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
const RETRY_TIMEOUT: std::time::Duration = std::time::Duration::from_secs(10); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
pub enum WatcherConfig { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
/// recommended watcher for os, usually inotify for linux based systems | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
RecommendedWatcher, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
/// poll based watcher. for watching files from NFS. | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
PollWatcher(u64), | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
enum Watcher { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
/// recommended watcher for os, usually inotify for linux based systems | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
RecommendedWatcher(notify::RecommendedWatcher), | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
/// poll based watcher. for watching files from NFS. | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think it would be more idiomatic to use only
Suggested change
My previous suggestion about this was only about the There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Since the There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think you can and indeed, maybe you need to |
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
PollWatcher(notify::PollWatcher), | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
impl Watcher { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
fn add_paths(&mut self, config_paths: &[PathBuf]) -> Result<(), Error> { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
for path in config_paths { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
self.watch(path, RecursiveMode::Recursive)?; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Ok(()) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
fn watch(&mut self, path: &Path, recursive_mode: RecursiveMode) -> Result<(), Error> { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
match self { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
&mut Watcher::RecommendedWatcher(ref mut watcher) => { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
watcher.watch(path, recursive_mode) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think you can get rid of this (In the other match arm too) This behaviour was improved a few years ago Read about it here: https://github.com/rust-lang/rfcs/blob/master/text/2005-match-ergonomics.md
Suggested change
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
&mut Watcher::PollWatcher(ref mut watcher) => watcher.watch(path, recursive_mode), | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// impl From<notify::RecommendedWatcher> for Watcher { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// fn from(recommended_watcher: notify::RecommendedWatcher) -> Self { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// Watcher::RecommendedWatcher(recommended_watcher) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// } | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// } | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// impl From<notify::PollWatcher> for Watcher { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// fn from(poll_watcher: notify::PollWatcher) -> Self { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// Watcher::PollWatcher(poll_watcher) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// } | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// } | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
/// Sends a ReloadFromDisk on config_path changes. | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
/// Accumulates file changes until no change for given duration has occurred. | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
/// Has best effort guarantee of detecting all file changes from the end of | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
/// this function until the main thread stops. | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
pub fn spawn_thread<'a>( | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
watcher_conf: WatcherConfig, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
signal_tx: crate::signal::SignalTx, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
config_paths: impl IntoIterator<Item = &'a PathBuf> + 'a, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
delay: impl Into<Option<Duration>>, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -33,7 +81,7 @@ pub fn spawn_thread<'a>( | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// Create watcher now so not to miss any changes happening between | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// returning from this function and the thread starting. | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let mut watcher = Some(create_watcher(&config_paths)?); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let mut watcher = Some(create_watcher(&watcher_conf, &config_paths)?); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
info!("Watching configuration files."); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -53,7 +101,7 @@ pub fn spawn_thread<'a>( | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// We need to read paths to resolve any inode changes that may have happened. | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
// And we need to do it before raising sighup to avoid missing any change. | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
if let Err(error) = add_paths(&mut watcher, &config_paths) { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
if let Err(error) = watcher.add_paths(&config_paths) { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
error!(message = "Failed to read files to watch.", %error); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
break; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -72,7 +120,7 @@ pub fn spawn_thread<'a>( | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
thread::sleep(RETRY_TIMEOUT); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
watcher = create_watcher(&config_paths) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
watcher = create_watcher(&watcher_conf, &config_paths) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
.map_err(|error| error!(message = "Failed to create file watcher.", %error)) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
.ok(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -91,26 +139,28 @@ pub fn spawn_thread<'a>( | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
fn create_watcher( | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
watcher_conf: &WatcherConfig, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
config_paths: &[PathBuf], | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
) -> Result< | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
( | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
RecommendedWatcher, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Receiver<Result<notify::Event, notify::Error>>, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
), | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Error, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
> { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
) -> Result<(Watcher, Receiver<Result<notify::Event, notify::Error>>), Error> { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
info!("Creating configuration file watcher."); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let (sender, receiver) = channel(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let mut watcher = recommended_watcher(sender)?; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
add_paths(&mut watcher, config_paths)?; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Ok((watcher, receiver)) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
fn add_paths(watcher: &mut RecommendedWatcher, config_paths: &[PathBuf]) -> Result<(), Error> { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
for path in config_paths { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
watcher.watch(path, RecursiveMode::Recursive)?; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let (sender, receiver) = channel(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
match watcher_conf { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
WatcherConfig::RecommendedWatcher => { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let recommended_watcher = recommended_watcher(sender)?; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let mut watcher = Watcher::RecommendedWatcher(recommended_watcher); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
watcher.add_paths(config_paths)?; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Ok((watcher, receiver)) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
WatcherConfig::PollWatcher(interval) => { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let config = | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
notify::Config::default().with_poll_interval(Duration::from_secs(*interval)); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let poll_watcher = notify::PollWatcher::new(sender, config)?; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Should we allow the user to specify There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I'd vote against it being user controllable and hope for it to just have a sane default. I can't think of a scenario where I'd wanna toggle it! There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. We found issues in openshift environments where the inotify watcher was constantly triggered and the file contents did not change at all. In this case, we would like to hash the contents to check if it really changed before reloading vector config. I think having sane defaults is good (for example, this would default to false), but there are situations where this is useful There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Would there be a downside to always hashing the changes? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Yes, as the docs I pointed states:
I prefer that downside to be opt-in |
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let mut watcher = Watcher::PollWatcher(poll_watcher); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
watcher.add_paths(config_paths)?; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Ok((watcher, receiver)) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Comment on lines
+148
to
+162
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think you can take
out of the match branches
Suggested change
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. yeah, this seems elegant. i'll do that |
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Ok(()) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
#[cfg(all(test, unix, not(target_os = "macos")))] // https://github.com/vectordotdev/vector/issues/5000 | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -140,12 +190,13 @@ mod tests { | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let delay = Duration::from_secs(3); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let dir = temp_dir().to_path_buf(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let file_path = dir.join("vector.toml"); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let watcher_conf = WatcherConfig::RecommendedWatcher; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
std::fs::create_dir(&dir).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let mut file = File::create(&file_path).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let (signal_tx, signal_rx) = broadcast::channel(128); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
spawn_thread(signal_tx, &[dir], delay).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
spawn_thread(watcher_conf, signal_tx, &[dir], delay).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
if !test(&mut file, delay * 5, signal_rx).await { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
panic!("Test timed out"); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -159,9 +210,10 @@ mod tests { | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let delay = Duration::from_secs(3); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let file_path = temp_file(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let mut file = File::create(&file_path).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let watcher_conf = WatcherConfig::RecommendedWatcher; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let (signal_tx, signal_rx) = broadcast::channel(128); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
spawn_thread(signal_tx, &[file_path], delay).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
spawn_thread(watcher_conf, signal_tx, &[file_path], delay).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
if !test(&mut file, delay * 5, signal_rx).await { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
panic!("Test timed out"); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -179,8 +231,10 @@ mod tests { | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let mut file = File::create(&file_path).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
std::os::unix::fs::symlink(&file_path, &sym_file).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let watcher_conf = WatcherConfig::RecommendedWatcher; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let (signal_tx, signal_rx) = broadcast::channel(128); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
spawn_thread(signal_tx, &[sym_file], delay).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
spawn_thread(watcher_conf, signal_tx, &[sym_file], delay).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
if !test(&mut file, delay * 5, signal_rx).await { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
panic!("Test timed out"); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -195,12 +249,13 @@ mod tests { | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let dir = temp_dir().to_path_buf(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let sub_dir = dir.join("sources"); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let file_path = sub_dir.join("input.toml"); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let watcher_conf = WatcherConfig::RecommendedWatcher; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
std::fs::create_dir_all(&sub_dir).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let mut file = File::create(&file_path).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
let (signal_tx, signal_rx) = broadcast::channel(128); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
spawn_thread(signal_tx, &[sub_dir], delay).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
spawn_thread(watcher_conf, signal_tx, &[sub_dir], delay).unwrap(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
if !test(&mut file, delay * 5, signal_rx).await { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
panic!("Test timed out"); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please, take a look into my comment about this in your closed PR
#21258 (comment)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we put this as
Recommended
or any thing that comes to ur mind? @jszwedkoThere was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yes, that would fit