I am trying nixos

My setup1

Update 07–09–2016: nix continues to evolve. So much so that a blog post like this or even the nix wiki often provides out-of-date information. I am working on an updated post about nix, but until then and after, I recommend you rely on the nix manual for authoritatve informantion about nixos and nix. If you encounter problems head straight the github repository for nix and check for related issues.

2(http://blog.timsears.com/slides/imtryingnix/imtryingnix.html)*

I have been running ubuntu 12.04 on VMWare Fusion. I started using nixos on October 6th.

That’s just 10 days ago.

So…all opinions herein are subject to change.

My current setup has its pluses…

…and its minuses

Some suggestions I have heard

“Bro, you’re running a mac. Just use brew.”

“Dude, you like the bleeding edge. Try Arch.”

Why Nixos?

As a Haskeller how could I resist this kind of marketing?

Nixos: The Purely Functional Linux Distribution

But wait there’s more!

Built on top of the Nix package manager, it is completely declarative…

Whoa.

Real reasons:

The potential…

Install

Boot a new machine from a .iso file, then…

$ fdisk /dev/sda # enter options n,p,1,w in sequence
$ mkfs.ext4 -j -L nixos /dev/sda1
$ mount LABEL=nixos /mnt
$ nixos-generate-config --root /mnt
$ nano /mnt/etc/nixos/configuration.nix # copy/paste a configuration.nix.
$ nixos-install
$ reboot

While it is truly possible to get a system going this way, I edited configuration about 20 times before I had it just right for my dev box. If you break something the old configuration is available from the boot menu.

Here’s my config file…

[timsears@nixos:~/blog/drafts]$ cat /etc/nixos/configuration.nix
# Edit this configuration file to define what should be installed on
# your system.  Help is available in the configuration.nix(5) man page
# and in the NixOS manual (accessible by running ‘nixos-help’).

{ config, pkgs, ... }:

{
  imports =
    [ # Include the results of the hardware scan.
      ./hardware-configuration.nix
    ];

  # Use the GRUB 2 boot loader.
  boot.loader.grub.enable = true;
  boot.loader.grub.version = 2;
  # Define on which hard drive you want to install Grub.
  boot.loader.grub.device = "/dev/sda";

  swapDevices = [ { device = "/swapfile1"; } ];

  networking.hostName = "nixos"; # Define your hostname.
  # networking.wireless.enable = true;  # I'm on a vm. Not needed.

  # Select internationalisation properties.
  i18n = {
    consoleFont = "lat9w-16";
    consoleKeyMap = "us";
    defaultLocale = "en_US.UTF-8";
  };

  environment.systemPackages = with pkgs; [
    (pkgs.texLiveAggregationFun { paths = [ pkgs.texLive pkgs.texLiveExtra pkgs.texLiveBeamer ]; })
     wget
     curl
     emacs
     xlibs.xmessage
     xfce.terminal
   ];

  nixpkgs.config.allowUnfree = true;

  time.timeZone = "US/Pacific";
  security.sudo.wheelNeedsPassword = false;

  # List services that you want to enable:

  # Enable the OpenSSH daemon.
  services.openssh.enable = true;

  services.xserver = { displayManager.slim.autoLogin = true;
                       displayManager.slim.defaultUser = "timsears";
                       windowManager.awesome.enable = true;
                       windowManager.default = "awesome";
                       # only seem to affect login screen
                       virtualScreen = { x = 1920; y = 1200; };
                       resolutions = [{ x = 1920; y = 1200; }] ;
                       enable = true;
                       layout = "us";
                        };

  # Define a user account. Don't forget to set a password with ‘passwd’.
  users.extraUsers.guest = {
    name = "timsears";
    group = "users";
    extraGroups = ["wheel"];
    uid = 1000;
    createHome = true;
    home = "/home/timsears";
    shell = "/run/current-system/sw/bin/bash";
   };
}

Configure (Global)

There are at least three levels of configuration. Global-, user- and project- level. We already saw global level. Software packages can be enabled here…

nano /etc/nixos/configuration.nix # make changes
nixos-rebuild switch

It’s really about that simple.

Configure (User)

You are encouraged to install software as a user with nix-env -i somepackage See installed packages with nix-env -q. Here’s mine so far…

cabal-install-1.16.0.2
cabal2nix-1.61
chromium-stable-with-plugins-35.0.1916.114
ghc-7.6.3-wrapper
git-1.9.4
gnome-terminal-3.10.2
haskell-hakyll-ghc7.6.3-4.5.1.0
haskell-haskell-platform-ghc7.6.3-2013.2.0.0
haskell-hoogle-ghc7.6.3-4.2.32
hasktags-0.68.7
nix-repl-1.7-1734e8a
structured-haskell-mode-1.0.2
w3m-0.5.3
xkill-1.0.4
xpdf-3.03

Eventually I will convert that to a nix expression. I expect to write a few custon expressions to install the odd missing package (like easyVision).

Configure (Project)

Here’s our first major win

You can have multiple profiles per user. (I haven’t used that feature yet.)

Or you can customize the build environment for each project.

You can put a nix expression in a project directory. Here’s a file that lives in a project I have been working on: ~/timsears/code/probmonad/default.nix

{ pkgs ? (import <nixpkgs> {})
#, haskellPackages ? pkgs.haskellPackages_ghc763
, haskellPackages ? pkgs.haskellPackages_ghc782
}:

let inherit (haskellPackages) cabal cabalInstall
    distributive comonad; # Haskell dependencies here
in

haskellPackages.cabal.mkDerivation (self: {
  pname = "probmonad";
  version = "0.1.0.0";
  src = "./.";
  isLibrary = false;
  isExecutable = true;
  buildTools = with haskellPackages; [cabalInstall];
  buildDepends = with haskellPackages; [ comonad distributive];
  meta = {
    license = self.stdenv.lib.licenses.gpl3;
    platforms = self.ghc.meta.platforms;
  };
  noHaddock = true;
})

Why this is great

Impressions so far

The Good

The Bad

The I Don’t Know

[EDIT: There is a video of the talk I gave here and a Reddit discussion here]


  1. This blog enty was based on a talk I gave at Hacker Dojo earlier today.

  2. Update 1–18–2015: Slides for the talk, with some minor updates are here.

Tim Sears October 16, 2014
Subscribe: Atom Feed