Why I’m writing this

Often I get asked the same questions about Nix commands. I’ve decided to write down the most important answers here, so I can just send a link to this page instead of explaining the same stuff over and over again.

About flakes

My assumption is, that you are using flakes. If you haven’t enabled flakes for your system yet, you can do so by adding the following line to your /etc/nixos/configuration.nix:

{
  nix = {
    package = pkgs.nixFlakes;
    extraOptions = ''
      experimental-features = nix-command flakes
    '';
  };
}

If you are using Nix without NixOS, you can enable flakes by adding the following line to your ~/.config/nix/nix.conf:

experimental-features = nix-command flakes

You don’t have to enable flakes! You can also use flake commands by adding --experimental-features 'nix-command flakes' to your commands. Example:

# with flakes enabled
nix flake show

# without flakes enabled
nix --experimental-features 'nix-command flakes' flake show

In this guide I will use the first option (enabling flakes globally).

Important commands

# use formatter defined in flake.nix
nix fmt flake.nix

# lists all syslinks into the nix store (helpfull for finding old builds that can be deleted)
nix-store --gc --print-roots

# delete unused elements in nix store
nix-collect-garbage

# also delete iterations from boot
# -> gives you more space on your hard drive
# -> most useful when being executed it with root privileges
nix-collect-garbage -d

# check whether the flake evaluates and run its tests
# -> this will catch syntax errors and missing dependencies
nix flake check

# show flake metadata
# -> this will show the flake inputs
nix flake info

# show contents of flake
# -> this will show all outputs of the flake
nix flake show

# updates all flake inputs
# -> update flake.lock (e.g. system update)
nix flake update

# update a single flake input
nix flake lock --update-input nixpkgs

# overwrite flake input
# -> for dev purposes - overwrites the flake input with a local repository
nix flake update --override-input project-xyz /home/nik/project-xyz

# build flake output
# -> builds the output of the flake into the nix store
# -> completly builds the system configuration, but does not switch to it
nix build '.#nixosConfigurations.daisy.config.system.build.toplevel' 

# don't create a symlink to the output
# -> does not create 'result' symlink in the current directory
nix build --no-link '.#nixosConfigurations.daisy.config.system.build.toplevel'

# verbose output
# -> shows more information about the build process
# -> add -v or --verbose to any nix command
nix build --verbose '.#nixosConfigurations.daisy.config.system.build.toplevel'

# show size of build output
# -> shows the size of the build output including everything it depends on
nix path-info --closure-size -h result

# compare the difference between two builds
# -> for example after a flake update
nix build '.#nixosConfigurations.daisy.config.system.build.toplevel' --out-link before-update
nix flake update
nix build '.#nixosConfigurations.daisy.config.system.build.toplevel' --out-link after-update
nix store diff-closures $(readlink -f before-update) $(readlink -f after-update)

# build flake output and switch to it
# -> changes the system configuration to the output of the flake
# -> --use-remote-sudo is needed when working as a non-root user
# -> basically executes sudo right before applying the configuration
# -> builds the system configuration with the name of the systems hostname
nixos-rebuild switch --use-remote-sudo --flake .

# build flake output and switch to it (with custom name)
# -> builds the system configuration with the name 'daisy'
nixos-rebuild switch --use-remote-sudo --flake .#daisy

# build flake output
# -> creates a result symlink in the current directory pointing to the output of the build
nix build .#my-package

# run flake app
# -> runs the flake app after building it
nix run .#my-package

# use any flake on github
# -> this will clone the flake into the nix store and build it
# -> can be used for any flake command! (e.g. nix flake info / nixos-rebuild switch, etc.)
nix run 'github:mayniklas/nixos#drone-gen'

# run flake app from nixpkgs
nix run nixpkgs#python311 -- --version  

# enter nix shell
nix-shell -p "python3.withPackages (ps: with ps; [ dbus-python ])"

# run command in nix-shell
nix-shell -p "python3.withPackages (ps: with ps; [ dbus-python ])" --run 'python3 eduroam-linux-Universitat_Bonn-Users_with_valid_Uni-ID.py'

# get a SHA256 hash of a file
nix-prefetch-url --type sha256 <url>

# build a config file
cat $(nix build --print-out-paths .#nixosConfigurations.daisy.config.home-manager.users.nik.xdg.configFile.sway/config.source)

Updating a flake system

Remember, that updating a flake system effectively means updating the lockfile and then rebuilding the system into the defined state.

# update flake.lock
nix flake update

# rebuild system
nixos-rebuild switch --use-remote-sudo --flake .

Of course you can also update a single flake input:

# update flake.lock
nix flake lock --update-input nixpkgs