diff options
author | Alyssa Ross <hi@alyssa.is> | 2024-02-13 12:25:07 +0100 |
---|---|---|
committer | Alyssa Ross <hi@alyssa.is> | 2024-02-13 12:25:07 +0100 |
commit | a5e1520e4538e29ecfbd4b168306f890566d7bfd (patch) | |
tree | 28099c268b5d4b1e33c2b29f0714c45f0b961382 /nixpkgs/lib | |
parent | 822f7c15c04567fbdc27020e862ea2b70cfbf8eb (diff) | |
parent | 3560d1c8269d0091b9aae10731b5e85274b7bbc1 (diff) | |
download | nixlib-a5e1520e4538e29ecfbd4b168306f890566d7bfd.tar nixlib-a5e1520e4538e29ecfbd4b168306f890566d7bfd.tar.gz nixlib-a5e1520e4538e29ecfbd4b168306f890566d7bfd.tar.bz2 nixlib-a5e1520e4538e29ecfbd4b168306f890566d7bfd.tar.lz nixlib-a5e1520e4538e29ecfbd4b168306f890566d7bfd.tar.xz nixlib-a5e1520e4538e29ecfbd4b168306f890566d7bfd.tar.zst nixlib-a5e1520e4538e29ecfbd4b168306f890566d7bfd.zip |
Merge branch 'nixos-unstable-small' of https://github.com/NixOS/nixpkgs
Conflicts: nixpkgs/nixos/modules/services/mail/rss2email.nix nixpkgs/pkgs/build-support/go/module.nix
Diffstat (limited to 'nixpkgs/lib')
23 files changed, 246 insertions, 36 deletions
diff --git a/nixpkgs/lib/attrsets.nix b/nixpkgs/lib/attrsets.nix index 99b686918453..0e896a93156d 100644 --- a/nixpkgs/lib/attrsets.nix +++ b/nixpkgs/lib/attrsets.nix @@ -3,7 +3,7 @@ let inherit (builtins) head tail length; - inherit (lib.trivial) id mergeAttrs; + inherit (lib.trivial) id mergeAttrs warn; inherit (lib.strings) concatStringsSep concatMapStringsSep escapeNixIdentifier sanitizeDerivationName; inherit (lib.lists) foldr foldl' concatMap concatLists elemAt all partition groupBy take foldl; in @@ -1197,9 +1197,10 @@ rec { (x // y) // mask; # DEPRECATED - zipWithNames = zipAttrsWithNames; + zipWithNames = warn + "lib.zipWithNames is a deprecated alias of lib.zipAttrsWithNames." zipAttrsWithNames; # DEPRECATED - zip = builtins.trace - "lib.zip is deprecated, use lib.zipAttrsWith instead" zipAttrsWith; + zip = warn + "lib.zip is a deprecated alias of lib.zipAttrsWith." zipAttrsWith; } diff --git a/nixpkgs/lib/default.nix b/nixpkgs/lib/default.nix index f6c94ae91634..a17307be6e07 100644 --- a/nixpkgs/lib/default.nix +++ b/nixpkgs/lib/default.nix @@ -116,7 +116,7 @@ let inherit (self.customisation) overrideDerivation makeOverridable callPackageWith callPackagesWith extendDerivation hydraJob makeScope makeScopeWithSplicing makeScopeWithSplicing'; - inherit (self.derivations) lazyDerivation; + inherit (self.derivations) lazyDerivation optionalDrvAttr; inherit (self.meta) addMetaAttrs dontDistribute setName updateName appendToName mapDerivationAttrset setPrio lowPrio lowPrioSet hiPrio hiPrioSet getLicenseFromSpdxId getExe getExe'; diff --git a/nixpkgs/lib/derivations.nix b/nixpkgs/lib/derivations.nix index 5b7ed1868e86..44b727ee31cc 100644 --- a/nixpkgs/lib/derivations.nix +++ b/nixpkgs/lib/derivations.nix @@ -98,4 +98,30 @@ in # `lazyDerivation` caller knew a shortcut, be taken from there. meta = args.meta or checked.meta; } // passthru; + + /* Conditionally set a derivation attribute. + + Because `mkDerivation` sets `__ignoreNulls = true`, a derivation + attribute set to `null` will not impact the derivation output hash. + Thus, this function passes through its `value` argument if the `cond` + is `true`, but returns `null` if not. + + Type: optionalDrvAttr :: Bool -> a -> a | Null + + Example: + (stdenv.mkDerivation { + name = "foo"; + x = optionalDrvAttr true 1; + y = optionalDrvAttr false 1; + }).drvPath == (stdenv.mkDerivation { + name = "foo"; + x = 1; + }).drvPath + => true + */ + optionalDrvAttr = + # Condition + cond: + # Attribute value + value: if cond then value else null; } diff --git a/nixpkgs/lib/fileset/internal.nix b/nixpkgs/lib/fileset/internal.nix index 4059d2e24426..f4fcc83e1012 100644 --- a/nixpkgs/lib/fileset/internal.nix +++ b/nixpkgs/lib/fileset/internal.nix @@ -5,6 +5,7 @@ let isAttrs isPath isString + nixVersion pathExists readDir split @@ -17,6 +18,7 @@ let attrNames attrValues mapAttrs + optionalAttrs zipAttrsWith ; @@ -56,6 +58,7 @@ let substring stringLength hasSuffix + versionAtLeast ; inherit (lib.trivial) @@ -840,6 +843,10 @@ rec { # https://github.com/NixOS/nix/commit/55cefd41d63368d4286568e2956afd535cb44018 _fetchGitSubmodulesMinver = "2.4"; + # Support for `builtins.fetchGit` with `shallow = true` was introduced in 2.4 + # https://github.com/NixOS/nix/commit/d1165d8791f559352ff6aa7348e1293b2873db1c + _fetchGitShallowMinver = "2.4"; + # Mirrors the contents of a Nix store path relative to a local path as a file set. # Some notes: # - The store path is read at evaluation time. @@ -894,7 +901,17 @@ rec { # However a simpler alternative still would be [a builtins.gitLsFiles](https://github.com/NixOS/nix/issues/2944). fetchResult = fetchGit ({ url = path; - } // extraFetchGitAttrs); + } + # In older Nix versions, repositories were always assumed to be deep clones, which made `fetchGit` fail for shallow clones + # For newer versions this was fixed, but the `shallow` flag is required. + # The only behavioral difference is that for shallow clones, `fetchGit` doesn't return a `revCount`, + # which we don't need here, so it's fine to always pass it. + + # Unfortunately this means older Nix versions get a poor error message for shallow repositories, and there's no good way to improve that. + # Checking for `.git/shallow` doesn't seem worth it, especially since that's more of an implementation detail, + # and would also require more code to handle worktrees where `.git` is a file. + // optionalAttrs (versionAtLeast nixVersion _fetchGitShallowMinver) { shallow = true; } + // extraFetchGitAttrs); in # We can identify local working directories by checking for .git, # see https://git-scm.com/docs/gitrepository-layout#_description. diff --git a/nixpkgs/lib/fileset/tests.sh b/nixpkgs/lib/fileset/tests.sh index e809aef6935a..af8338eb7855 100755 --- a/nixpkgs/lib/fileset/tests.sh +++ b/nixpkgs/lib/fileset/tests.sh @@ -1439,6 +1439,19 @@ if [[ -n "$fetchGitSupportsSubmodules" ]]; then fi rm -rf -- * +# shallow = true is not supported on all Nix versions +# and older versions don't support shallow clones at all +if [[ "$(nix-instantiate --eval --expr "$prefixExpression (versionAtLeast builtins.nixVersion _fetchGitShallowMinver)")" == true ]]; then + createGitRepo full + # Extra commit such that there's a commit that won't be in the shallow clone + git -C full commit --allow-empty -q -m extra + git clone -q --depth 1 "file://${PWD}/full" shallow + cd shallow + checkGitTracked + cd .. + rm -rf -- * +fi + # Go through all stages of Git files # See https://www.git-scm.com/book/en/v2/Git-Basics-Recording-Changes-to-the-Repository diff --git a/nixpkgs/lib/licenses.nix b/nixpkgs/lib/licenses.nix index 8dc01e560746..47b7005c561d 100644 --- a/nixpkgs/lib/licenses.nix +++ b/nixpkgs/lib/licenses.nix @@ -337,6 +337,11 @@ in mkLicense lset) ({ fullName = "Creative Commons Attribution 1.0"; }; + cc-by-20 = { + spdxId = "CC-BY-2.0"; + fullName = "Creative Commons Attribution 2.0"; + }; + cc-by-30 = { spdxId = "CC-BY-3.0"; fullName = "Creative Commons Attribution 3.0"; diff --git a/nixpkgs/lib/lists.nix b/nixpkgs/lib/lists.nix index 9397acf148fc..b612bc16697e 100644 --- a/nixpkgs/lib/lists.nix +++ b/nixpkgs/lib/lists.nix @@ -2,7 +2,7 @@ { lib }: let inherit (lib.strings) toInt; - inherit (lib.trivial) compare min id; + inherit (lib.trivial) compare min id warn; inherit (lib.attrsets) mapAttrs; inherit (lib.lists) sort; in @@ -848,8 +848,8 @@ rec { crossLists (x:y: "${toString x}${toString y}") [[1 2] [3 4]] => [ "13" "14" "23" "24" ] */ - crossLists = builtins.trace - "lib.crossLists is deprecated, use lib.cartesianProductOfSets instead" + crossLists = warn + "lib.crossLists is deprecated, use lib.cartesianProductOfSets instead." (f: foldl (fs: args: concatMap (f: map f args) fs) [f]); diff --git a/nixpkgs/lib/modules.nix b/nixpkgs/lib/modules.nix index 64939a1eae81..0c484fa684aa 100644 --- a/nixpkgs/lib/modules.nix +++ b/nixpkgs/lib/modules.nix @@ -1256,7 +1256,7 @@ let (opt.highestPrio or defaultOverridePriority) (f opt.value); - doRename = { from, to, visible, warn, use, withPriority ? true }: + doRename = { from, to, visible, warn, use, withPriority ? true, condition ? true }: { config, options, ... }: let fromOpt = getAttrFromPath from options; @@ -1272,7 +1272,7 @@ let } // optionalAttrs (toType != null) { type = toType; }); - config = mkMerge [ + config = mkIf condition (mkMerge [ (optionalAttrs (options ? warnings) { warnings = optional (warn && fromOpt.isDefined) "The option `${showOption from}' defined in ${showFiles fromOpt.files} has been renamed to `${showOption to}'."; @@ -1280,7 +1280,7 @@ let (if withPriority then mkAliasAndWrapDefsWithPriority (setAttrByPath to) fromOpt else mkAliasAndWrapDefinitions (setAttrByPath to) fromOpt) - ]; + ]); }; /* Use this function to import a JSON file as NixOS configuration. diff --git a/nixpkgs/lib/options.nix b/nixpkgs/lib/options.nix index 9c10dfc8b36a..0d1d90efe217 100644 --- a/nixpkgs/lib/options.nix +++ b/nixpkgs/lib/options.nix @@ -254,13 +254,31 @@ rec { else if all isInt list && all (x: x == head list) list then head list else throw "Cannot merge definitions of `${showOption loc}'. Definition values:${showDefs defs}"; + /* + Require a single definition. + + WARNING: Does not perform nested checks, as this does not run the merge function! + */ mergeOneOption = mergeUniqueOption { message = ""; }; - mergeUniqueOption = { message }: loc: defs: - if length defs == 1 - then (head defs).value - else assert length defs > 1; - throw "The option `${showOption loc}' is defined multiple times while it's expected to be unique.\n${message}\nDefinition values:${showDefs defs}\n${prioritySuggestion}"; + /* + Require a single definition. + + NOTE: When the type is not checked completely by check, pass a merge function for further checking (of sub-attributes, etc). + */ + mergeUniqueOption = args@{ + message, + # WARNING: the default merge function assumes that the definition is a valid (option) value. You MUST pass a merge function if the return value needs to be + # - type checked beyond what .check does (which should be very litte; only on the value head; not attribute values, etc) + # - if you want attribute values to be checked, or list items + # - if you want coercedTo-like behavior to work + merge ? loc: defs: (head defs).value }: + loc: defs: + if length defs == 1 + then merge loc defs + else + assert length defs > 1; + throw "The option `${showOption loc}' is defined multiple times while it's expected to be unique.\n${message}\nDefinition values:${showDefs defs}\n${prioritySuggestion}"; /* "Merge" option definitions by checking that they all have the same value. */ mergeEqualOption = loc: defs: @@ -379,7 +397,7 @@ rec { if ! isString text then throw "literalExpression expects a string." else { _type = "literalExpression"; inherit text; }; - literalExample = lib.warn "literalExample is deprecated, use literalExpression instead, or use literalMD for a non-Nix description." literalExpression; + literalExample = lib.warn "lib.literalExample is deprecated, use lib.literalExpression instead, or use lib.literalMD for a non-Nix description." literalExpression; /* Transition marker for documentation that's already migrated to markdown syntax. This is a no-op and no longer needed. diff --git a/nixpkgs/lib/strings.nix b/nixpkgs/lib/strings.nix index 49654d8abaa7..7083576dd529 100644 --- a/nixpkgs/lib/strings.nix +++ b/nixpkgs/lib/strings.nix @@ -561,7 +561,7 @@ rec { [""" "'" "<" ">" "&"]; # warning added 12-12-2022 - replaceChars = lib.warn "replaceChars is a deprecated alias of replaceStrings, replace usages of it with replaceStrings." builtins.replaceStrings; + replaceChars = lib.warn "lib.replaceChars is a deprecated alias of lib.replaceStrings." builtins.replaceStrings; # Case conversion utilities. lowerChars = stringToCharacters "abcdefghijklmnopqrstuvwxyz"; @@ -1133,7 +1133,7 @@ rec { "/prefix/nix-profiles-library-paths.patch" "/prefix/compose-search-path.patch" ] */ - readPathsFromFile = lib.warn "lib.readPathsFromFile is deprecated, use a list instead" + readPathsFromFile = lib.warn "lib.readPathsFromFile is deprecated, use a list instead." (rootPath: file: let lines = lib.splitString "\n" (readFile file); diff --git a/nixpkgs/lib/systems/inspect.nix b/nixpkgs/lib/systems/inspect.nix index 38ca9967cdde..c6a33781ae28 100644 --- a/nixpkgs/lib/systems/inspect.nix +++ b/nixpkgs/lib/systems/inspect.nix @@ -48,6 +48,7 @@ rec { isRiscV64 = { cpu = { family = "riscv"; bits = 64; }; }; isRx = { cpu = { family = "rx"; }; }; isSparc = { cpu = { family = "sparc"; }; }; + isSparc64 = { cpu = { family = "sparc"; bits = 64; }; }; isWasm = { cpu = { family = "wasm"; }; }; isMsp430 = { cpu = { family = "msp430"; }; }; isVc4 = { cpu = { family = "vc4"; }; }; diff --git a/nixpkgs/lib/tests/misc.nix b/nixpkgs/lib/tests/misc.nix index 3059878ba069..193e68a96933 100644 --- a/nixpkgs/lib/tests/misc.nix +++ b/nixpkgs/lib/tests/misc.nix @@ -1902,7 +1902,7 @@ runTests { expected = true; }; - # lazyDerivation + # DERIVATIONS testLazyDerivationIsLazyInDerivationForAttrNames = { expr = attrNames (lazyDerivation { @@ -1955,6 +1955,24 @@ runTests { expected = derivation; }; + testOptionalDrvAttr = let + mkDerivation = args: derivation (args // { + builder = "builder"; + system = "system"; + __ignoreNulls = true; + }); + in { + expr = (mkDerivation { + name = "foo"; + x = optionalDrvAttr true 1; + y = optionalDrvAttr false 1; + }).drvPath; + expected = (mkDerivation { + name = "foo"; + x = 1; + }).drvPath; + }; + testTypeDescriptionInt = { expr = (with types; int).description; expected = "signed integer"; diff --git a/nixpkgs/lib/tests/modules.sh b/nixpkgs/lib/tests/modules.sh index a90ff4ad9a2f..b3bbdf9485ac 100755 --- a/nixpkgs/lib/tests/modules.sh +++ b/nixpkgs/lib/tests/modules.sh @@ -101,6 +101,7 @@ checkConfigError 'It seems as if you.re trying to declare an option by placing i checkConfigError 'It seems as if you.re trying to declare an option by placing it into .config. rather than .options.' config.nest.wrong2 ./error-mkOption-in-config.nix checkConfigError 'The option .sub.wrong2. does not exist. Definition values:' config.sub ./error-mkOption-in-submodule-config.nix checkConfigError '.*This can happen if you e.g. declared your options in .types.submodule.' config.sub ./error-mkOption-in-submodule-config.nix +checkConfigError '.*A definition for option .bad. is not of type .non-empty .list of .submodule...\.' config.bad ./error-nonEmptyListOf-submodule.nix # types.pathInStore checkConfigOutput '".*/store/0lz9p8xhf89kb1c1kk6jxrzskaiygnlh-bash-5.2-p15.drv"' config.pathInStore.ok1 ./types.nix @@ -406,6 +407,16 @@ checkConfigOutput "{}" config.submodule.a ./emptyValues.nix checkConfigError 'The option .int.a. is used but not defined' config.int.a ./emptyValues.nix checkConfigError 'The option .nonEmptyList.a. is used but not defined' config.nonEmptyList.a ./emptyValues.nix +# types.unique +# requires a single definition +checkConfigError 'The option .examples\.merged. is defined multiple times while it.s expected to be unique' config.examples.merged.a ./types-unique.nix +# user message is printed +checkConfigError 'We require a single definition, because seeing the whole value at once helps us maintain critical invariants of our system.' config.examples.merged.a ./types-unique.nix +# let the inner merge function check the values (on demand) +checkConfigError 'A definition for option .examples\.badLazyType\.a. is not of type .string.' config.examples.badLazyType.a ./types-unique.nix +# overriding still works (unlike option uniqueness) +checkConfigOutput '^"bee"$' config.examples.override.b ./types-unique.nix + ## types.raw checkConfigOutput '^true$' config.unprocessedNestingEvaluates.success ./raw.nix checkConfigOutput "10" config.processedToplevel ./raw.nix @@ -464,6 +475,9 @@ checkConfigOutput '^1234$' config.c.d.e ./doRename-basic.nix checkConfigOutput '^"The option `a\.b. defined in `.*/doRename-warnings\.nix. has been renamed to `c\.d\.e.\."$' \ config.result \ ./doRename-warnings.nix +checkConfigOutput "^true$" config.result ./doRename-condition.nix ./doRename-condition-enable.nix +checkConfigOutput "^true$" config.result ./doRename-condition.nix ./doRename-condition-no-enable.nix +checkConfigOutput "^true$" config.result ./doRename-condition.nix ./doRename-condition-migrated.nix # Anonymous modules get deduplicated by key checkConfigOutput '^"pear"$' config.once.raw ./merge-module-with-key.nix diff --git a/nixpkgs/lib/tests/modules/doRename-condition-enable.nix b/nixpkgs/lib/tests/modules/doRename-condition-enable.nix new file mode 100644 index 000000000000..e6eabfa6f89a --- /dev/null +++ b/nixpkgs/lib/tests/modules/doRename-condition-enable.nix @@ -0,0 +1,10 @@ +{ config, lib, ... }: +{ + config = { + services.foo.enable = true; + services.foo.bar = "baz"; + result = + assert config.services.foos == { "" = { bar = "baz"; }; }; + true; + }; +} diff --git a/nixpkgs/lib/tests/modules/doRename-condition-migrated.nix b/nixpkgs/lib/tests/modules/doRename-condition-migrated.nix new file mode 100644 index 000000000000..8d21610e8ec6 --- /dev/null +++ b/nixpkgs/lib/tests/modules/doRename-condition-migrated.nix @@ -0,0 +1,10 @@ +{ config, lib, ... }: +{ + config = { + services.foos."".bar = "baz"; + result = + assert config.services.foos == { "" = { bar = "baz"; }; }; + assert config.services.foo.bar == "baz"; + true; + }; +} diff --git a/nixpkgs/lib/tests/modules/doRename-condition-no-enable.nix b/nixpkgs/lib/tests/modules/doRename-condition-no-enable.nix new file mode 100644 index 000000000000..66ec004d3147 --- /dev/null +++ b/nixpkgs/lib/tests/modules/doRename-condition-no-enable.nix @@ -0,0 +1,9 @@ +{ config, lib, options, ... }: +{ + config = { + result = + assert config.services.foos == { }; + assert ! options.services.foo.bar.isDefined; + true; + }; +} diff --git a/nixpkgs/lib/tests/modules/doRename-condition.nix b/nixpkgs/lib/tests/modules/doRename-condition.nix new file mode 100644 index 000000000000..c08b3035be6f --- /dev/null +++ b/nixpkgs/lib/tests/modules/doRename-condition.nix @@ -0,0 +1,42 @@ +/* + Simulate a migration from a single-instance `services.foo` to a multi instance + `services.foos.<name>` module, where `name = ""` serves as the legacy / + compatibility instance. + + - No instances must exist, unless one is defined in the multi-instance module, + or if the legacy enable option is set to true. + - The legacy instance options must be renamed to the new instance, if it exists. + + The relevant scenarios are tested in separate files: + - ./doRename-condition-enable.nix + - ./doRename-condition-no-enable.nix + */ +{ config, lib, ... }: +let + inherit (lib) mkOption mkEnableOption types doRename; +in +{ + options = { + services.foo.enable = mkEnableOption "foo"; + services.foos = mkOption { + type = types.attrsOf (types.submodule { + options = { + bar = mkOption { type = types.str; }; + }; + }); + default = { }; + }; + result = mkOption {}; + }; + imports = [ + (doRename { + from = [ "services" "foo" "bar" ]; + to = [ "services" "foos" "" "bar" ]; + visible = true; + warn = false; + use = x: x; + withPriority = true; + condition = config.services.foo.enable; + }) + ]; +} diff --git a/nixpkgs/lib/tests/modules/error-nonEmptyListOf-submodule.nix b/nixpkgs/lib/tests/modules/error-nonEmptyListOf-submodule.nix new file mode 100644 index 000000000000..1189e8891560 --- /dev/null +++ b/nixpkgs/lib/tests/modules/error-nonEmptyListOf-submodule.nix @@ -0,0 +1,7 @@ +{ lib, ... }: +{ + options.bad = lib.mkOption { + type = lib.types.nonEmptyListOf (lib.types.submodule { }); + default = [ ]; + }; +} diff --git a/nixpkgs/lib/tests/modules/types-unique.nix b/nixpkgs/lib/tests/modules/types-unique.nix new file mode 100644 index 000000000000..115be0126975 --- /dev/null +++ b/nixpkgs/lib/tests/modules/types-unique.nix @@ -0,0 +1,27 @@ +{ lib, ... }: +let + inherit (lib) mkOption types; +in +{ + options.examples = mkOption { + type = types.lazyAttrsOf + (types.unique + { message = "We require a single definition, because seeing the whole value at once helps us maintain critical invariants of our system."; } + (types.attrsOf types.str)); + }; + imports = [ + { examples.merged = { b = "bee"; }; } + { examples.override = lib.mkForce { b = "bee"; }; } + ]; + config.examples = { + merged = { + a = "aye"; + }; + override = { + a = "aye"; + }; + badLazyType = { + a = true; + }; + }; +} diff --git a/nixpkgs/lib/tests/packages-from-directory/c/not-a-namespace/not-a-package.nix b/nixpkgs/lib/tests/packages-from-directory/c/not-a-namespace/not-a-package.nix index e69de29bb2d1..ffcd4415b08f 100644 --- a/nixpkgs/lib/tests/packages-from-directory/c/not-a-namespace/not-a-package.nix +++ b/nixpkgs/lib/tests/packages-from-directory/c/not-a-namespace/not-a-package.nix @@ -0,0 +1 @@ +{ } diff --git a/nixpkgs/lib/tests/packages-from-directory/c/support-definitions.nix b/nixpkgs/lib/tests/packages-from-directory/c/support-definitions.nix index e69de29bb2d1..ffcd4415b08f 100644 --- a/nixpkgs/lib/tests/packages-from-directory/c/support-definitions.nix +++ b/nixpkgs/lib/tests/packages-from-directory/c/support-definitions.nix @@ -0,0 +1 @@ +{ } diff --git a/nixpkgs/lib/trivial.nix b/nixpkgs/lib/trivial.nix index b2796096e8bc..58620006de15 100644 --- a/nixpkgs/lib/trivial.nix +++ b/nixpkgs/lib/trivial.nix @@ -189,7 +189,7 @@ in { they take effect as soon as the oldest release reaches end of life. */ oldestSupportedRelease = # Update on master only. Do not backport. - 2305; + 2311; /* Whether a feature is supported in all supported releases (at the time of release branch-off, if applicable). See `oldestSupportedRelease`. */ @@ -230,7 +230,7 @@ in { else if lib.pathExists revisionFile then lib.fileContents revisionFile else default; - nixpkgsVersion = builtins.trace "`lib.nixpkgsVersion` is deprecated, use `lib.version` instead!" version; + nixpkgsVersion = warn "lib.nixpkgsVersion is a deprecated alias of lib.version." version; /* Determine whether the function is being called from inside a Nix shell. diff --git a/nixpkgs/lib/types.nix b/nixpkgs/lib/types.nix index cea63c598321..12bf18633e3a 100644 --- a/nixpkgs/lib/types.nix +++ b/nixpkgs/lib/types.nix @@ -557,6 +557,7 @@ rec { in list // { description = "non-empty ${optionDescriptionPhrase (class: class == "noun") list}"; emptyValue = { }; # no .value attr, meaning unset + substSubModules = m: nonEmptyListOf (elemType.substSubModules m); }; attrsOf = elemType: mkOptionType rec { @@ -613,23 +614,12 @@ rec { nestedTypes.elemType = elemType; }; - # Value of given type but with no merging (i.e. `uniq list`s are not concatenated). - uniq = elemType: mkOptionType rec { - name = "uniq"; - inherit (elemType) description descriptionClass check; - merge = mergeOneOption; - emptyValue = elemType.emptyValue; - getSubOptions = elemType.getSubOptions; - getSubModules = elemType.getSubModules; - substSubModules = m: uniq (elemType.substSubModules m); - functor = (defaultFunctor name) // { wrapped = elemType; }; - nestedTypes.elemType = elemType; - }; + uniq = unique { message = ""; }; unique = { message }: type: mkOptionType rec { name = "unique"; inherit (type) description descriptionClass check; - merge = mergeUniqueOption { inherit message; }; + merge = mergeUniqueOption { inherit message; inherit (type) merge; }; emptyValue = type.emptyValue; getSubOptions = type.getSubOptions; getSubModules = type.getSubModules; |