dotfiles

My PC Dotfiles & Website

scripts/install.nix (4155B)


  1{
  2  lib,
  3  pkgs,
  4  files,
  5  ...
  6}:
  7with files.path; let
  8  inherit (lib) licenses recursiveUpdate;
  9in
 10  recursiveUpdate
 11  {
 12    meta = {
 13      mainProgram = "os-install";
 14      description = "System Install Script";
 15      homepage = repo;
 16      license = licenses.gpl3Only;
 17      maintainers = ["maydayv7"];
 18    };
 19  }
 20  (
 21    pkgs.writeShellApplication {
 22      name = "os-install";
 23      runtimeInputs = with pkgs; [
 24        coreutils
 25        disko.disko
 26        git
 27        gptfdisk
 28        netcat
 29        nixFlakes
 30        nixos-install-tools
 31        util-linux
 32        zfs
 33      ];
 34
 35      text = ''
 36        set -euo pipefail
 37        ${files.scripts.commands}
 38
 39        TRIES=5
 40        CLEAN_TARGET=false
 41
 42        cleanup() {
 43          if [ "$CLEAN_TARGET" = true ]
 44          then
 45            umount -R /mnt 2> /dev/null || true
 46            zpool export fspool 2> /dev/null || true
 47            CLEAN_TARGET=false
 48          fi
 49        }
 50
 51        trap cleanup EXIT
 52
 53        install_system() {
 54          local attempt=0
 55          while [ "$attempt" -lt "$TRIES" ]
 56          do
 57            attempt=$((attempt + 1))
 58            if nixos-install --no-root-passwd --root /mnt --flake "$URL#$HOST"
 59            then
 60              return 0
 61            fi
 62            newline
 63            info "Couldn't finish installation (attempt $attempt/$TRIES)"
 64          done
 65          return 1
 66        }
 67
 68        if [ "$EUID" -ne 0 ]
 69        then
 70          error "This Command must be Executed as 'root'"
 71        fi
 72        internet
 73
 74        # Target Device and Repository
 75        read -rp "Enter Name of Device to Install: " HOST
 76        if [ -z "$HOST" ]
 77        then
 78          error "Device name cannot be empty"
 79        fi
 80
 81        read -rp "Enter Path to Repository (path/URL): " URL
 82        if [ -z "$URL" ]
 83        then
 84          URL=${flake}
 85        fi
 86
 87        # Target Disk
 88        echo "Resolving target disk for '$HOST'..."
 89        if ! DISK=$(nix eval --raw "$URL#nixosConfigurations.$HOST.config.system.fs.disk")
 90        then
 91          error "Couldn't resolve 'system.fs.disk' for '$HOST'"
 92        fi
 93        if [ ! -b "$DISK" ]
 94        then
 95          error "'$DISK' is not a valid block device" "Set 'system.fs.disk' for '$HOST' to this device's disk"
 96        fi
 97        if [ "$(lsblk --nodeps --noheadings --output TYPE "$DISK" | tr -d '[:space:]')" != "disk" ]
 98        then
 99          error "'$DISK' is not a whole-disk block device"
100        fi
101
102        # Confirm Destructive Wipe
103        lsblk --nodeps --output NAME,PATH,SIZE,MODEL,SERIAL "$DISK"
104        warn "ALL DATA on '$DISK' will be PERMANENTLY ERASED for Automatic Partitioning"
105        read -rp "Type the Disk path to confirm: " CONFIRM
106        if [ "$CONFIRM" != "$DISK" ]
107        then
108          error "Confirmation did not match '$DISK', aborting"
109        fi
110
111        # Wipe Stale Signatures
112        CLEAN_TARGET=true
113        echo "Wiping existing signatures on '$DISK'..."
114        swapoff --all 2> /dev/null || true
115        zpool labelclear -f "$DISK" 2> /dev/null || true
116        for part in "$DISK"*
117        do
118          if [ -b "$part" ]
119          then
120            zpool labelclear -f "$part" 2> /dev/null || true
121          fi
122        done
123        wipefs --all --force "$DISK" 2> /dev/null || true
124        sgdisk --zap-all "$DISK" 2> /dev/null || true
125        newline
126
127        # Partition, Format and Mount Target
128        echo "Partitioning and formatting '$DISK'..."
129        disko --mode destroy,format,mount --flake "$URL#$HOST"
130        newline
131
132        # Install
133        echo "Installing System '$HOST' from '$URL' onto '$DISK'..."
134        newline
135        until install_system
136        do
137          read -rp "Installation failed after $TRIES attempts. Try again? (Y/*): " choice
138          case $choice in
139            [Yy]*) newline; info "Retrying installation...";;
140            *) cleanup; error "Installation cancelled";;
141          esac
142        done
143        newline
144
145        cleanup
146        info "Run 'os setup' after rebooting to finish the install"
147        info "Select the (recovery) boot menu option and run the above script as the 'recovery' user"
148        restart
149      '';
150    }
151  )