-
-
Save paulvictor/86191d6b2d031ce26bac1870dc4bfb91 to your computer and use it in GitHub Desktop.
NixOS install script based on @grahamc's "Erase Your Darlings" blog post
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env bash | |
# | |
# NixOS install script synthesized from: | |
# | |
# - Erase Your Darlings (https://grahamc.com/blog/erase-your-darlings) | |
# - ZFS Datasets for NixOS (https://grahamc.com/blog/nixos-on-zfs) | |
# - NixOS Manual (https://nixos.org/nixos/manual/) | |
# | |
# It expects the name of the block device (e.g. 'sda') to partition | |
# and install NixOS on and an authorized public ssh key to log in as | |
# 'root' remotely. The script must also be executed as root. | |
# | |
# Example: `sudo ./install.sh sde "ssh-rsa AAAAB..."` | |
# | |
set -euo pipefail | |
################################################################################ | |
export COLOR_RESET="\033[0m" | |
export RED_BG="\033[41m" | |
export BLUE_BG="\033[44m" | |
function err { | |
echo -e "${RED_BG}$1${COLOR_RESET}" | |
} | |
function info { | |
echo -e "${BLUE_BG}$1${COLOR_RESET}" | |
} | |
################################################################################ | |
export DISK=$1 | |
if ! [[ -v DISK ]]; then | |
err "Missing argument. Expected block device name, e.g. 'sda'" | |
exit 1 | |
fi | |
export DISK_PATH="/dev/${DISK}" | |
if ! [[ -b "$DISK_PATH" ]]; then | |
err "Invalid argument: '${DISK_PATH}' is not a block special file" | |
exit 1 | |
fi | |
if [[ "$EUID" > 0 ]]; then | |
err "Must run as root" | |
exit 1 | |
fi | |
export ZFS_POOL="master" | |
# ephemeral datasets | |
export ZFS_LOCAL="${ZFS_POOL}/local" | |
export ZFS_DS_ROOT="${ZFS_LOCAL}/root" | |
export ZFS_DS_NIX="${ZFS_LOCAL}/nix" | |
export ZFS_DS_TMP="${ZFS_LOCAL}/tmp" | |
export ZFS_DS_GNU="${ZFS_LOCAL}/gnu" | |
# persistent datasets | |
export ZFS_SAFE="${ZFS_POOL}/safe" | |
export ZFS_DS_HOME="${ZFS_SAFE}/home" | |
export ZFS_DS_PERSIST="${ZFS_SAFE}/persist" | |
export ZFS_DS_TOMB="${ZFS_SAFE}/tomb" | |
export ZFS_BLANK_SNAPSHOT="${ZFS_DS_ROOT}@blank" | |
################################################################################ | |
info "Running the UEFI (GPT) partitioning and formatting directions from the NixOS manual ..." | |
parted "$DISK_PATH" -- mklabel gpt | |
parted "$DISK_PATH" -- mkpart primary 512MiB 100% | |
parted "$DISK_PATH" -- mkpart ESP fat32 1MiB 512MiB | |
parted "$DISK_PATH" -- set 2 boot on | |
export DISK_PART_ROOT="${DISK_PATH}p1" # The p is specifically for nvme's, adjust accordingly | |
export DISK_PART_BOOT="${DISK_PATH}p2" | |
info "Formatting boot partition ..." | |
mkfs.fat -F 32 -n BOOT "$DISK_PART_BOOT" | |
info "Creating '$ZFS_POOL' ZFS pool for '$DISK_PART_ROOT' ..." | |
zpool create -f "$ZFS_POOL" -o ashift=13 "$DISK_PART_ROOT" | |
zpool set autotrim=on "$ZFS_POOL" | |
info "Enabling compression for '$ZFS_POOL' ZFS pool ..." | |
zfs set compression=on "$ZFS_POOL" | |
info "Creating '$ZFS_DS_ROOT' ZFS dataset ..." | |
zfs create -p -o mountpoint=legacy "$ZFS_DS_ROOT" | |
info "Configuring extended attributes setting for '$ZFS_DS_ROOT' ZFS dataset ..." | |
zfs set xattr=sa "$ZFS_DS_ROOT" | |
info "Configuring access control list setting for '$ZFS_DS_ROOT' ZFS dataset ..." | |
zfs set acltype=posixacl "$ZFS_DS_ROOT" | |
info "Creating '$ZFS_BLANK_SNAPSHOT' ZFS snapshot ..." | |
zfs snapshot "$ZFS_BLANK_SNAPSHOT" | |
info "Mounting '$ZFS_DS_ROOT' to /mnt ..." | |
mount -t zfs "$ZFS_DS_ROOT" /mnt | |
info "Mounting '$DISK_PART_BOOT' to /mnt/boot ..." | |
mkdir /mnt/boot | |
mount -t vfat "$DISK_PART_BOOT" /mnt/boot | |
info "Creating '$ZFS_DS_NIX' ZFS dataset ..." | |
zfs create -p -o mountpoint=legacy "$ZFS_DS_NIX" | |
info "Disabling access time setting for '$ZFS_DS_NIX' ZFS dataset ..." | |
zfs set atime=off "$ZFS_DS_NIX" | |
info "Mounting '$ZFS_DS_NIX' to /mnt/nix ..." | |
mkdir /mnt/nix | |
mount -t zfs "$ZFS_DS_NIX" /mnt/nix | |
################################################################################ | |
info "Creating '$ZFS_DS_TMP' ZFS dataset ..." | |
zfs create -p -o mountpoint=legacy -o setuid=off -o devices=off -o sync=disabled "$ZFS_DS_TMP" | |
info "Mounting '$ZFS_DS_TMP' to /mnt/tmp ..." | |
mkdir /mnt/tmp | |
mount -t zfs "$ZFS_DS_TMP" /mnt/tmp | |
################################################################################ | |
info "Creating '$ZFS_DS_GNU' ZFS dataset ..." | |
zfs create -p -o mountpoint=legacy "$ZFS_DS_GNU" | |
info "Disabling access time setting for '$ZFS_DS_GNU' ZFS dataset ..." | |
zfs set atime=off "$ZFS_DS_GNU" | |
info "Mounting '$ZFS_DS_GNU' to /mnt/gnu ..." | |
mkdir /mnt/gnu | |
mount -t zfs "$ZFS_DS_GNU" /mnt/gnu | |
################################################################################ | |
info "Creating '$ZFS_SAFE' ZFS dataset ..." | |
zfs create -p -o mountpoint=none -o encryption=on -o keyformat=passphrase "$ZFS_SAFE" | |
info "Creating '$ZFS_DS_HOME' ZFS dataset ..." | |
zfs create -p -o mountpoint=legacy "$ZFS_DS_HOME" | |
info "Mounting '$ZFS_DS_HOME' to /mnt/home ..." | |
mkdir /mnt/home | |
mount -t zfs "$ZFS_DS_HOME" /mnt/home | |
info "Creating '$ZFS_DS_PERSIST' ZFS dataset ..." | |
zfs create -p -o mountpoint=legacy "$ZFS_DS_PERSIST" | |
info "Mounting '$ZFS_DS_PERSIST' to /mnt/persist ..." | |
mkdir /mnt/persist | |
mount -t zfs "$ZFS_DS_PERSIST" /mnt/persist | |
info "Creating '$ZFS_DS_TOMB' ZFS dataset ..." | |
zfs create -p -o mountpoint=legacy "$ZFS_DS_TOMB" | |
info "Mounting '$ZFS_DS_TOMB' to /mnt/tomb ..." | |
mkdir /mnt/tomb | |
mount -t zfs "$ZFS_DS_TOMB" /mnt/tomb | |
info "Permit ZFS auto-snapshots on ${ZFS_SAFE}/* datasets ..." | |
zfs set com.sun:auto-snapshot=true "$ZFS_DS_HOME" | |
zfs set com.sun:auto-snapshot=true "$ZFS_DS_PERSIST" | |
zfs set com.sun:auto-snapshot=true "$ZFS_DS_TOMB" |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment