mirror of
https://github.com/storytold/craft-libs.git
synced 2026-11-08 19:42:12 +00:00
CP6.13: hunspell.rs — Windows drives are probed for LibreOffice only when its language folders are wanted (CodeRabbit on craft-libs#489)
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01FypgCX8LsYYE8fsj4byBm2
This commit is contained in:
1 parent
9614ab270d
commit
6057debe6e
1 file changed
+34
-10
@@ -105,16 +105,7 @@ fn search_tiers(lo_exts: Option<&[String]>) -> (Vec<PathBuf>, Vec<PathBuf>) {
|
||||
system.extend(lo_dirs(&base.join("LibreOffice").join("share").join("extensions").to_string_lossy()));
|
||||
}
|
||||
}
|
||||
// If LibreOffice is installed on another drive (e.g. D:\Program Files\LibreOffice), check drives C..Z
|
||||
for drive in b'C'..=b'Z' {
|
||||
let drive_char = drive as char;
|
||||
for pf in ["Program Files", "Program Files (x86)"] {
|
||||
let lo_base = PathBuf::from(format!(r"{drive_char}:\{pf}\LibreOffice\share\extensions"));
|
||||
if lo_base.is_dir() {
|
||||
system.extend(lo_dirs(&lo_base.to_string_lossy()));
|
||||
}
|
||||
}
|
||||
}
|
||||
system.extend(lo_drive_dirs(lo_exts, Path::is_dir));
|
||||
} else if cfg!(target_os = "macos") {
|
||||
if let Some(h) = &home {
|
||||
// An app started from Finder or the Dock doesn't see `WORDCRAFT_DICTIONARIES`; this
|
||||
@@ -144,6 +135,23 @@ fn search_tiers(lo_exts: Option<&[String]>) -> (Vec<PathBuf>, Vec<PathBuf>) {
|
||||
(dirs, system)
|
||||
}
|
||||
|
||||
/// LibreOffice's language folders (`<drive>:\Program Files\LibreOffice\share\extensions\<ext>`)
|
||||
/// on the drives C to Z where `is_dir` finds LibreOffice installed. No drive is probed without
|
||||
/// `lo_exts` (no LibreOffice folders are wanted then).
|
||||
fn lo_drive_dirs(lo_exts: Option<&[String]>, is_dir: impl Fn(&Path) -> bool) -> Vec<PathBuf> {
|
||||
let Some(exts) = lo_exts else { return Vec::new() };
|
||||
let mut out = Vec::new();
|
||||
for drive in 'C'..='Z' {
|
||||
for pf in ["Program Files", "Program Files (x86)"] {
|
||||
let base = PathBuf::from(format!(r"{drive}:\{pf}\LibreOffice\share\extensions"));
|
||||
if is_dir(&base) {
|
||||
out.extend(exts.iter().map(|e| base.join(e)));
|
||||
}
|
||||
}
|
||||
}
|
||||
out
|
||||
}
|
||||
|
||||
/// The user's data folder on Linux and the BSDs: `$XDG_DATA_HOME` when it is an absolute path (the
|
||||
/// XDG Base Directory spec ignores a relative one), else `~/.local/share`.
|
||||
fn xdg_data_home(xdg: Option<std::ffi::OsString>, home: Option<&Path>) -> Option<PathBuf> {
|
||||
@@ -610,6 +618,22 @@ fn decode_utf8_dic(dic: &[u8]) -> Result<String, String> {
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
||||
/// CodeRabbit on craft-libs#489: without LibreOffice extension names no drive is probed; with
|
||||
/// them, only drives where LibreOffice is found give folders.
|
||||
#[test]
|
||||
fn libreoffice_drives_are_probed_only_when_wanted() {
|
||||
let probes = std::cell::Cell::new(0);
|
||||
let count = |_: &Path| {
|
||||
probes.set(probes.get() + 1);
|
||||
false
|
||||
};
|
||||
assert!(lo_drive_dirs(None, count).is_empty());
|
||||
assert_eq!(probes.get(), 0);
|
||||
let exts = ["dict-tr".to_string()];
|
||||
let found = lo_drive_dirs(Some(&exts), |p: &Path| p.to_string_lossy().starts_with(r"D:\Program Files\"));
|
||||
assert_eq!(found, [PathBuf::from(r"D:\Program Files\LibreOffice\share\extensions").join("dict-tr")]);
|
||||
}
|
||||
|
||||
/// Another region's Language pack never beats the system's dictionary of the right region
|
||||
/// (`pt-pt` pack vs system `pt_BR`; `de-ch` vs `de_DE`; `en-gb` vs `en_US`), but beats the
|
||||
/// system's other names; the right region's pack beats the system; the dictionaries folder
|
||||
|
||||
Reference in new issue
Block a user