59 lines
1.7 KiB
Rust
59 lines
1.7 KiB
Rust
use notify::{Event, RecursiveMode, Result, Watcher};
|
|
use std::{fs::File, io::{Read as _, Seek as _, SeekFrom, pipe}, path::{Path, PathBuf}, sync::mpsc};
|
|
|
|
pub fn default_log_file () -> PathBuf {
|
|
let base = xdg::BaseDirectories::new ()
|
|
.data_home
|
|
.expect ("could not find default log file.");
|
|
base.join ("Steam/steamapps/common/Team Fortress 2/tf/console.log")
|
|
.to_path_buf ()
|
|
}
|
|
|
|
pub struct Console {
|
|
prev_size : usize,
|
|
}
|
|
|
|
fn file_size (file : &Path) -> u64 {
|
|
if let Ok (mut f) = File::open (file) {
|
|
let x = f.seek (SeekFrom::End (0));
|
|
x.unwrap_or (0)
|
|
} else {
|
|
0
|
|
}
|
|
}
|
|
|
|
impl Console {
|
|
pub fn watch<F> (log_file : &Path, cb : F) -> Result<
|
|
// mpsc::Receiver<std::result::Result<Event, notify::Error>>
|
|
()
|
|
>
|
|
where F : Fn (&str) -> ()
|
|
{
|
|
let mut prev_size = file_size (log_file);
|
|
let (tx, rx) = mpsc::channel::<Result<Event>> ();
|
|
let mut watcher = notify::recommended_watcher (tx)?;
|
|
watcher.watch (log_file, RecursiveMode::NonRecursive)?;
|
|
for res in rx {
|
|
if let Err (err) = res {
|
|
log::error! ("{:?}", err);
|
|
continue
|
|
};
|
|
|
|
let new_size = file_size (log_file);
|
|
|
|
if prev_size < new_size {
|
|
let mut f = File::open (log_file)
|
|
.expect ("failed to read log file");
|
|
f.seek (SeekFrom::Start (prev_size)).unwrap ();
|
|
let mut buf = String::new ();
|
|
f.read_to_string (&mut buf).unwrap ();
|
|
cb (&buf)
|
|
} if new_size < prev_size {
|
|
log::warn! ("log file shrank!??");
|
|
}
|
|
prev_size = new_size;
|
|
}
|
|
Ok (())
|
|
}
|
|
}
|