Skip to content

Generate version alias info to streamline updates #610

@roberth

Description

@roberth

When the version bounds change, so do the attribute names, which leads to busywork such as most of the commits in

Proposal

For every configured version bound, figure out a minimal identifying suffix.

Alias

For each such suffix, add an alias such as

  Cabal_3_10_x = self.Cabal_3_10_2_1;

Suffix

Minimal identifying suffix examples:

2.*    => _2_x
<3.0   => _2_x      # usually works, but weird if it points to a 1_x version; might want to check
>=1.2  => _1_2plus

Generic override

To really solve the problem, we need to take care of attribute definitions as well; the left hand side of the attribute =.
A possible solution is to also generate in the package set:

  versionAliases = {
    Cabal = {
      "Cabal_3_10_x" = { version = "3.10.2.1"; aliasOf = "Cabal_3_10_2_1" };
      "Cabal_3_10_2_1" = { version = "3.10.2.1"; };
    };
  }

This allows a function to be written that applies overrides to all aliases, or a version range.

# configuration-common.nix (for example)
{ pkgs, ... }:
# ... as usual

self: super:
{
  # ... as usual
}
// super.overrideRange "Cabal" { atLeast = "3.8"; lessThan = "3.12"; } (Cabal:
    # do anything you would do in a normal overlay attribute value here
    # using the compose style library, you may even eta reduce this lambda, yay!
    addBuildDepends [ self.hspec_2_11_x ] Cabal
  )
// super.overrideAll "hspec-discover" (super.generateOptParseApplicativeCompletions ["hspec-discover"])

Though probably we should use composeExtensions to avoid accidentally overwriting things in the attrset before the dynamic overrides (perhaps only for the first //, or the design could be adapted; see below).

In an overlay, it is acceptable for attrNames of a layer to depend on super; just not on self. attrValues may always refer to self, as usual. So I expect no strictness problems with such a design.

Improved interface:

# configuration-common.nix (for example)
{ pkgs, ... }:
# ... as usual

haskellLib.versionRangeOverrides (self: super: {
  # ... as usual
})
{ "Cabal" = [
    { atLeast = "3.8"; lessThan = "3.12";
      modify =
        self: super: Cabal: addBuildDepends [ self.hspec_2_11_x ] Cabal;
  ];
 "hspec-discover" = [ { modify = self: super: super.generateOptParseApplicativeCompletions ["hspec-discover"]; } ];
}

This allows versionRangeOverrides to use composeExtensions once, and compose the dynamic part in a single concatenation using concatMapAttrs instead of many //.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions