Bisecting
Bisecting is a feature of version control systems such as Git and Mercurial to easily pinpoint regressions. Owing to their reproducibility, Nix and NixOS are well-suited to this. As a result, we will list a few tips for using tools like this in the Nix context.
Commit selection
There are different ways to tweak git bisect
's commit selection to reduce the required builds:
git bisect start
flag--first-parent
: select merge commits, which depending on the repository can help for caching as well as commit stability.- brokenhydrasect
: select cached commits cached by Hydranixpkgs-staging-bisecter
(nix-build
only): reduce number of derivations to be built.
Automating bisects
git bisect run
: runs the selected command until the culprit is found.nix-bisect
: helps better judge outcome (git bisect
'sgood
vsbad
skip
) and gives nicer outputs thangit bisect run
.
Bisecting dependencies
While for regressions from changes in a Nix project itself we can bisect following the regular process, bisecting regression in dependencies is a bit different in the sense the repository you would build is separate from the repository you are bisecting. One can do this by running a bisect from a local checkout of the dependency that induced the regression.
Bisecting inputs of Flake projects
For dependencies managed using Flakes, such a bisect run
can be used with Nix Flake commands' flag --override-input
to override specific inputs to use the bisected dependency in its inputs.
Using git bisect run
from your local checkout of the dependency that caused the regression, the flake directory to run a command for can be overridden for a NixOS configuration, for example, using nixos-rebuild's --flake
flag. If we can reproduce the issue using a dry-build
, this might then look like: git bisect run nixos-rebuild dry-build --override-input $DEPENDENCY_NAME $(pwd) --flake <NIXOS_CONFIG_DIR>#<FLAKE_ATTRIBUTE>
.
For a regular Nix Flake project, we do not have a command flag like nixos-rebuild's --flake
to specify the directory of your project. We might then address this by wrapping the Nix command in a script changing directory there, for example using: git bisect run sh -c "cd <PROJECT_DIR>; nix flake check --override-input <DEPENDENCY_NAME> $(pwd)"
.