From 67d262f923d42a20b1327832239089c4621b4ac5 Mon Sep 17 00:00:00 2001 From: Emily Date: Mon, 10 Feb 2025 20:54:52 +0000 Subject: [PATCH] nix: catch reads of unmanaged defaults MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit When we’re not managing the Nix installation, these defaults aren’t used out of the box and won’t accurately represent the state of any unmanaged Nix or the desired Nix package, so reading the option defaults is a bug. This was previously a warning for `nix.package` and a silent failure for all the others. Now that all the problematic accesses in nix-darwin have been appropriately conditionalized, and since a throw gives a backtrace where a warning doesn’t, give throwing defaults to all the `nix.*` options that don’t reflect reality and that that modules shouldn’t be reading when `nix.enable` is off. I’m not in love with the implementation strategy here… ideally we’d think of something better than this and then upstream it to NixOS. `nix.nrBuildUsers` growing a fake default that is never used is particularly unfortunate. But this should hopefully catch mistakes in module code reasonably reliably. (cherry picked from commit cd445c546561d5ca4e9124cb4668ce80939ac0c9) --- modules/nix/default.nix | 43 +++++++++++++++++++++++++---------------- tests/nix-enable.nix | 1 - 2 files changed, 26 insertions(+), 18 deletions(-) diff --git a/modules/nix/default.nix b/modules/nix/default.nix index 817bfc0ef..22f7fe688 100644 --- a/modules/nix/default.nix +++ b/modules/nix/default.nix @@ -154,6 +154,14 @@ let }) ]; + managedDefault = name: default: { + default = if cfg.enable then default else throw '' + ${name}: accessed when `nix.enable` is off; this is a bug in + nix-darwin or a third‐party module + ''; + defaultText = default; + }; + in { @@ -211,9 +219,7 @@ in package = mkOption { type = types.package; - default = warnIf (!cfg.enable) - "nix.package: accessed when `nix.enable` is off; this is a bug" - pkgs.nix; + inherit (managedDefault "nix.package" pkgs.nix) default; defaultText = literalExpression "pkgs.nix"; description = '' This option specifies the Nix package instance to use throughout the system. @@ -242,7 +248,7 @@ in distributedBuilds = mkOption { type = types.bool; - default = false; + inherit (managedDefault "nix.distributedBuilds" false) default defaultText; description = '' Whether to distribute builds to the machines listed in {option}`nix.buildMachines`. @@ -252,7 +258,7 @@ in # Not in NixOS module daemonProcessType = mkOption { type = types.enum [ "Background" "Standard" "Adaptive" "Interactive" ]; - default = "Standard"; + inherit (managedDefault "nix.daemonProcessType" "Standard") default defaultText; description = '' Nix daemon process resource limits class. These limits propagate to build processes. `Standard` is the default process type @@ -267,7 +273,7 @@ in # Not in NixOS module daemonIOLowPriority = mkOption { type = types.bool; - default = false; + inherit (managedDefault "nix.daemonIOLowPriority" false) default defaultText; description = '' Whether the Nix daemon process should considered to be low priority when doing file system I/O. @@ -395,7 +401,7 @@ in }; }; }); - default = [ ]; + inherit (managedDefault "nix.buildMachines" [ ]) default defaultText; description = '' This option lists the machines to be used if distributed builds are enabled (see {option}`nix.distributedBuilds`). @@ -409,7 +415,7 @@ in envVars = mkOption { type = types.attrs; internal = true; - default = { }; + inherit (managedDefault "nix.envVars" { }) default defaultText; description = "Environment variables used by Nix."; }; @@ -424,6 +430,7 @@ in nrBuildUsers = mkOption { type = types.int; + inherit (managedDefault "nix.nrBuildUsers" 0) default defaultText; description = '' Number of `nixbld` user accounts created to perform secure concurrent builds. If you receive an error @@ -451,11 +458,13 @@ in # Definition differs substantially from NixOS module nixPath = mkOption { type = nixPathType; - default = lib.optionals cfg.channel.enable [ - # Include default path . - { darwin-config = "${config.environment.darwinConfig}"; } - "/nix/var/nix/profiles/per-user/root/channels" - ]; + inherit (managedDefault "nix.nixPath" ( + lib.optionals cfg.channel.enable [ + # Include default path . + { darwin-config = "${config.environment.darwinConfig}"; } + "/nix/var/nix/profiles/per-user/root/channels" + ] + )) default; defaultText = lib.literalExpression '' lib.optionals cfg.channel.enable [ @@ -477,7 +486,7 @@ in checkConfig = mkOption { type = types.bool; - default = true; + inherit (managedDefault "nix.checkConfig" true) default defaultText; description = '' If enabled (the default), checks for data type mismatches and that Nix can parse the generated nix.conf. @@ -538,7 +547,7 @@ in }; } )); - default = { }; + inherit (managedDefault "nix.registry" { }) default defaultText; description = '' A system-wide flake registry. ''; @@ -546,7 +555,7 @@ in extraOptions = mkOption { type = types.lines; - default = ""; + inherit (managedDefault "nix.extraOptions" "") default defaultText; example = '' keep-outputs = true keep-derivations = true @@ -715,7 +724,7 @@ in }; }; }; - default = { }; + inherit (managedDefault "nix.settings" { }) default defaultText; description = '' Configuration for Nix, see diff --git a/tests/nix-enable.nix b/tests/nix-enable.nix index 0828834f1..e052aa2f4 100644 --- a/tests/nix-enable.nix +++ b/tests/nix-enable.nix @@ -2,7 +2,6 @@ { nix.enable = false; - nix.package = throw "`nix.package` used when `nix.enable` is turned off"; test = '' printf >&2 'checking for unexpected Nix binary in /sw/bin\n'