From c5c7cd5bc729c86545bcbd1de498c2b4e6a1ca17 Mon Sep 17 00:00:00 2001 From: Wolfgang Walther Date: Wed, 6 Aug 2025 14:31:19 +0200 Subject: [PATCH] ci/eval/compare: don't treat renames as rebuilds When a package's attrpath is renamed it is currently treated as a rebuild, even though the outpath already exists and is already cached. This also happens when adding new names for packagesets that already exist, for example when starting to eval `perlPackages` in CI, which is just the same as `perl540Packages` currently. It would also happen when `perlPackages` is switched from `perl540Packages` to `perl999Packages`. Assuming that `perl999Packages` had already been built before, this doesn't really cause any rebuilds. --- ci/eval/compare/default.nix | 7 +++---- ci/eval/default.nix | 3 ++- ci/eval/diff.nix | 19 ++++++++++++++++++- 3 files changed, 23 insertions(+), 6 deletions(-) diff --git a/ci/eval/compare/default.nix b/ci/eval/compare/default.nix index 46507a492a59..5807f8ef52f7 100644 --- a/ci/eval/compare/default.nix +++ b/ci/eval/compare/default.nix @@ -73,12 +73,11 @@ let ; # Attrs - # - keys: "added", "changed" and "removed" + # - keys: "added", "changed", "removed" and "rebuilds" # - values: lists of `packagePlatformPath`s diffAttrs = builtins.fromJSON (builtins.readFile "${combinedDir}/combined-diff.json"); - rebuilds = diffAttrs.added ++ diffAttrs.changed; - rebuildsPackagePlatformAttrs = convertToPackagePlatformAttrs rebuilds; + rebuildsPackagePlatformAttrs = convertToPackagePlatformAttrs diffAttrs.rebuilds; changed-paths = let @@ -90,7 +89,7 @@ let in writeText "changed-paths.json" ( builtins.toJSON { - attrdiff = lib.mapAttrs (_: extractPackageNames) diffAttrs; + attrdiff = lib.mapAttrs (_: extractPackageNames) { inherit (diffAttrs) added changed removed; }; inherit rebuildsByPlatform rebuildsByKernel diff --git a/ci/eval/default.nix b/ci/eval/default.nix index 56e07f8da670..21285757a277 100644 --- a/ci/eval/default.nix +++ b/ci/eval/default.nix @@ -218,7 +218,8 @@ let reduce .[] as $item ({}; { added: (.added + $item.added), changed: (.changed + $item.changed), - removed: (.removed + $item.removed) + removed: (.removed + $item.removed), + rebuilds: (.rebuilds + $item.rebuilds) }) ' > $out/combined-diff.json diff --git a/ci/eval/diff.nix b/ci/eval/diff.nix index 629b4f8d3a6a..785b0d784308 100644 --- a/ci/eval/diff.nix +++ b/ci/eval/diff.nix @@ -18,13 +18,20 @@ let added: [ ], removed: [ ], changed: [ ], + rebuilds: [ ], } */ diff = + old: new: let filterKeys = cond: attrs: lib.attrNames (lib.filterAttrs cond attrs); + oldOutputs = lib.pipe old [ + (lib.mapAttrsToList (_: lib.attrValues)) + lib.concatLists + (lib.flip lib.genAttrs (_: true)) + ]; in - old: new: { + { added = filterKeys (n: _: !(old ? ${n})) new; removed = filterKeys (n: _: !(new ? ${n})) old; changed = filterKeys ( @@ -35,6 +42,16 @@ let # Filter out attributes that are the same as the new value && (v != (new.${n})) ) old; + # A "rebuild" is every attrpath ... + rebuilds = filterKeys ( + _: pkg: + # ... that has at least one output ... + lib.any ( + output: + # ... which has not been built in "old" already. + !(oldOutputs ? ${output}) + ) (lib.attrValues pkg) + ) new; }; getAttrs =