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

Simplify flake.nix by creating generic callPackage-able package.nix #9535

Merged
merged 32 commits into from
Dec 13, 2023

Conversation

tfc
Copy link
Contributor

@tfc tfc commented Dec 4, 2023

Motivation

With a parametrized package.nix file, it is now easier to understand and change the main nix derivation and its derived ones for testing, internal api docs etc.

thx a lot @Ericson2314

Context

This work item has been identified on the way towards meson.

Priorities

Add 👍 to pull requests you find important.

@Ericson2314
Copy link
Member

The package.nix is pretty crazy --- my fault. But I think that really is for the best because it faithfully is presenting the interface of the underlying build system, which is also pretty crazy!

I think this division of labor:

  • top level thin (currently flake) curates known-good configurations, presents simpler interface
  • package.nix presents the underlying thing in all its glory with little/no opinions / simplification / curating

is actually good, but it is certainly something to discuss.

@edolstra
Copy link
Member

edolstra commented Dec 5, 2023

We actually intentionally moved everything into one file (204291f) because IMHO that's easier to maintain and read (since you don't have to look at half a dozen files to know what's going on). Splitting it up adds a lot of boilerplate code for passing arguments (like the first 37 lines of package.nix).

Parameterizing package.nix suffers from the general Nixpkgs problem that the options are undiscoverable.

@Ericson2314
Copy link
Member

Ericson2314 commented Dec 5, 2023

@edolstra I had a feeling you might be skeptical :). There are a number of things to discuss, but I think these might be the important ones:

We actually intentionally moved everything into one file (204291f) because

To me at least, this does not feel like a a return to the pre-204291f way of doing things, because:

  • none of those files were really usable in isolation, but package.nix is usable in isolation, and indeed the "ultimate" most flexible thing that should be suitable for any downstream task
  • the old release-common.nix just like today's commonDeps in the flake.nix, and I object to both as scattering the definition of individual builds around in an unhelpful why --- why certain things but not others from commonDeps are used in the constituents is far from clear. I therefore think what we have with this PR is more consolidated and easier to read:
    • package.nix is completely self contained and you can understand it without looking at the flake.nix
    • the flake.nix is also readable without understanding exactly what package.nix is. The auto-passed arguments don't need to be thought about, and the manually overriden ones are pretty self-explanatory within the flake.nix

Splitting it up adds a lot of boilerplate code for passing arguments (like the first 37 lines of package.nix).

Parameterizing package.nix suffers from the general Nixpkgs problem that the options are undiscoverable.

These are indeed deficiencies with our current callPackage pattern, but they are deficiencies for which we don't yet have solutions, let alone standardized ones. (Subflakes are not yet a solution because Flake inputs do not yet work for these non-file-tree things.)

I think the right thing to do is stick to this established pattern in the ecosystem, and then try to think about things that improve it! I already thought in general use Nix's own flake.nix as a dogfooding exercise to identify issues with Flakes as we try to stabilize them --- I likewise think we should also use Nix's own package.nix as a dogfooding exercise to fix this problems too.

And while we're at it, I'd add the __forDefaults as another hack in package.nix that needs a proper solution --- not being able to augment the let-rec of the parameter defaults without adding a "fake" parameter" is annoying.

Copy link
Member

@roberth roberth left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Finally working on the package expression won't involve looking for parentheses half the time, while anxious about possibly having to reindent 300 lines of pure conflict.

I might now actually point to this flake as a possible way to do it, if, oddly enough, someone isn't convinced to use flake-parts.

Also, love the documented package parameters. Not formally discoverable just yet, but most definitely a step in the right direction!

