Skip to contents

The Nix package manager

Nix is a package manager that can be installed on your computer (regardless of OS) and can be used to install software like with any other package manager. If you’re familiar with the Ubuntu Linux distribution, you likely have used apt-get to install software. On macOS, you may have used homebrew for similar purposes. Nix functions in a similar way, but has many advantages over classic package managers. The main advantage of Nix, at least for our purposes, is that its repository of software is huge. As of writing, it contains more than 80.000 packages, and the entirety of CRAN and Bioconductor is available through Nix’s repositories. This means that using Nix, it is possible to install not only R, but also all the packages required for your project. The obvious question is why use Nix instead of simply installing R and R packages as usual. The answer is that Nix makes sure to install every dependency of any package, up to required system libraries. For example, the xlsx package requires the Java programming language to be installed on your computer to successfully install. This can be difficult to achieve, and xlsx bullied many R developers throughout the years (especially those using a Linux distribution, sudo R CMD javareconf still plagues my nightmares). But with Nix, it suffices to declare that we want the xlsx package for our project, and Nix figures out automatically that Java is required and installs and configures it. It all just happens without any required intervention from the user. The second advantage of Nix is that it is possible to pin a certain revision of the Nix packages’ repository (called nixpkgs) for our project. Pinning a revision ensures that every package that Nix installs will always be at exactly the same versions, regardless of when in the future the packages get installed.

rix workflow

The idea of rix is for you to declare the environment you need using the provided rix() function. rix() is the package’s main function and generates a file called default.nix which is then used by the Nix package manager to build that environment. Ideally, you would set up such an environment for each of your projects. You can then use this environment to either work interactively, or run R scripts. It is possible to have as many environments as projects, and software that is common to environments will simply be re-used and not get re-installed to save space. Environments are isolated for each other, but can still interact with your system’s files, unlike with Docker where a volume must be mounted. Environments can also interact with the software installed on your computer through the usual means, which can sometimes lead to issues. We have provided functions and documentation to avoid this, so take your time read through the vignettes and you should be fine.

rix() has several arguments:

  • the R version you need for your project;
  • a list of R packages that your project needs;
  • an optional list of additional software (for example a Python interpreter, or Quarto);
  • an optional list with packages to install from Github;
  • an optional list of LaTeX packages;
  • whether you want to use RStudio as an IDE for your project (or VS Code, or another environment);
  • the path to save the default.nix file (by default the current working directory)

For example:

rix(r_ver = "latest",
    r_pkgs = c("dplyr", "chronicler"),
    ide = "other")

The call above writes a default.nix file in the current working directory. This default.nix can in turn be used by Nix to build an environment containing the latest version of R, with the dplyr and {chronicler} packages.

Take note of the ide = "other" argument: this argument, and the values it can take, are further discussed in the vignette vignette("e-interactive-use") but continue reading this vignette and then vignettes numbered by a “d”.

Using default.nix files

The Nix package manager can be used to build reproducible development environments according to the specifications found in the generated default.nix files, which contain a Nix expression. An expression is Nix jargon for a function with multiple inputs and one output, this output being our development environment. rix does not require Nix to be installed to generate valid expressions (but does require an internet connection), so you could generate expressions and use them on other machines. To actually build an environment using a default.nix file, go to where you chose to write it (ideally in a new, empty folder that will be the root folder of your project) and use the Nix package manager to build the environment. Call the following function in a terminal:

nix-build

Once Nix is done building the environment, you can start working on it interactively by using the following command in a terminal emulator (not the R console):

nix-shell

You will drop into a Nix shell which provides the installed software.

Now that you know more about Nix and rix, it is time to get these tools installed on your system.