diff --git a/Cargo.lock b/Cargo.lock
index d58fca343..0b692ebf3 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -84,7 +84,7 @@ version = "1.1.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "40c48f72fd53cd289104fc64099abca73db4166ad86ea0b4341abe65af83dadc"
dependencies = [
- "windows-sys 0.60.2",
+ "windows-sys 0.61.2",
]
[[package]]
@@ -95,7 +95,7 @@ checksum = "291e6a250ff86cd4a820112fb8898808a366d8f9f58ce16d1f538353ad55747d"
dependencies = [
"anstyle",
"once_cell_polyfill",
- "windows-sys 0.60.2",
+ "windows-sys 0.61.2",
]
[[package]]
@@ -671,7 +671,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "39cab71617ae0d63f51a36d69f866391735b51691dbda63cf6f96d042b63efeb"
dependencies = [
"libc",
- "windows-sys 0.52.0",
+ "windows-sys 0.61.2",
]
[[package]]
@@ -1326,7 +1326,7 @@ checksum = "3640c1c38b8e4e43584d8df18be5fc6b0aa314ce6ebf51b53313d4306cca8e46"
dependencies = [
"hermit-abi",
"libc",
- "windows-sys 0.52.0",
+ "windows-sys 0.61.2",
]
[[package]]
@@ -1611,7 +1611,7 @@ version = "0.50.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7957b9740744892f114936ab4a57b3f487491bbeafaf8083688b16841a4240e5"
dependencies = [
- "windows-sys 0.59.0",
+ "windows-sys 0.61.2",
]
[[package]]
@@ -2209,7 +2209,7 @@ dependencies = [
"errno",
"libc",
"linux-raw-sys",
- "windows-sys 0.52.0",
+ "windows-sys 0.61.2",
]
[[package]]
@@ -2516,7 +2516,6 @@ dependencies = [
"cfg-if",
"libc",
"psm",
- "windows-sys 0.52.0",
"windows-sys 0.59.0",
]
@@ -2608,7 +2607,7 @@ dependencies = [
"getrandom 0.3.4",
"once_cell",
"rustix",
- "windows-sys 0.52.0",
+ "windows-sys 0.61.2",
]
[[package]]
@@ -3202,7 +3201,7 @@ version = "0.1.11"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c2a7b1c03c876122aa43f3020e6c3c3ee5c05081c9a00739faf7503aeba10d22"
dependencies = [
- "windows-sys 0.52.0",
+ "windows-sys 0.61.2",
]
[[package]]
diff --git a/docs/cli.md b/docs/cli.md
index 56c9f9621..18b38eec2 100644
--- a/docs/cli.md
+++ b/docs/cli.md
@@ -60,7 +60,7 @@ prek install [OPTIONS] [HOOK|PROJECT]...
--allow-missing-configAllow a missing pre-commit configuration file
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -127,7 +127,7 @@ prek install-hooks [OPTIONS] [HOOK|PROJECT]...
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -191,7 +191,7 @@ prek run [OPTIONS] [HOOK|PROJECT]...
--all-files, -aRun on all files in the repo
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -277,7 +277,7 @@ prek list [OPTIONS] [HOOK|PROJECT]...
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -364,7 +364,7 @@ prek uninstall [OPTIONS]
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -400,7 +400,7 @@ prek validate-config [OPTIONS] [CONFIG]...
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -436,7 +436,7 @@ prek validate-manifest [OPTIONS] [MANIFEST]...
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -467,7 +467,7 @@ prek sample-config [OPTIONS]
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -500,7 +500,7 @@ prek auto-update [OPTIONS]
--bleeding-edgeUpdate to the bleeding edge of the default branch instead of the latest tagged version
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -553,7 +553,7 @@ prek cache dir [OPTIONS]
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -584,7 +584,7 @@ prek cache gc [OPTIONS]
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -615,7 +615,7 @@ prek cache clean [OPTIONS]
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -646,7 +646,7 @@ prek cache size [OPTIONS]
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -683,7 +683,7 @@ prek init-template-dir [OPTIONS]
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -748,7 +748,7 @@ prek try-repo [OPTIONS] [HOOK|PROJECT]...
--all-files, -aRun on all files in the repo
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
@@ -837,7 +837,7 @@ prek self update [OPTIONS] [TARGET_VERSION]
--cd, -C dirChange to directory before running
--color colorWhether to use color in output
-May also be set with the PREK_COLOR environment variable.
[default: auto]
Possible values:
+Possible values:
auto: Enables colored output only when the output is going to a terminal or TTY with support
always: Enables colored output regardless of the detected environment
diff --git a/src/cli/mod.rs b/src/cli/mod.rs
index 96a39112e..8b2c1695b 100644
--- a/src/cli/mod.rs
+++ b/src/cli/mod.rs
@@ -9,9 +9,9 @@ use clap_complete::engine::ArgValueCompleter;
use serde::{Deserialize, Serialize};
use prek_consts::CONFIG_FILE;
-use prek_consts::env_vars::EnvVars;
use crate::config::{HookType, Language, Stage};
+use crate::settings::{CliOverrides, ColorChoice};
mod auto_update;
mod cache_clean;
@@ -72,28 +72,6 @@ impl From for ExitCode {
}
}
-#[derive(Debug, Copy, Clone, clap::ValueEnum)]
-pub enum ColorChoice {
- /// Enables colored output only when the output is going to a terminal or TTY with support.
- Auto,
-
- /// Enables colored output regardless of the detected environment.
- Always,
-
- /// Disables colored output.
- Never,
-}
-
-impl From for anstream::ColorChoice {
- fn from(value: ColorChoice) -> Self {
- match value {
- ColorChoice::Auto => Self::Auto,
- ColorChoice::Always => Self::Always,
- ColorChoice::Never => Self::Never,
- }
- }
-}
-
const STYLES: Styles = Styles::styled()
.header(AnsiColor::Green.on_default().effects(Effects::BOLD))
.usage(AnsiColor::Green.on_default().effects(Effects::BOLD))
@@ -144,14 +122,8 @@ pub(crate) struct GlobalArgs {
pub(crate) cd: Option,
/// Whether to use color in output.
- #[arg(
- global = true,
- long,
- value_enum,
- env = EnvVars::PREK_COLOR,
- default_value_t = ColorChoice::Auto,
- )]
- pub(crate) color: ColorChoice,
+ #[arg(global = true, long, value_enum)]
+ pub(crate) color: Option,
/// Refresh all cached data.
#[arg(global = true, long)]
@@ -198,6 +170,13 @@ pub(crate) struct GlobalArgs {
pub show_settings: bool,
}
+impl GlobalArgs {
+ /// Build CLI overrides from the parsed arguments.
+ pub fn cli_overrides(&self) -> CliOverrides {
+ CliOverrides::new().color(self.color)
+ }
+}
+
#[derive(Debug, Subcommand)]
pub(crate) enum Command {
/// Install the prek git hook.
diff --git a/src/main.rs b/src/main.rs
index 7f3be6990..6cda7ab34 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -23,6 +23,7 @@ use crate::cli::{CacheCommand, CacheNamespace, Cli, Command, ExitStatus};
use crate::cli::{SelfCommand, SelfNamespace, SelfUpdateArgs};
use crate::printer::Printer;
use crate::run::USE_COLOR;
+use crate::settings::Settings;
use crate::store::Store;
mod archive;
@@ -40,6 +41,7 @@ mod process;
#[cfg(all(unix, feature = "profiler"))]
mod profiler;
mod run;
+pub mod settings;
mod store;
mod version;
mod warnings;
@@ -141,7 +143,20 @@ async fn run(mut cli: Cli) -> Result {
// Enabled ANSI colors on Windows.
let _ = anstyle_query::windows::enable_ansi_colors();
- ColorChoice::write_global(cli.globals.color.into());
+ // Determine working directory early (--cd flag or current dir)
+ let working_dir = cli
+ .globals
+ .cd
+ .clone()
+ .unwrap_or_else(|| std::env::current_dir().unwrap_or_default());
+
+ // Initialize settings from all sources (env vars, pyproject.toml, CLI overrides)
+ Settings::init_with_cli(&working_dir, cli.globals.cli_overrides());
+
+ let settings = Settings::get();
+
+ // Set color from resolved settings (CLI > pyproject.toml > env var > default)
+ ColorChoice::write_global(settings.resolved_color().into());
let store = Store::from_settings()?;
let log_file = LogFile::from_args(cli.globals.log_file.clone(), cli.globals.no_log_file);
diff --git a/src/settings.rs b/src/settings.rs
new file mode 100644
index 000000000..3e02bd5b2
--- /dev/null
+++ b/src/settings.rs
@@ -0,0 +1,362 @@
+//! Unified configuration settings for prek.
+//!
+//! Settings are resolved from multiple sources with the following precedence (highest to lowest):
+//! 1. CLI flags (merged via `CliOverrides`)
+//! 2. `pyproject.toml` `[tool.prek]` section
+//! 3. Environment variables (`PREK_*`)
+//! 4. Built-in defaults
+
+use std::path::{Path, PathBuf};
+use std::sync::{LazyLock, RwLock};
+
+use prek_consts::env_vars::EnvVars;
+use serde::Deserialize;
+
+/// Global settings instance, initialized lazily.
+///
+/// Call `Settings::init_with_cli()` early in main to set the working directory,
+/// or it will default to the current directory.
+static SETTINGS: LazyLock> = LazyLock::new(|| RwLock::new(Settings::default()));
+
+/// Check if settings have been initialized
+static INITIALIZED: LazyLock> = LazyLock::new(|| RwLock::new(false));
+
+/// Prek configuration settings.
+#[derive(Debug, Clone, Default, PartialEq, Eq)]
+#[allow(clippy::struct_excessive_bools)]
+pub struct Settings {
+ /// Hook IDs to skip (equivalent to `PREK_SKIP`).
+ pub skip: Vec,
+ /// Override the prek data directory (equivalent to `PREK_HOME`).
+ pub home: Option,
+ /// Control colored output: "auto", "always", or "never" (equivalent to `PREK_COLOR`).
+ pub color: Option,
+ /// Allow running without a `.pre-commit-config.yaml` (equivalent to `PREK_ALLOW_NO_CONFIG`).
+ pub allow_no_config: bool,
+ /// Disable parallelism for installs and runs (equivalent to `PREK_NO_CONCURRENCY`).
+ pub no_concurrency: bool,
+ /// Disable Rust-native built-in hooks (equivalent to `PREK_NO_FAST_PATH`).
+ pub no_fast_path: bool,
+ /// Control how uv is installed (equivalent to `PREK_UV_SOURCE`).
+ pub uv_source: Option,
+ /// Use system's trusted store instead of bundled roots (equivalent to `PREK_NATIVE_TLS`).
+ pub native_tls: bool,
+ /// Container runtime to use: "auto", "docker", or "podman" (equivalent to `PREK_CONTAINER_RUNTIME`).
+ pub container_runtime: Option,
+}
+
+/// Settings as parsed from pyproject.toml `[tool.prek]`
+#[derive(Debug, Default, Deserialize)]
+#[serde(default, rename_all = "kebab-case")]
+#[allow(clippy::struct_excessive_bools)]
+struct PyProjectSettings {
+ skip: Vec,
+ home: Option,
+ color: Option,
+ allow_no_config: bool,
+ no_concurrency: bool,
+ no_fast_path: bool,
+ uv_source: Option,
+ native_tls: bool,
+ container_runtime: Option,
+}
+
+/// Wrapper to extract `[tool.prek]` from pyproject.toml
+#[derive(Debug, Deserialize)]
+struct PyProjectToml {
+ tool: Option,
+}
+
+#[derive(Debug, Deserialize)]
+struct PyProjectTool {
+ prek: Option,
+}
+
+/// Color output choice.
+#[derive(Debug, Clone, Copy, Default, PartialEq, Eq, Deserialize, clap::ValueEnum)]
+#[serde(rename_all = "lowercase")]
+pub enum ColorChoice {
+ /// Enables colored output only when the output is going to a terminal or TTY with support.
+ #[default]
+ Auto,
+ /// Enables colored output regardless of the detected environment.
+ Always,
+ /// Disables colored output.
+ Never,
+}
+
+impl std::fmt::Display for ColorChoice {
+ fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
+ match self {
+ Self::Auto => write!(f, "auto"),
+ Self::Always => write!(f, "always"),
+ Self::Never => write!(f, "never"),
+ }
+ }
+}
+
+impl From for anstream::ColorChoice {
+ fn from(value: ColorChoice) -> Self {
+ match value {
+ ColorChoice::Auto => Self::Auto,
+ ColorChoice::Always => Self::Always,
+ ColorChoice::Never => Self::Never,
+ }
+ }
+}
+
+impl std::str::FromStr for ColorChoice {
+ type Err = String;
+ fn from_str(s: &str) -> Result {
+ match s.to_lowercase().as_str() {
+ "auto" => Ok(Self::Auto),
+ "always" => Ok(Self::Always),
+ "never" => Ok(Self::Never),
+ _ => Err(format!("invalid color choice: {s}")),
+ }
+ }
+}
+
+/// Container runtime choice.
+#[derive(Debug, Clone, Copy, Default, PartialEq, Eq, Deserialize, clap::ValueEnum)]
+#[serde(rename_all = "lowercase")]
+pub enum ContainerRuntime {
+ /// Auto-detect available runtime.
+ #[default]
+ Auto,
+ /// Use Docker.
+ Docker,
+ /// Use Podman.
+ Podman,
+}
+
+impl std::str::FromStr for ContainerRuntime {
+ type Err = String;
+ fn from_str(s: &str) -> Result {
+ match s.to_lowercase().as_str() {
+ "auto" => Ok(Self::Auto),
+ "docker" => Ok(Self::Docker),
+ "podman" => Ok(Self::Podman),
+ _ => Err(format!("invalid container runtime: {s}")),
+ }
+ }
+}
+
+impl std::fmt::Display for ContainerRuntime {
+ fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
+ match self {
+ Self::Auto => write!(f, "auto"),
+ Self::Docker => write!(f, "docker"),
+ Self::Podman => write!(f, "podman"),
+ }
+ }
+}
+
+/// CLI overrides that take highest precedence.
+///
+/// This struct contains only the fields that can be set via CLI flags.
+/// Fields are all optional - `None` means "use value from other sources".
+#[derive(Copy, Debug, Clone, Default)]
+pub struct CliOverrides {
+ pub color: Option,
+}
+
+impl CliOverrides {
+ pub fn new() -> Self {
+ Self::default()
+ }
+
+ #[must_use]
+ pub fn color(mut self, color: Option) -> Self {
+ self.color = color;
+ self
+ }
+}
+
+impl Settings {
+ /// Initialize settings with CLI overrides.
+ ///
+ /// This should be called early in `main()` before any settings are accessed.
+ pub fn init_with_cli(working_dir: &Path, cli: CliOverrides) {
+ let settings = Self::load(working_dir, cli);
+ *SETTINGS.write().expect("settings lock poisoned") = settings;
+ *INITIALIZED.write().expect("initialized lock poisoned") = true;
+ }
+
+ /// Get the global settings instance.
+ ///
+ /// If settings haven't been initialized, this will initialize them
+ /// using the current directory.
+ pub fn get() -> Settings {
+ {
+ let initialized = *INITIALIZED.read().expect("initialized lock poisoned");
+ if !initialized {
+ let cwd = std::env::current_dir().unwrap_or_default();
+ Self::init_with_cli(&cwd, CliOverrides::default());
+ }
+ }
+ SETTINGS.read().expect("settings lock poisoned").clone()
+ }
+
+ /// Load and merge settings from all sources.
+ fn load(start_dir: &Path, cli: CliOverrides) -> Self {
+ // Start with pyproject.toml settings (or defaults)
+ let pyproject = Self::load_pyproject(start_dir).unwrap_or_default();
+
+ // Layer env vars on top, then CLI
+ Settings {
+ skip: env_list("PREK_SKIP")
+ .or_else(|| env_list("SKIP"))
+ .unwrap_or(pyproject.skip),
+ home: env_path("PREK_HOME").or(pyproject.home),
+ color: cli
+ .color
+ .or_else(|| env_parse::("PREK_COLOR"))
+ .or(pyproject.color),
+ allow_no_config: env_bool("PREK_ALLOW_NO_CONFIG").unwrap_or(pyproject.allow_no_config),
+ no_concurrency: env_bool("PREK_NO_CONCURRENCY").unwrap_or(pyproject.no_concurrency),
+ no_fast_path: env_bool("PREK_NO_FAST_PATH").unwrap_or(pyproject.no_fast_path),
+ uv_source: env_string("PREK_UV_SOURCE").or(pyproject.uv_source),
+ native_tls: env_bool("PREK_NATIVE_TLS").unwrap_or(pyproject.native_tls),
+ container_runtime: env_parse("PREK_CONTAINER_RUNTIME").or(pyproject.container_runtime),
+ }
+ }
+
+ /// Walk up the directory tree to find and parse pyproject.toml
+ fn load_pyproject(start_dir: &Path) -> Option {
+ let mut dir = Some(start_dir);
+ while let Some(d) = dir {
+ if let Ok(content) = std::fs::read_to_string(d.join("pyproject.toml")) {
+ if let Ok(parsed) = toml::from_str::(&content) {
+ if let Some(settings) = parsed.tool.and_then(|t| t.prek) {
+ return Some(settings);
+ }
+ }
+ }
+ dir = d.parent();
+ }
+ None
+ }
+
+ /// Check if a hook should be skipped.
+ pub fn should_skip(&self, hook_id: &str) -> bool {
+ self.skip.iter().any(|s| s == hook_id)
+ }
+
+ /// Get the resolved color choice.
+ pub fn resolved_color(&self) -> ColorChoice {
+ self.color.unwrap_or_default()
+ }
+
+ /// Get the resolved container runtime.
+ pub fn resolved_container_runtime(&self) -> ContainerRuntime {
+ self.container_runtime.unwrap_or_default()
+ }
+}
+
+// Simple env var helpers
+fn env_string(key: &str) -> Option {
+ EnvVars::var(key).ok()
+}
+
+fn env_path(key: &str) -> Option {
+ env_string(key).map(PathBuf::from)
+}
+
+fn env_bool(key: &str) -> Option {
+ EnvVars::var_as_bool(key)
+}
+
+fn env_parse(key: &str) -> Option {
+ env_string(key).and_then(|s| s.parse().ok())
+}
+
+fn env_list(key: &str) -> Option> {
+ env_string(key).map(|s| {
+ s.split(',')
+ .map(|p| p.trim().to_string())
+ .filter(|p| !p.is_empty())
+ .collect()
+ })
+}
+
+#[cfg(test)]
+mod tests {
+ use super::*;
+ use std::io::Write;
+ use tempfile::TempDir;
+
+ #[test]
+ fn test_default_settings() {
+ let settings = Settings::default();
+ assert!(settings.skip.is_empty());
+ assert!(settings.home.is_none());
+ assert!(!settings.no_concurrency);
+ }
+
+ #[test]
+ fn test_pyproject_loading() {
+ let dir = TempDir::new().unwrap();
+ let pyproject = dir.path().join("pyproject.toml");
+
+ let mut file = std::fs::File::create(&pyproject).unwrap();
+ write!(
+ file,
+ r#"
+[tool.prek]
+skip = ["black", "ruff"]
+no-concurrency = true
+color = "always"
+"#
+ )
+ .unwrap();
+
+ let settings = Settings::load(dir.path(), CliOverrides::default());
+ assert_eq!(settings.skip, vec!["black", "ruff"]);
+ assert!(settings.no_concurrency);
+ assert_eq!(settings.color, Some(ColorChoice::Always));
+ }
+
+ #[test]
+ fn test_walks_up_directory_tree() {
+ let dir = TempDir::new().unwrap();
+ let pyproject = dir.path().join("pyproject.toml");
+
+ let mut file = std::fs::File::create(&pyproject).unwrap();
+ write!(
+ file,
+ r#"
+[tool.prek]
+skip = ["parent-hook"]
+"#
+ )
+ .unwrap();
+
+ std::fs::create_dir_all(dir.path().join("subdir/nested")).unwrap();
+
+ let settings = Settings::load(&dir.path().join("subdir/nested"), CliOverrides::default());
+ assert_eq!(settings.skip, vec!["parent-hook"]);
+ }
+
+ #[test]
+ fn test_cli_overrides_pyproject() {
+ let dir = TempDir::new().unwrap();
+ let pyproject = dir.path().join("pyproject.toml");
+
+ let mut file = std::fs::File::create(&pyproject).unwrap();
+ write!(
+ file,
+ r#"
+[tool.prek]
+color = "auto"
+"#
+ )
+ .unwrap();
+
+ let settings = Settings::load(
+ dir.path(),
+ CliOverrides::new().color(Some(ColorChoice::Always)),
+ );
+ assert_eq!(settings.color, Some(ColorChoice::Always));
+ }
+}
diff --git a/src/store.rs b/src/store.rs
index 9ba56352a..39b3a2761 100644
--- a/src/store.rs
+++ b/src/store.rs
@@ -9,13 +9,12 @@ use futures::StreamExt;
use thiserror::Error;
use tracing::{debug, warn};
-use prek_consts::env_vars::EnvVars;
-
use crate::config::RemoteRepo;
use crate::fs::LockedFile;
use crate::git::clone_repo;
use crate::hook::InstallInfo;
use crate::run::CONCURRENCY;
+use crate::settings::Settings;
use crate::workspace::HookInitReporter;
#[derive(Debug, Error)]
@@ -41,13 +40,15 @@ impl Store {
Self { path: path.into() }
}
- /// Create a store from environment variables or default paths.
+ /// Create a store from settings or default paths.
pub(crate) fn from_settings() -> Result {
- let path = if let Some(path) = EnvVars::var_os(EnvVars::PREK_HOME) {
- Some(path.into())
+ let settings = Settings::get();
+
+ let path = if let Some(home) = settings.home {
+ Some(home)
} else {
etcetera::choose_base_strategy()
- .map(|path| path.cache_dir().join("prek"))
+ .map(|strategy| strategy.cache_dir().join("prek"))
.ok()
};