Admittedly, this is not a thorough review. I expect ~1 mistake and the most effective way to find it, is to merge. (unfortunately git diff --color-moved --ignore-space-change wasn't helpful to me this time)

@roberth
Copy link
Member

roberth commented Dec 5, 2023

And while we're at it, I'd add the __forDefaults as another hack in package.nix that needs a proper solution --- not being able to augment the let-rec of the parameter defaults without adding a "fake" parameter" is annoying.

This could be addressed by the Nixpkgs architecture team, although it's just a tip of the iceberg when it comes to the situation with

  • package function arguments
  • mkDerivation arguments
  • derivation arguments
  • package attributes

which all compose in custom ways without any overarching design and plenty of bugs remaining because it's so ad hoc.
@DavHau has done great work on this kind of thing, but currently we're stuck on how to actually deliver such a thing without regressing eval performance to any significant degree in Nixpkgs.
My latest thoughts on the subject are around here if you're eager to know.
However, as you might guess, I don't have enough bandwidth to act on yet another such project.
Everything taken together, I would kindly suggest not to worry too much about this topic for now. Certainly not in the context of this PR, which is just an incremental improvement.

@Ericson2314
Copy link
Member

Thanks for the positive feedback!

I expect ~1 mistake and the most effective way to find it, is to merge.

If we want to do this, I suggest we try to get Hydra back up to 100% first, e.g. by merging #9518. Then we at have a proper "control" for getting back up to 100% if this introduces any minor issues.

configure.ac Outdated
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why does this need to include non-Nix changes? If it's only Nix changes, you should be able to verify correctness by making sure you get the same derivations. It's probably also cleaner that way.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The configure script changes are because the configure script wrongly still checks for a bunch of would-be mandatory stuff when passing --disable-build.

I could PR that separately before the rest, but note that due to switching to things like lib.enableFeature I wasn't going for 100% preserved hashes.

Copy link
Member

@roberth roberth Dec 7, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nix-diff is your friend in that case. (EDIT: on derivation paths)

Comment on lines +15 to +22
# Experimental fileset library: https://github.com/NixOS/nixpkgs/pull/222981
# Not an "idiomatic" flake input because:
# - Propagation to dependent locks: https://github.com/NixOS/nix/issues/7730
# - Subflake would download redundant and huge parent flake
# - No git tree hash support: https://github.com/NixOS/nix/issues/6044
inherit (import (builtins.fetchTarball { url = "https://github.com/NixOS/nix/archive/1bdcd7fc8a6a40b2e805bad759b36e64e911036b.tar.gz"; sha256 = "sha256:14ljlpdsp4x7h1fkhbmc4bd3vsqnx8zdql4h3037wh09ad6a0893"; }))
fileset;

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This might be a good time to switch to stable file set combinators, now in NixOS 23.11!

The one thing that changed is that lib.fileset.intersect is now lib.fileset.intersection.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh I just saw #9546, probably best to do this PR independently of the update for now.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure can do after that, or if you backport those to 23.05 I'll happily use them right away!

@tomberek tomberek added the idea approved The given proposal has been discussed and approved by the Nix team. An implementation is welcome. label Dec 11, 2023
package.nix Outdated Show resolved Hide resolved
lowdown.nix Outdated Show resolved Hide resolved
doInstallCheck
;

doBuild = !finalAttrs.dontBuild;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This combined with the subsequent dontBuild = !attrs.doBuild feels weird. One of those seems superfluous...

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is convenience so we are always using do* identifiers. They are not redundant because attrs vs finalAttrs.

@Ericson2314 Ericson2314 self-assigned this Dec 11, 2023
@Ericson2314
Copy link
Member

Nix team meeting notes:

Big wide ranging discussion on how this touched on other issues

  • callPackage avoids the flakes system parameter problem

  • But a few awkward Nixpkgs conventions (long arguments, complicated overriding) that need to be fixed in Nixpkgs someday are also exposed

Decision: agree to do this, but it shouldn't be considered part of the public interface of the repo (the way flake.nix is) yet.

@Ericson2314
Copy link
Member

OK I think I fixed macOS, and also @thufschmitt as of https://hydra.nixos.org/eval/1802827 basically fixed master, so we can merge this and then fix anything that hydra might find as it happens.

@Ericson2314 Ericson2314 merged commit e6515bd into NixOS:master Dec 13, 2023
8 checks passed
jlesquembre added a commit to jlesquembre/nix that referenced this pull request Dec 14, 2023
Issue introduced in NixOS#9535
@jlesquembre jlesquembre mentioned this pull request Dec 14, 2023
@cole-h
Copy link
Member

cole-h commented Dec 18, 2023

(EDIT: I can reproduce in the default devshell as well, so it's not limited to native-clangStdenvPackages and not solved by the above "Fix clang devshell" PR)

This broke make install for me:

$ cat repro.sh
#!/usr/bin/env bash
nix develop .#native-clangStdenvPackages -c bash -euo pipefail -c '
autoreconf --install --force --verbose
./configure $configureFlags --prefix=$(pwd)/out
make -j$(nproc) install doc_generate=no
'

$ repo.sh
autoreconf: export WARNINGS=
autoreconf: Entering directory '.'
autoreconf: configure.ac: not using Gettext
autoreconf: running: aclocal --force
autoreconf: configure.ac: tracing
autoreconf: configure.ac: not using Libtool
autoreconf: configure.ac: not using Intltool
autoreconf: configure.ac: not using Gtkdoc
autoreconf: running: /nix/store/nhp2wyp7wgar861mqaysc8fcl77q8m7w-autoconf-2.71/bin/autoconf --force
configure.ac:1: warning: AC_INIT: not a literal: "m4_esyscmd(bash -c "echo -n $(cat ./.version)$VERSION_SUFFIX")"
autoreconf: running: /nix/store/nhp2wyp7wgar861mqaysc8fcl77q8m7w-autoconf-2.71/bin/autoheader --force
autoreconf: configure.ac: not using Automake
autoreconf: Leaving directory '.'
checking for a sed that does not truncate output... /nix/store/4mca20b13q88s6llkr8mc468rh9l9bmr-gnused-4.9/bin/sed
checking build system type... x86_64-pc-linux-gnu
checking host system type... x86_64-pc-linux-gnu
checking for the canonical Nix system name... x86_64-linux
checking for gcc... clang
checking whether the C compiler works... yes
checking for C compiler default output file name... a.out
checking for suffix of executables...
checking whether we are cross compiling... no
checking for suffix of object files... o
checking whether the compiler supports GNU C... yes
checking whether clang accepts -g... yes
checking for clang option to enable C11 features... none needed
checking whether the compiler supports GNU C++... yes
checking whether clang++ accepts -g... yes
checking for clang++ option to enable C++11 features... none needed
checking how to run the C preprocessor... clang -E
checking for ar... ar
checking for special C compiler options needed for large files... no
checking for _FILE_OFFSET_BITS value needed for large files... no
checking for dirent.h that defines DIR... yes
checking for library containing opendir... none required
checking for struct dirent.d_type... yes
checking that GCC bug 80431 is fixed... yes
checking for pubsetbuf... yes
checking for statvfs... yes
checking for pipe2... yes
checking for lutimes... yes
checking whether it is possible to create a link to a symlink... yes
checking for stdio.h... yes
checking for stdlib.h... yes
checking for string.h... yes
checking for inttypes.h... yes
checking for stdint.h... yes
checking for strings.h... yes
checking for sys/stat.h... yes
checking for sys/types.h... yes
checking for unistd.h... yes
checking for locale... yes
checking for bash... /nix/store/0rwyq0j954a7143p0wzd4rhycny8i967-bash-5.2-p15/bin/bash
checking for flex... /nix/store/nfhymsyisbwmax4nrz7krmzch4y5sb9b-flex-2.6.4/bin/flex
checking for bison... /nix/store/8w3nvb3n3bb1p7zknlh9yabswxn5aafr-bison-3.8.2/bin/bison
checking for dot... no
checking for lsof... lsof
checking for jq... /nix/store/wgqafnfqzqa6p51bb32wdmsplgz62nnj-jq-1.6-bin/bin/jq
checking for boostlib >= 1.66 (106600) includes in "/nix/store/afz926ghcvzh6glhvlbxnd8yc4yqzaq6-boost-1.79.0/lib/include"... no
checking for boostlib >= 1.66 (106600)... yes
checking whether -latomic is needed... no
checking pkg-config is at least version 0.9.0... yes
checking for libcrypto >= 1.1.1... yes
checking for libarchive >= 3.1.2... yes
checking for sqlite3 >= 3.6.19... yes
checking for libcurl... yes
checking for libeditline... yes
checking for libsodium... yes
checking for libbrotlienc libbrotlidec... yes
checking for libcpuid... yes
checking for libseccomp... yes
./configure: line 7492: sys/xattr.h: No such file or directory
checking for aws/s3/S3Client.h... yes
checking for bdw-gc... yes
checking for gtest_main... yes
checking for rapidcheck/gtest.h... yes
checking for nlohmann_json >= 3.9... yes
checking for lowdown >= 0.9.0... yes
checking for libgit2... yes
checking for setresuid... yes
checking for setreuid... yes
checking for lchown... yes
checking for strsignal... yes
checking for posix_fallocate... yes
checking for sysconf... yes
checking whether sandbox-shell has the standalone feature... disabled
configure: creating ./config.status
config.status: creating config.h
  GEN    Makefile.config
  INST   /home/vin/workspace/vcs/nix/out/include/nix/config.h
  MKDIR  /etc/profile.d/
  MKDIR  /etc/init/
install: cannot change permissions of ‘/etc/profile.d/’: No such file or directory
make: *** [scripts/local.mk:8: /etc/profile.d/] Error 1
make: *** Waiting for unfinished jobs....
install: cannot change permissions of ‘/etc/init/’: No such file or directory
make: *** [misc/upstart/local.mk:3: /etc/init/] Error 1
  CXX    src/build-remote/build-remote.o
  CXX    src/nix-build/nix-build.o
  CXX    src/nix-channel/nix-channel.o
  CXX    src/nix-collect-garbage/nix-collect-garbage.o
  CXX    src/nix-env/user-env.o
  CXX    src/nix-copy-closure/nix-copy-closure.o
  CXX    src/nix-env/nix-env.o

specifically, eff9b12:

eff9b12bc296213c3ba824e90869bcafc4103e1c is the first bad commit
commit eff9b12bc296213c3ba824e90869bcafc4103e1c
Author: Jacek Galowicz <jacek@galowicz.de>
Date:   Fri Dec 1 11:25:22 2023 +0000

    Further changes

 binary-tarball.nix |   6 ++-
 coverage.nix       |  35 ++++++++++++++++
 flake.nix          | 117 +++++++++++++----------------------------------------
 package.nix        |  88 ++++++++++++++++++++--------------------
 4 files changed, 109 insertions(+), 137 deletions(-)
 create mode 100644 coverage.nix

@cole-h
Copy link
Member

cole-h commented Dec 18, 2023

Fixed in #9633.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
idea approved The given proposal has been discussed and approved by the Nix team. An implementation is welcome.
Projects
Archived in project
Development

Successfully merging this pull request may close these issues.

7 participants