cosmic-files/src/operation/notifiers.rs
2026-04-14 17:04:53 +02:00

58 lines
1.5 KiB
Rust

// Copyright 2026 System76 <info@system76.com>
// SPDX-License-Identifier: GPL-3.0-only
use std::path::{Path, PathBuf};
use std::sync::{Arc, LazyLock, Mutex};
use tokio::sync::Notify;
/// Monitor files which are being written to.
pub struct FileWritingNotifier {
data: Vec<PathBuf>,
notify: Arc<Notify>,
}
static ACTIVELY_WRITING: LazyLock<Mutex<FileWritingNotifier>> = LazyLock::new(|| {
Mutex::new(FileWritingNotifier {
data: Vec::new(),
notify: Arc::new(Notify::new()),
})
});
/// Append path that is being written to.
pub fn actively_writing_add(path: PathBuf) {
ACTIVELY_WRITING.lock().unwrap().data.push(path);
}
/// Remove path to file that has finished writing and notify waiters.
pub fn actively_writing_remove(path: &Path) {
let mut guard = ACTIVELY_WRITING.lock().unwrap();
guard.data.retain(|p| p != path);
guard.notify.notify_waiters();
}
/// Wait until the actively-writing queue is empty or a file has been removed.
pub async fn actively_writing_tick() {
let notify = (|| {
let guard = ACTIVELY_WRITING.lock().unwrap();
if !guard.data.is_empty() {
return Some(guard.notify.clone());
}
None
})();
if let Some(notify) = notify {
notify.notified().await
}
}
/// Check if a file is being written to. Avoid thumbnail generation until after it is finished.
pub fn is_actively_writing_to(path: &Path) -> bool {
ACTIVELY_WRITING
.lock()
.unwrap()
.data
.iter()
.any(|p| p == path)
}