Archived
Give linode-* hosts a real Disko config, simplify auto-install.sh
Linode provisions and sizes /dev/sda (root) and /dev/sdb (swap) itself as whole, unpartitioned block devices before the OS ever boots. modules/disko/linode.nix declares them with destroy = false (skips Disko's wipe stage for these disks entirely) and a bare filesystem/swap content type matching that existing layout, so re-running it against an already-provisioned disk only mkfs/mkswaps if blkid shows it isn't formatted yet -- never repartitions or destroys data. With every host reachable through the installer menu now carrying a Disko config, auto-install.sh no longer needs to probe the flake and branch between `disko --mode destroy,format,mount` and a bind-mount fallback -- it just always runs Disko. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01La55Nsss8jZ7ZuzUV9mfot
This commit is contained in:
@@ -93,7 +93,10 @@ Three different paths depending on target, none of them involving a manual
|
|||||||
`nixos-rebuild switch` from this repo:
|
`nixos-rebuild switch` from this repo:
|
||||||
|
|
||||||
- Most hosts: boot the auto-installer, pick the target from its menu — see
|
- Most hosts: boot the auto-installer, pick the target from its menu — see
|
||||||
`docs/auto-installer.md`.
|
`docs/auto-installer.md`. Every menu target has a Disko config the
|
||||||
|
installer formats unconditionally (`docs/auto-installer.md`'s "Storage"
|
||||||
|
section covers how this stays non-destructive for `linode-*`, whose disks
|
||||||
|
Linode itself provisions ahead of time).
|
||||||
- `lxc-*` targets: not installed at all — build a ready-to-run container
|
- `lxc-*` targets: not installed at all — build a ready-to-run container
|
||||||
tarball and `pct restore` it directly. `docs/auto-installer.md` covers why
|
tarball and `pct restore` it directly. `docs/auto-installer.md` covers why
|
||||||
(and the installer's menu excludes them for the same reason).
|
(and the installer's menu excludes them for the same reason).
|
||||||
|
|||||||
+19
-5
@@ -126,10 +126,24 @@ next, where you can `scp` a key in after boot, same as before this migration.
|
|||||||
## Storage
|
## Storage
|
||||||
|
|
||||||
Disk partitioning is handled by Disko — the installer has no hardcoded
|
Disk partitioning is handled by Disko — the installer has no hardcoded
|
||||||
`parted`/`mkfs`/`mkswap`/`mount` commands. Each host defines its own layout
|
`parted`/`mkfs`/`mkswap`/`mount` commands, and `auto-install.sh` runs
|
||||||
via `disko.devices`; a host without one is installed in place via bind-mount
|
`disko --mode destroy,format,mount` unconditionally, no branching on whether
|
||||||
(this is how every LXC container target works, since they have no raw block
|
the target has a Disko config. Every host reachable through this menu has
|
||||||
device to partition).
|
one:
|
||||||
|
|
||||||
|
- `proxmox-*` (`modules/disko/proxmox.nix`): a real GPT partition table
|
||||||
|
(ESP + swap + root) on `/dev/sda`.
|
||||||
|
- `linode-*` (`modules/disko/linode.nix`): Linode provisions and sizes
|
||||||
|
`/dev/sda`/`/dev/sdb` itself as whole, unpartitioned block devices before
|
||||||
|
the OS ever boots, so this declares them with `destroy = false` (skips
|
||||||
|
disko's wipe stage for these disks entirely — see the option's own docs)
|
||||||
|
and a bare `filesystem`/`swap` content type with no partition table, and
|
||||||
|
the format step it does run only calls `mkfs`/`mkswap` if `blkid` shows
|
||||||
|
the device isn't already formatted — a re-run against an
|
||||||
|
already-provisioned Linode disk is a no-op, not a wipe.
|
||||||
|
|
||||||
|
`lxc-*` is the only category without one — it's excluded from this menu
|
||||||
|
entirely (see "LXC hosts" above), so it never reaches this code path.
|
||||||
|
|
||||||
## Installer process
|
## Installer process
|
||||||
|
|
||||||
@@ -138,7 +152,7 @@ device to partition).
|
|||||||
1. Queries `nixosConfigurations` from this flake over the network (`git+https://<lanDomain>/beatzaplenty/nixos.git`) — this happens at *install* time, not build time, so a generic installer image always sees whatever hosts are currently committed, without needing a rebuild.
|
1. Queries `nixosConfigurations` from this flake over the network (`git+https://<lanDomain>/beatzaplenty/nixos.git`) — this happens at *install* time, not build time, so a generic installer image always sees whatever hosts are currently committed, without needing a rebuild.
|
||||||
2. Presents them as a menu; confirms the choice.
|
2. Presents them as a menu; confirms the choice.
|
||||||
3. Skips the `nix-cache` substituter when installing a `nix-cache` host itself (consistent with that host's own runtime config).
|
3. Skips the `nix-cache` substituter when installing a `nix-cache` host itself (consistent with that host's own runtime config).
|
||||||
4. Runs `disko --mode destroy,format,mount` if the target has a Disko config, otherwise bind-mounts `/` onto `/mnt`.
|
4. Runs `disko --mode destroy,format,mount` (see "Storage" above — every host reachable through this menu has a Disko config, so this is unconditional).
|
||||||
5. Installs the target's SSH host key from `/etc/host-keys` or `/root/host-keys` (see "Host keys" above).
|
5. Installs the target's SSH host key from `/etc/host-keys` or `/root/host-keys` (see "Host keys" above).
|
||||||
6. Runs `nixos-install --flake <url>#<choice> --no-root-password`.
|
6. Runs `nixos-install --flake <url>#<choice> --no-root-password`.
|
||||||
7. Cleans up and reboots.
|
7. Cleans up and reboots.
|
||||||
|
|||||||
@@ -0,0 +1,35 @@
|
|||||||
|
_:
|
||||||
|
|
||||||
|
{
|
||||||
|
# Linode provisions and sizes these disks itself (via the Linode
|
||||||
|
# dashboard/API) before the OS ever boots, and presents them as whole,
|
||||||
|
# unpartitioned block devices — /dev/sda is the root filesystem directly,
|
||||||
|
# /dev/sdb is swap directly, no partition table on either. Nothing here
|
||||||
|
# should ever repartition or resize them:
|
||||||
|
# - `destroy = false` skips each disk entirely during disko's destroy
|
||||||
|
# stage (see disko's disk.destroy option) — no wipefs, ever.
|
||||||
|
# - the filesystem content type's own create step only runs mkfs if the
|
||||||
|
# device isn't already formatted (checked via `blkid`), so re-running
|
||||||
|
# this against an already-provisioned Linode disk is a no-op.
|
||||||
|
disko.devices.disk = {
|
||||||
|
main = {
|
||||||
|
device = "/dev/sda";
|
||||||
|
destroy = false;
|
||||||
|
|
||||||
|
content = {
|
||||||
|
type = "filesystem";
|
||||||
|
format = "ext4";
|
||||||
|
mountpoint = "/";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
swap = {
|
||||||
|
device = "/dev/sdb";
|
||||||
|
destroy = false;
|
||||||
|
|
||||||
|
content = {
|
||||||
|
type = "swap";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
||||||
@@ -33,14 +33,11 @@
|
|||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
fileSystems."/" =
|
# fileSystems."/" and swapDevices are now owned by disko
|
||||||
{
|
# (../disko/linode.nix, imported from ../platforms/linode.nix) — same
|
||||||
device = "/dev/sda";
|
# /dev/sda root + /dev/sdb swap layout, declared there instead so disko's
|
||||||
fsType = "ext4";
|
# (idempotent, non-destructive — see that file) format/mount scripts stay
|
||||||
};
|
# in sync with what NixOS actually mounts.
|
||||||
|
|
||||||
swapDevices =
|
|
||||||
[{ device = "/dev/sdb"; }];
|
|
||||||
|
|
||||||
nixpkgs.hostPlatform = lib.mkDefault "x86_64-linux";
|
nixpkgs.hostPlatform = lib.mkDefault "x86_64-linux";
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -119,21 +119,12 @@
|
|||||||
nix_extra_opts+=(--option substituters "https://cache.nixos.org/")
|
nix_extra_opts+=(--option substituters "https://cache.nixos.org/")
|
||||||
fi
|
fi
|
||||||
|
|
||||||
if nix eval --refresh --json --extra-experimental-features "flakes nix-command" "''${nix_extra_opts[@]}" "''${FLAKE_BASE_URL}#nixosConfigurations.''${choice}.config.disko.devices.disk.main.device" >/dev/null 2>&1; then
|
# Every host reachable through this menu has a Disko config (lxc-*
|
||||||
disko --mode destroy,format,mount \
|
# is filtered out above, and is the only category that doesn't —
|
||||||
--flake "''${FLAKE_BASE_URL}#''${choice}" "''${nix_extra_opts[@]}" --yes-wipe-all-disks
|
# see docs/auto-installer.md), so this can run unconditionally: no
|
||||||
else
|
# need to probe the flake first and branch on whether Disko applies.
|
||||||
# No raw disk to partition — true for every LXC container, which has
|
disko --mode destroy,format,mount \
|
||||||
# no block device visible from inside it, only its already-mounted
|
--flake "''${FLAKE_BASE_URL}#''${choice}" "''${nix_extra_opts[@]}" --yes-wipe-all-disks
|
||||||
# root filesystem. nixos-install defaults to installing into /mnt; if
|
|
||||||
# nothing points /mnt at the real root, the new system gets built and
|
|
||||||
# written to a disconnected empty directory, never actually becomes
|
|
||||||
# bootable, and the container silently keeps running this installer
|
|
||||||
# environment forever. Bind-mount / onto /mnt so the install actually
|
|
||||||
# lands on the filesystem this container boots from.
|
|
||||||
echo "Selected host has no Disko configuration — installing in place via bind mount."
|
|
||||||
mount --bind / /mnt
|
|
||||||
fi
|
|
||||||
|
|
||||||
# sops-nix derives this host's decryption key from its own SSH host key
|
# sops-nix derives this host's decryption key from its own SSH host key
|
||||||
# at *activation* time, which runs before systemd would otherwise
|
# at *activation* time, which runs before systemd would otherwise
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
{
|
{
|
||||||
imports = [
|
imports = [
|
||||||
../hardware-configuration/vm/linode.nix
|
../hardware-configuration/vm/linode.nix
|
||||||
|
../disko/linode.nix
|
||||||
];
|
];
|
||||||
|
|
||||||
networking = {
|
networking = {
|
||||||
|
|||||||
Reference in New Issue
Block a user