5

Even after reading the Nix manuals it is still confusing what Nix expressions really are. Sometimes they are referred to as derivations, but store derivations also mean something else.

toraritte
  • 6,300
  • 3
  • 46
  • 67

2 Answers2

5

In Nix, a Nix expression is just a general term for any type of value that you can write in the Nix language. A Nix expression can be a set, a list, a number, a string, a function, a name, a arithmetic operation, a function call, and much more.

Nix expressions can contain other Nix expressions: for example, the expression 1 + 2 contains two expressions inside it: 1 and 2.

People often like to write complicated Nix expressions that represent how to build a piece of software. Those expressions are really just sets with some special attributes. The Nix software can evaluate such an expression and turn it into a .drv file (a very simple, compact way of describing how to build some software), which can then be built.

You can do lots of things with the Nix language and Nix expressions that don't involve derivations or building software. The nix eval command lets you evaluate a Nix expression. Run nix eval --help to see its help screen, or run these commands to evaluate some simple expressions:

nix eval '(1 + 2)'  # gives 3

nix eval '({ a = 1; b = 2; }.a)'  # gives 1

(For some reason, this command seems to require parentheses to be put around most of the Nix expressions it evaluates, but that just seems like a bug or odd design choice, and surrounding parentheses are not an essential part of every Nix expression.)

David Grayson
  • 84,103
  • 24
  • 152
  • 189
  • The surrounding parentheses are due to interaction with the shell. Single quotes tell bash not to mess with what's inside (e.g. * globbing). Entering the nix evaluation enviornment via, nix repl, allows you to play around with expressions without the extra quotes. – trevor cook Oct 18 '19 at 18:15
  • 1
    Your explanation doesn't tell me why `nix eval '1 + 2'` doesn't work. Globbing is not a factor here. You can't blame the shell. I think `nix eval` is just designed so that most of the time it is trying to evaluate something different that isn't really a Nix expression, and parentheses tell it that it should actually evaluate an expression. – David Grayson Oct 18 '19 at 18:20
  • I think I'll just see my low-reading-comprehension-self out. Cheers! – trevor cook Oct 18 '19 at 18:23
2

A Nix expression is a set of instructions describing how to build a software component (package, project, application, etc.) using the Nix purely functional language.

To quote Gabriel Gonzalez: "You can think of a derivation as a language-agnostic recipe for how to build something (such as a Haskell package)."


Nix expressions are also commonly called derivations (as in Nix derivation expressions), but

*------------------------------------------------------*
|                                                      |
|       STORE DERIVATION =/= NIX EXPRESSION            |
|                                                      |
*------------------------------------------------------*
|                                                      |
| NIX EXPRESSION == function                           |
|                                                      |
| ( Describes how to build a component. That is, how ) |
| ( to  compose  its  input parameters, which can be ) |
| ( other components as well.                        ) |
|                                                      |
| STORE DERIVATION == function application             |
|                                                      |
| ( Call a  Nix  expression with concrete arguments. ) |
| ( Corollary: a single Nix  expression  can produce ) |
| ( different derivations depending on the inputs.   ) |
|                                                      |
*------------------------------------------------------*

The purpose of Nix expressions is to produce a store derivation that can be built into a component (executable, library, etc.).

For context:

Two-stage building of Nix expressions. nix-instantiate translates Nix expressions into store derivations, and nix-store --realize builds the derivation into a software component.

Image taken from Eelco Dolstra's PhD thesis, section "2.4 Store derivations".

Extra

Normal form of a Nix expression

According to section "5.4 Translating Nix expressions to store derivations" in Eelco Dolstra's PhD thesis:

The normal form [of a Nix expression] should be

  • a call to derivation, or

  • a nested structure of lists and attribute sets that contain calls to derivation.

In any case, these derivation Nix expressions are subsequently translated to store derivations.

What is a software component?

A package, application, development environment, software library, etc.

More formally from "3.1 What is a component?" in Eelco Dolstra's PhD thesis:

A software component is                      

    *-------------------------------------*
1.  | a software artifact that is subject |
    | to automatic composition            |
    *-------------------------------------*

    It can require, and be required by,   
    other components.                     

    *----------------------*              
2.  | a unit of deployment |              
    *----------------------*    

(That entire section is worth reading.)

toraritte
  • 6,300
  • 3
  • 46
  • 67
  • 2
    It's worth mentioning [ATerms](https://homepages.cwi.nl/~daybuild/daily-books/technology/aterm-guide/aterm-guide.html), which are the format of the derivation files. Nix-the-programming-language is just one (but not the only) way to produce an ATerm. As mentioned [here](http://www.haskellforall.com/2017/11/compare-nix-derivations-using-nix-diff.html), the GUIX project produces ATerms using Guile instead of Nix. – chepner Oct 04 '19 at 22:06
  • This is so awesome, thanks for the post and for pointing it out! – toraritte Oct 05 '19 at 00:53
  • 3
    No, a Nix expression is really any value or function expressed in the Nix language. Your definition is too narrow, and it contradicts sentences in the [Nix manual](https://nixos.org/nix/manual/#chap-writing-nix-expressions) such as "A set is just a list of key/value pairs where each key is a string and each value is an arbitrary Nix expression.". A Nix expression can be things like sets, numbers, strings, and lists; they are not all derivations. – David Grayson Oct 05 '19 at 17:36
  • @David Grayson You are correct, I took the narrower meaning used in Dolstra's thesis, and even there he sometimes refers to derivation-producing Nix expressions as _Nix derivation expressions_. – toraritte Oct 05 '19 at 22:52