kadena-io / chainweb-data

Data ingestion for Chainweb.
BSD 3-Clause "New" or "Revised" License
14 stars 8 forks source link

Migrate to hs-nix-infra for the Nix setup #170

Closed enobayram closed 10 months ago

enobayram commented 10 months ago

This PR does the following:

Unify the GHC derivation used across Kadena projects

Instead of depending on nixpkgs and haskellNix directly, this flake now depends on our new hs-nix-infra flake and uses the nixpkgs and haskellNix revisions provided by it. The hash of the nixpkgs and haskellNix flakes used for defining the haskell.nix project determines the hash of the GHC package that gets used to compile the Haskell modules.

When multiple projects depend on nixpkgs and haskellNix independently, it's very hard (and not really well supported by nix CLI) to make sure that they don't deviate from each others' nixpkgs and haskellNix pins arbitrarily. I.e. updating two projects' flake.lock files at slightly different times is likely to cause one of the pins to be on a different revision, even though the difference doesn't matter functionally.

These unnecessarily different GHC packages put a lot of pressure on our CI infrastructure, taking hours to build functionally equivalent GHC packages and bloating the cache (with binaries from all the architectures we build and cache for). That also bloats the /nix/store of any chainweb-data user that wants to nix build an uncached chainweb-data version.

The new workflow for updating Haskell-Nix toolchain

After this PR, the new workflow for managing our Haskell dependencies used by Nix will involve the following steps:

Hopefully, this new workflow will reduce the number of nixpkgs + haskellNix versions we depend on across our Haskell projects.

Add a recursive alternative to the default package

As part of the CI automation for this repo, we're building and caching the Nix binaries for chainweb-data, which makes it convenient for any user to nix build chainweb-data from any commit/branch since all the dependencies will come from our binary cache. However, even without building anything locally, evaluating the default package of this flake takes a significant amount of time and involves downloading ~2 GB of Nix dependencies. This is due to the complexity of what haskellNix does for us at Nix evaluation time.

This PR introduces a recursive package to this flake's output, which uses recursive-nix to push the Nix evaluation of the default package into the build of a derivation. This means, any user that tries to nix build .#recursive will fetch the chainweb-data binary from our cache without having to perform any complex Nix evaluation locally or downloading the Nix dependencies of any such evaluation as long as the recursive derivation they're building is already in our binary cache. If not, the recursive-nix derivation will be built locally (in which case make sure your local Nix setup has recursive-nix enabled), which is essentially as much work as building default itself. This might still be worthwhile however, since subsequent builds of the same recursive derivation will complete immediately, without having to evaluate the default derivation again.