Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

lib: Discourage use of extend #376033

Merged
merged 2 commits into from
Feb 9, 2025
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions doc/module-system/module-system.chapter.md
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,15 @@ An attribute set of module arguments that can be used in `imports`.

This is in contrast to `config._module.args`, which is only available after all `imports` have been resolved.

::: {.warning}
You may be tempted to use `specialArgs.lib` to provide extra library functions. Doing so limits the interoperability of modules, as well as the interoperability of Module System applications.

`lib` is reserved for the Nixpkgs library, and should not be used for custom functions.

Instead, you may create a new attribute in `specialArgs` to provide custom functions.
This clarifies their origin and avoids incompatibilities.
:::

#### `class` {#module-system-lib-evalModules-param-class}

If the `class` attribute is set and non-`null`, the module system will reject `imports` with a different `_class` declaration.
Expand Down
2 changes: 2 additions & 0 deletions flake.nix
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,8 @@
- `lib.nixos` for other NixOS-provided functionality, such as [`runTest`](https://nixos.org/manual/nixos/unstable/#sec-call-nixos-test-outside-nixos)
*/
# DON'T USE lib.extend TO ADD NEW FUNCTIONALITY.
# THIS WAS A MISTAKE. See the warning in lib/default.nix.
lib = lib.extend (final: prev: {

/**
Expand Down
31 changes: 29 additions & 2 deletions lib/default.nix
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,36 @@
*/
let

inherit (import ./fixed-points.nix { inherit lib; }) makeExtensible;
# A copy of `lib.makeExtensible'` in order to document `extend`.
# It has been leading to some trouble, so we have to document it specially.
makeExtensible' =
rattrs:
let self = rattrs self // {
/**
Patch the Nixpkgs library

lib = makeExtensible (self: let
The name `extends` is a bit misleading, as it doesn't actually extend the library, but rather patches it.
It is merely a consequence of being implemented by `makeExtensible`.
roberth marked this conversation as resolved.
Show resolved Hide resolved

# Inputs

- An "extension function" `f` that returns attributes that will be updated in the returned Nixpkgs library.

# Output

A patched Nixpkgs library.

:::{.warning}
This functionality is intended as an escape hatch for when the provided version of the Nixpkgs library has a flaw.

If you were to use it to add new functionality, you will run into compatibility and interoperability issues.
:::
*/
extend = f: lib.makeExtensible (lib.extends f rattrs);
};
in self;

lib = makeExtensible' (self: let
callLibs = file: import file { lib = self; };
in {

Expand Down