Updating attributes where one set is rec

Hi there!

I came across a situation where I’m using an overlay to override an input. I’m updating (merging) it with a new set. The issue is that the old set is “rec” and there are some attributes in it that use interpolation using the attributes that I update.

to use a contrived example with nix-repl:

args = rec { version = "1.0"; hint = "${version}"; }

args.hint = > "1.0"

args // { version = "1.1";} 

{ hint = "1.0"; version = "1.1"; }

Is there a way to make hint be “1.1” after the merge without having to assign it explicitly? In the real situation there are multiple interpolations that use $version.

Thanks a lot!

rec is not fixable like that. You can effectively desugar

rec {
  foo = <foo body>;
  bar = <bar body>;
  baz = <baz body>;
}

Into

let
  foo = <foo body>;
  bar = <bar body>;
  baz = <baz body>;
in {
  foo = foo;
  bar = bar;
  baz = baz;
}

So the code using rec needs to be rewritten to be overrideable

And we found another motivation why rec should be avoided!

https://nix.dev/guides/best-practices#recursive-attribute-set-rec