Merge pull request #73 from michel/lib/share-search-key
perf(lib): lowercase each shared path once at scan time
This commit is contained in:
@@ -13,6 +13,9 @@ use std::path::{Path, PathBuf};
|
|||||||
pub struct SharedFile {
|
pub struct SharedFile {
|
||||||
/// Backslash-separated path exposed to peers, e.g. `music\album\song.mp3`.
|
/// Backslash-separated path exposed to peers, e.g. `music\album\song.mp3`.
|
||||||
pub virtual_path: String,
|
pub virtual_path: String,
|
||||||
|
/// `virtual_path` lowercased once at scan time, so answering a search does
|
||||||
|
/// not lowercase every shared path again.
|
||||||
|
search_key: String,
|
||||||
/// The real filesystem path used to serve the bytes.
|
/// The real filesystem path used to serve the bytes.
|
||||||
pub real_path: PathBuf,
|
pub real_path: PathBuf,
|
||||||
pub size: u64,
|
pub size: u64,
|
||||||
@@ -106,10 +109,7 @@ impl Shares {
|
|||||||
}
|
}
|
||||||
self.files
|
self.files
|
||||||
.iter()
|
.iter()
|
||||||
.filter(|f| {
|
.filter(|f| terms.iter().all(|t| f.search_key.contains(t.as_str())))
|
||||||
let haystack = f.virtual_path.to_lowercase();
|
|
||||||
terms.iter().all(|t| haystack.contains(t.as_str()))
|
|
||||||
})
|
|
||||||
.collect()
|
.collect()
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -200,6 +200,7 @@ fn scan_root(
|
|||||||
}
|
}
|
||||||
let virtual_path = virtual_path_for(root_name, root, &path);
|
let virtual_path = virtual_path_for(root_name, root, &path);
|
||||||
files.push(SharedFile {
|
files.push(SharedFile {
|
||||||
|
search_key: virtual_path.to_lowercase(),
|
||||||
virtual_path,
|
virtual_path,
|
||||||
real_path: path,
|
real_path: path,
|
||||||
size: meta.len(),
|
size: meta.len(),
|
||||||
@@ -278,6 +279,20 @@ mod tests {
|
|||||||
let _ = std::fs::remove_dir_all(root);
|
let _ = std::fs::remove_dir_all(root);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn a_mixed_case_path_matches_a_lowercase_query() {
|
||||||
|
let root = std::env::temp_dir()
|
||||||
|
.join(format!("soulseek-shares-case-{}", std::process::id()));
|
||||||
|
let _ = std::fs::remove_dir_all(&root);
|
||||||
|
std::fs::create_dir_all(root.join("Live Set")).unwrap();
|
||||||
|
std::fs::write(root.join("Live Set").join("Opening TRACK.flac"), b"x")
|
||||||
|
.unwrap();
|
||||||
|
let shares = Shares::scan(&root).unwrap();
|
||||||
|
|
||||||
|
assert_eq!(shares.search("live opening track").len(), 1);
|
||||||
|
let _ = std::fs::remove_dir_all(root);
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn search_is_case_insensitive_and_multi_term_and() {
|
fn search_is_case_insensitive_and_multi_term_and() {
|
||||||
let root = temp_tree();
|
let root = temp_tree();
|
||||||
|
|||||||
Reference in New Issue
Block a user