Skip to content

Commit 6086db5

Browse files
committed
Fix
1 parent 002fd8f commit 6086db5

2 files changed

Lines changed: 34 additions & 12 deletions

File tree

crates/bundles/src/cache.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -112,7 +112,7 @@ impl<'this, T: FileIndex<'this>> BundleCache<'this, T> {
112112
};
113113

114114
let hash_dir = ensure_dir!(inline, &cache_root.join("hashes"));
115-
let hash_file = hash_dir.join(app_dirs::app_dirs2::sanitized(&bundle.get_location()));
115+
let hash_file = hash_dir.join(app_dirs::sanitize(&bundle.get_location()));
116116

117117
let saved_hash = {
118118
if !hash_file.exists() {

crates/io_base/src/app_dirs.rs

Lines changed: 33 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -16,25 +16,27 @@ use tectonic_errors::prelude::*;
1616
/// The instance of the `directories` crate that this crate links to.
1717
pub use directories;
1818

19-
const PROJECT_DIRS: LazyLock<ProjectDirs> =
20-
LazyLock::new(|| ProjectDirs::from("", "TectonicProject", "Tectonic").unwrap());
19+
const PROJECT_DIRS: LazyLock<Result<ProjectDirs>> = LazyLock::new(|| {
20+
ProjectDirs::from("", "TectonicProject", "Tectonic")
21+
.ok_or_else(|| Error::from("Unable to find standard directories for platform"))
22+
});
2123

2224
/// Get the directory for per-user Tectonic configuration files.
2325
///
2426
/// This constructs the path but does not ensure that the directory actually
2527
/// exists. The function [`ensure_user_config`] makes sure that the directory is
2628
/// created.
2729
///
28-
/// This function is currently implemented with [`app_dirs2::get_app_root`] using
29-
/// the `UserConfig` data type. Return values have the form:
30+
/// This function is currently implemented with [`ProjectDirs::config_dir`] using
31+
/// the `ProjectDirs` data type. Return values have the form:
3032
///
3133
/// - Windows: `%APPDATA%\TectonicProject\Tectonic`, where `%APPDATA%` is
3234
/// something like `C:\Users\knuth\AppData\Roaming`.
3335
/// - macOS: `$HOME/Library/Application Support/Tectonic`
3436
/// - Others: `$XDG_CONFIG_HOME/Tectonic` if defined, otherwise
3537
/// `$HOME/.config/Tectonic`
3638
pub fn get_user_config() -> Result<PathBuf> {
37-
Ok(PROJECT_DIRS.config_dir().to_path_buf())
39+
Ok(PROJECT_DIRS?.config_dir().to_path_buf())
3840
}
3941

4042
/// Get the directory for per-user Tectonic configuration files, creating it if needed.
@@ -53,8 +55,8 @@ pub fn ensure_user_config() -> Result<PathBuf> {
5355
/// should be a forward slash on all platforms. It may be an empty string if you
5456
/// want to get the toplevel user cache directory.
5557
///
56-
/// This function is currently implemented with [`app_dirs2::app_dir`] using the
57-
/// `UserCache` data type. Return values have the form:
58+
/// This function is currently implemented with [`ProjectDirs::cache_dir`] using the
59+
/// `ProjectDirs` data type. Return values have the form:
5860
///
5961
/// - Windows: `%LOCALAPPDATA%\TectonicProject\Tectonic`, where `%LOCALAPPDATA%`
6062
/// is something like `C:\Users\knuth\AppData\Local`.
@@ -63,12 +65,12 @@ pub fn ensure_user_config() -> Result<PathBuf> {
6365
/// `$HOME/.cache/Tectonic`
6466
///
6567
///
66-
/// The cache location defaults to the `AppDataType::UserCache`
67-
/// provided by `app_dirs2` but can be overwritten using the
68+
/// The cache location defaults to the `ProjectDirs::cache_dir`
69+
/// provided by `directories` but can be overwritten using the
6870
/// `TECTONIC_CACHE_DIR` environment variable.
6971
///
7072
/// This method may perform I/O to create the user cache directory, so it is
71-
/// fallible. (Due to its `app_dirs2` implementation, it would have to be
73+
/// fallible. (Due to its `directories` implementation, it would have to be
7274
/// fallible even if it didn't perform I/O.)
7375
pub fn get_user_cache_dir(subdir: &str) -> Result<PathBuf> {
7476
let env_cache_path = env::var_os("TECTONIC_CACHE_DIR");
@@ -80,8 +82,28 @@ pub fn get_user_cache_dir(subdir: &str) -> Result<PathBuf> {
8082
fs::create_dir_all(&env_cache_path)?;
8183
env_cache_path
8284
}
83-
None => PROJECT_DIRS.cache_dir().join(subdir),
85+
None => PROJECT_DIRS?.cache_dir().join(subdir),
8486
};
8587

8688
Ok(cache_path)
8789
}
90+
91+
/// Borrowed from `app_dirs2`, convert any string into a consistently valid file or directory name.
92+
pub fn sanitize(component: &str) -> String {
93+
let mut buf = String::with_capacity(component.len());
94+
for (i, c) in component.chars().enumerate() {
95+
let is_alnum = c.is_ascii_alphanumeric();
96+
let is_space = c == ' ';
97+
let is_hyphen = c == '-';
98+
let is_underscore = c == '_';
99+
let is_period = c == '.' && i != 0; // Disallow accidentally hidden folders
100+
let is_valid = is_alnum || is_space || is_hyphen || is_underscore || is_period;
101+
if is_valid {
102+
buf.push(c);
103+
} else {
104+
use std::fmt::Write;
105+
let _ = write!(&mut buf, ",{},", c as u32);
106+
}
107+
}
108+
buf
109+
}

0 commit comments

Comments
 (0)