I have been working with nix for a while and mostly enjoying it!
But once thing that seems unclear to me is, nix is just a language right, effectively just fancy json. But json however fancy, can not build my OS. So what is the thing that takes this config and actually makes the changes?
nixos-rebuild seems to be a bash wrapper over a python wrapper over nix-env
So is that it? Is this github.com/nixos/nix what is doing all of the heavy lifting from the config to installing the files? Is the nix store implemented there?
From a more general point of view, home-manager and plasma-manager seem to be implemented in nix only. How is the nix executable so powerful that it can do the job for both of these too?
I think, what I am asking, in the entire ecosystem, is there any other executable applying the nix evaluation results, besides nix from github.com/nixos/nix?
the glue is derivations, Nix is a pure, lazy, functional language, where json is only able to describe static data. Nix being pure means it cannot produce side effects (like talking to the network or writing or reading from your disk) for that to happen “something else” needs to handle these requests, the interpreter or a daemon is the one responsable for handling builtins.readFile or derivations which are descriptions of how to produce side effects: “fetch something from the network”, “run this command”, etc. The Nix daemon is the interpreter for such requests. So even if the language itself is turing-complete, its evaluation is isolated (kept pure – depending only on function inputs to produce outputs). The result of a derivation can be a dependency of another derivation (eg when you interpolate a binary path “${pkgs.hello}/bin/hello”). To me Nix (the daemon) is an effects interpreter and derivations are the effect language.
Interesting! Does that mean that the Nix daemon is really quite minimal, only implementing the nix language and applying the side effects as they come form the nix language, buy doesn’t actually decide anything itself? Is there like a store.nix that defines how the store works?
Not exactly. The Nix daemon handles the instantiation of derivations, and the Nix client handles the interpretation of the Nix language (for the purpose of producing derivations as results, to be shipped off to the daemon). Both client and daemon use the same internal library for interacting with the Nix store.
You’ve found the correct repository for digging deeper, but unfortunately it isn’t a small piece of software — there are many devilish details. Each folder in src is one of a couple dozen components that handle one small piece of the puzzle; in particular, libstore is the implementation of the store.
So nix is building most of the data needed for the deployment, including using some bash glue code that compiles regular software, and sticks it in /nix/store, but nix itself cannot perform deployment - that would violate its property of having no side-effects. That’s why we have some external command like nixos-rebuild to handle calling any other programs to handle said side effects.