fix: propagate and update the directory node till its first parent when the files of a directory change (#1987)

This commit is contained in:
三咲雅 · Misaki Masa 2024-12-04 22:44:35 +08:00 committed by GitHub
parent b4d1174f46
commit 2771aef677
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
4 changed files with 32 additions and 29 deletions

View file

@ -25,12 +25,8 @@ impl Manager {
return;
};
let mut ops = vec![opt.op];
for u in LINKED.read().from_dir(ops[0].cwd()) {
ops.push(ops[0].rebase(u));
}
for op in ops {
let linked: Vec<_> = LINKED.read().from_dir(opt.op.cwd()).map(|u| opt.op.rebase(u)).collect();
for op in [opt.op].into_iter().chain(linked) {
let idx = self.tabs.cursor;
self.yanked.apply_op(&op);

View file

@ -16,29 +16,27 @@ impl DerefMut for Linked {
}
impl Linked {
pub fn from_dir(&self, url: &Url) -> Vec<&Url> {
pub fn from_dir<'a, 'b>(&'a self, url: &'b Url) -> Box<dyn Iterator<Item = &'a Url> + 'b>
where
'a: 'b,
{
if let Some(to) = self.get(url) {
self.iter().filter(|(k, v)| *v == to && *k != url).map(|(k, _)| k).collect()
Box::new(self.iter().filter(move |(k, v)| *v == to && *k != url).map(|(k, _)| k))
} else {
self.iter().filter(|(_, v)| *v == url).map(|(k, _)| k).collect()
Box::new(self.iter().filter(move |(_, v)| *v == url).map(|(k, _)| k))
}
}
pub fn from_file(&self, url: &Url) -> Vec<Url> {
if self.is_empty() {
return Default::default();
return vec![];
}
let Some(p) = url.parent_url() else {
return Default::default();
return vec![];
};
let relatives = self.from_dir(&p);
if relatives.is_empty() {
return Default::default();
}
let name = url.file_name().unwrap();
relatives.into_iter().map(|u| u.join(name)).collect()
self.from_dir(&p).map(|u| u.join(name)).collect()
}
}

View file

@ -34,9 +34,7 @@ impl Watcher {
if event.kind.is_access() {
return;
}
for path in event.paths {
out_tx_.send(Url::from(path)).ok();
}
Self::push_files_impl(&out_tx_, event.paths.into_iter().map(Url::from));
};
let config = notify::Config::default().with_poll_interval(Duration::from_millis(500));
@ -55,11 +53,23 @@ impl Watcher {
self.in_tx.send(new.into_iter().cloned().collect()).ok();
}
pub(super) fn push_files(&self, url: Vec<Url>) {
let watched = WATCHED.read();
for u in url {
if u.parent_url().is_some_and(|p| watched.contains(&p)) {
self.out_tx.send(u).ok();
pub(super) fn push_files(&self, urls: Vec<Url>) {
Self::push_files_impl(&self.out_tx, urls.into_iter());
}
fn push_files_impl(out_tx: &mpsc::UnboundedSender<Url>, urls: impl Iterator<Item = Url>) {
let (mut parents, watched) = (HashSet::new(), WATCHED.read());
for u in urls {
let Some(p) = u.parent_url() else { continue };
if !watched.contains(&p)
&& LINKED.read().from_dir(&p).find(|&u| watched.contains(u)).is_none()
{
continue;
}
out_tx.send(u).ok();
if !parents.contains(&p) {
out_tx.send(p.clone()).ok();
parents.insert(p);
}
}
}

View file

@ -1,4 +1,3 @@
table.unpack = table.unpack or unpack
function Err(s, ...) return Error.custom(string.format(s, ...)) end
function ya.clamp(min, x, max)
@ -30,11 +29,11 @@ end
function ya.readable_size(size)
local units = { "B", "K", "M", "G", "T", "P", "E", "Z", "Y", "R", "Q" }
local i = 1
while size > 1024.0 and i < #units do
size = size / 1024.0
while size > 1024 and i < #units do
size = size / 1024
i = i + 1
end
return string.format("%.1f%s", size, units[i])
return string.format("%.1f%s", size, units[i]):gsub("[.,]0", "", 1)
end
function ya.readable_path(path)