function-arguments.md

Named function inputs

Before this, you'll want

  1. Functions
The Nix language13 min

Positional arguments are lovely with two inputs and miserable with five. makeUser "yurii" true 1000 false is a puzzle even for the person who wrote it, and you get to solve it again every time you read the line.

So a function can unpack an attribute set instead, naming the inputs it wants straight out of it:

nix replevaluated as you typeNixA plain Nix expression. Nothing from nixpkgs or a module system is supplied.

The inputs here have names, so their order no longer matters. toString turns the number into text. We’ll return to builtins a bit later.

Call with an attribute set

The names in the function pattern must match the names in the set you hand it.

Try it

Send the parcel to the hallway and get "parcel → hallway".

nix replevaluated as you typeNixA plain Nix expression. Nothing from nixpkgs or a module system is supplied.

Give an input a default

? gives a named input a default. If the caller leaves it out, the default wins.

nix replevaluated as you typeNixA plain Nix expression. Nothing from nixpkgs or a module system is supplied.

Accept extra inputs deliberately

By default a named-input function is strict: hand it a name it did not ask for and it refuses. ... says “take the names I asked for and allow the rest.”

nix replevaluated as you typeNixA plain Nix expression. Nothing from nixpkgs or a module system is supplied.

Which is the everyday case, because the set you get handed is very often not one you wrote. Here the order sheet has more on it than the kitchen ever asked about, and the kitchen does not get to go and edit somebody’s order.

Try it

Let the kitchen take an order sheet with extra things written on it.

nix replevaluated as you typeNixA plain Nix expression. Nothing from nixpkgs or a module system is supplied.

The fix belongs in the function’s { dish, servings ? 2 } part. That is the whole reason ... exists. If somebody else assembles the set you get called with, you have to say out loud whether you mind what else is in it.

Return a whole configuration

A function can build a configuration, not just a number or string. Two small named inputs go in, and a whole structured value comes out.

Try it

Name this machine round-table and give it a desktop.

nix replevaluated as you typeNixA plain Nix expression. Nothing from nixpkgs or a module system is supplied.

Notice how you never touched makeMachine definition. Everything you changed was in the call, which is exactly what this pattern buys you. The shape gets written once, and the choices get made somewhere else entirely. It is one of the most common shapes in Nix, and in the following lessons you will meet it holding a whole operating system.

Unused inputs stay asleep

Functions do not evaluate an input unless they use it.

nix replevaluated as you typeNixA plain Nix expression. Nothing from nixpkgs or a module system is supplied.

The broken calculation was passed in, but anything was never needed. Nix left it sleeping.

Build a ridiculous pet

Play around with this one. Add an input, give it a default, or make the returned set completely ridiculous. Every piece is one you already know.

nix replevaluated as you typeNixA plain Nix expression. Nothing from nixpkgs or a module system is supplied.

What to keep

  • { item, room }: takes one attribute set and names the inputs it needs.
  • servings ? 2 supplies a default when the caller leaves servings out.
  • ... deliberately allows names the function does not use.
  • Functions can return anything, including an entire configuration.
  • Lazy evaluation leaves unused inputs asleep.

You can now read the function header on packages, shells, and NixOS modules without treating it as a spell.

Useful links

NORMALCOURSE IN BETA