fix: stepwise renaming causes uncertain sorting order (#398)

This commit is contained in:
三咲雅 · Misaki Masa 2023-11-25 10:10:34 +08:00 committed by GitHub
parent 56b0611f7c
commit 47af821f48
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 23 additions and 30 deletions

View file

@ -19,36 +19,35 @@ impl FilesSorter {
return false; return false;
} }
let by_alphabetical = |a: &File, b: &File| {
if self.sensitive {
return self.cmp(&*a.url, &*b.url, self.promote(a, b));
}
self.cmp(
a.url.as_os_str().to_ascii_uppercase(),
b.url.as_os_str().to_ascii_uppercase(),
self.promote(a, b),
)
};
match self.by { match self.by {
SortBy::None => return false, SortBy::None => return false,
SortBy::Alphabetical => items.sort_unstable_by(|a, b| { SortBy::Alphabetical => items.sort_unstable_by(by_alphabetical),
if self.sensitive {
return self.cmp(&*a.url, &*b.url, self.promote(a, b));
}
self.cmp(
a.url.as_os_str().to_ascii_uppercase(),
b.url.as_os_str().to_ascii_uppercase(),
self.promote(a, b),
)
}),
SortBy::Created => items.sort_unstable_by(|a, b| { SortBy::Created => items.sort_unstable_by(|a, b| {
if let (Some(aa), Some(bb)) = (a.created, b.created) { let ord = self.cmp(a.created, b.created, self.promote(a, b));
return self.cmp(aa, bb, self.promote(a, b)); if ord == Ordering::Equal { by_alphabetical(a, b) } else { ord }
}
Ordering::Equal
}), }),
SortBy::Modified => items.sort_unstable_by(|a, b| { SortBy::Modified => items.sort_unstable_by(|a, b| {
if let (Some(aa), Some(bb)) = (a.modified, b.modified) { let ord = self.cmp(a.modified, b.modified, self.promote(a, b));
return self.cmp(aa, bb, self.promote(a, b)); if ord == Ordering::Equal { by_alphabetical(a, b) } else { ord }
}
Ordering::Equal
}), }),
SortBy::Natural => self.sort_naturally(items), SortBy::Natural => self.sort_naturally(items),
SortBy::Size => items.sort_unstable_by(|a, b| { SortBy::Size => items.sort_unstable_by(|a, b| {
let aa = if a.is_dir() { sizes.get(&a.url).copied() } else { None }; let aa = if a.is_dir() { sizes.get(&a.url).copied() } else { None };
let bb = if b.is_dir() { sizes.get(&b.url).copied() } else { None }; let bb = if b.is_dir() { sizes.get(&b.url).copied() } else { None };
self.cmp(aa.unwrap_or(a.len), bb.unwrap_or(b.len), self.promote(a, b)) let ord = self.cmp(aa.unwrap_or(a.len), bb.unwrap_or(b.len), self.promote(a, b));
if ord == Ordering::Equal { by_alphabetical(a, b) } else { ord }
}), }),
} }
true true

View file

@ -1,4 +1,4 @@
use std::{collections::BTreeSet, ffi::OsStr, io::{stdout, BufWriter, Write}, path::PathBuf}; use std::{collections::BTreeMap, ffi::OsStr, io::{stdout, BufWriter, Write}, path::PathBuf};
use anyhow::{anyhow, bail, Result}; use anyhow::{anyhow, bail, Result};
use tokio::{fs::{self, OpenOptions}, io::{stdin, AsyncReadExt, AsyncWriteExt}}; use tokio::{fs::{self, OpenOptions}, io::{stdin, AsyncReadExt, AsyncWriteExt}};
@ -22,13 +22,9 @@ impl Manager {
return Ok(()); return Ok(());
} }
let parent = old.parent_url().unwrap();
emit!(Files(FilesOp::Deleting(parent, BTreeSet::from([old]))));
let file = File::from(new.clone()).await?; let file = File::from(new.clone()).await?;
emit!(Files(FilesOp::Creating(file.parent().unwrap(), file.into_map()))); emit!(Files(FilesOp::Replacing(file.parent().unwrap(), BTreeMap::from_iter([(old, file)]))));
Self::_hover(Some(new)); Ok(Self::_hover(Some(new)))
Ok(())
} }
pub fn rename(&self, opt: impl Into<Opt>) -> bool { pub fn rename(&self, opt: impl Into<Opt>) -> bool {

View file

@ -133,9 +133,7 @@ impl Watcher {
watched: Arc<RwLock<IndexMap<Url, Option<Url>>>>, watched: Arc<RwLock<IndexMap<Url, Option<Url>>>>,
) { ) {
// TODO: revert this once a new notification is implemented // TODO: revert this once a new notification is implemented
// let rx = UnboundedReceiverStream::new(rx).chunks_timeout(100, let rx = UnboundedReceiverStream::new(rx).chunks_timeout(10, Duration::from_millis(20));
// Duration::from_millis(200));
let rx = UnboundedReceiverStream::new(rx).chunks_timeout(1, Duration::ZERO);
pin!(rx); pin!(rx);
while let Some(urls) = rx.next().await { while let Some(urls) = rx.next().await {