Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Nix: Declarative OS

Nix: Declarative OS

Barcamp Bangkhen 11

Manatsawin Hanmongkolchai

November 25, 2023
Tweet

More Decks by Manatsawin Hanmongkolchai

Other Decks in Programming

Transcript

  1. Compile • Answer: it should.. but many times no ◦

    File owner, file creation time ◦ Different architecture ◦ Some software encode the time of build into the version info ◦ Some software encode the source code path in exceptions ◦ Hashmap/dictionary may have random iteration order ◦ When listing file, the file may appear in random order ◦ When downloading file from the internet, they may change
  2. Software should be deterministic • Nix is a build tool.

    It assume that builds are deterministic, and try to avoid ways you can create non-deterministic ◦ Your code build in empty environment (no files, envar at all) ◦ No internet access allowed! ◦ Explicit inputs files and environment variables are copied into the environment ◦ Then you run the build & install command (which is also an input)
  3. Software should be deterministic • Nix is a build tool.

    It assume that builds are deterministic, and try to avoid ways you can create non-deterministic ◦ Your code build in empty environment (no files, envar at all) ◦ No internet access allowed! ◦ Explicit inputs files and environment variables are copied into the environment ◦ Then you run the build & install command (which is also an input) • Then the output are named as hash(inputs). This is called "derivation"
  4. Derivation Factory function (provide default compile commands) Fixed output (can

    access internet, but output must match sha256) Compile time dependency
  5. Hash is magic • How to cache builds? Hash the

    inputs, lookup the hash in cache.nixos.org, if exists then download output. No need to build! ◦ Build once, run everywhere • How to run npm install without internet? Nix support fixed output derivation where you say that the output is a fixed value, and Nix disable the sandbox. ◦ This is what Google Bazel fails to make it easy and harms adoption
  6. NixOS • Can you recursively describe how to build a

    Linux distro from scratch? • Yes! And that is what NixOS is • There is no "install package" "upgrade" operation in NixOS. You only "rebuild" • Real declarative infrastructure, because everything is in the config ◦ Where do you declare root user in your Ansible? In Nix you could trace the source to root user's definition. ◦ When a service is removed from configuration, it is uninstalled. No need to write uninstall instructions
  7. NixOS • NixOS is composed of Nixpkgs, a collection of

    Linux packages, and a huge configuration collections (10k+ options) • You can use Nixpkgs on other Linux (and macOS)! (but you don't get to use the options)
  8. Nix Ecosystem usable on non NixOS • Home Manager •

    direnv Nix flake integration • devenv.sh ← haven't test this yet, for app development • Other NixOS stuff (no time to talk today) ◦ Build distroless Docker images without Docker ◦ Raspberry Pi!
  9. Home Manager • Manage dotfiles • Comes with 1,000+ configurations,

    like programs.git.userEmail ◦ So that you can use expressions to compute the value, or merge several sources • Can install software from Nixpkgs ◦ Get your computer ready with all the tools you use, configured to your liking! • Can rollback
  10. direnv • Please don't make your app read .env file

    • It's the application starter's responsibility to prepare configuration • Use direnv to load configuration automatically
  11. direnv + Nix • You can describe your shell with

    Nix: ◦ How to build the shell interpreter ◦ What software are available ◦ What environment variables to set (including $PATH) • Then use direnv to auto load it • You can install multiple versions of the same tools in different shells • Demo
  12. Cons • The language is very FP-style. Might not be

    familiar with devs or ops • Nixpkgs is not well documented, you'll have to look in the source. But it's not badly written ◦ It feel like navigating my company's internal system sometimes • Using Nix with private repository is pretty much limited ◦ Unless you don't care that your credential is a build input, and can be distributed ◦ Nix understand some impurity (eg. http_proxy) but it is case-by-case
  13. Cons • If you don't refresh version often/you tweak default

    build options, then cache is not used and it become Gentoo • Use very large amount of disk space ◦ You will end up with several identical Java that use slightly different compiler to compile, each almost a GB, because you can never be sure that it is 100% identical ◦ Garbage collection is a cronjob. Nix don't delete build artifacts