aboutsummaryrefslogtreecommitdiff
path: root/tests
Commit message (Collapse)AuthorAgeFilesLines
* refactor: extract get_raid_level fzf preview into raid.sh helperCraig Jennings2026-04-261-0/+69
| | | | | | | | | | | | | | `get_raid_level()` carried a 98-line inline fzf `--preview` shell snippet that contained five nearly-parallel `case` branches emitting per-level preview text, plus three exported variables (`RAID_DISK_COUNT`, `RAID_TOTAL_GB`, `RAID_SMALLEST_GB`) just to pass values into the fzf preview subshell. The inline shell-in-shell had no syntax highlighting, no shellcheck on the inner snippet, and any edit to preview copy meant editing inside a single-quoted argument. I extracted the per-level text into a new `raid_preview(level, disk_count, total_gb, smallest_gb)` helper in `lib/raid.sh`. It reuses the existing `raid_fault_tolerance` and `raid_usable_bytes` primitives for the data lines instead of redoing the arithmetic inline. That keeps the math in one place. The fzf `--preview` argument is now a one-liner that calls `raid_preview` with the sizing values, and the env-var exports are gone. `export -f raid_preview raid_fault_tolerance raid_usable_bytes` makes the functions visible in fzf's preview subshell. I verified this against a fresh `bash -c` subshell, which is what fzf spawns internally. `get_raid_level()` shrinks from 144 to 49 lines. Preview text is now bats-tested. Added 8 unit tests across the 5 RAID levels (headline, fault-tolerance line, computed usable space), mixed-size handling for mirror (smallest disk, not average), unknown level returning 1 with empty output, and a sanity loop confirming every valid level produces non-empty output. No behavior change. The preview pane shows the same text, the same level options, the same selected output. The pure logic in `lib/raid.sh` is unchanged.
* fix: fail fast on missing ZFSBootMenu efibootmgr entryCraig Jennings2026-04-261-0/+78
| | | | | | | | | | The post-bootloader boot-order step in `configure_zfsbootmenu` parsed `efibootmgr` output through a `grep | head | grep -oP` chain with no null guards. If any link returned empty (the entry wasn't created, the label was different, or efibootmgr itself failed), the surrounding `if [[ -n "$bootnum" ]]` silently skipped, the install reported success, and the user rebooted into a machine that wouldn't boot ZFSBootMenu by default. I replaced the chain with two pure helpers in `lib/common.sh`, `parse_efibootmgr_entry` and `parse_efibootmgr_bootorder`. The caller in `archangel` invokes them with explicit `|| error` guards on each parse stage. The helpers capture `efibootmgr` output once and reuse it (it was called twice before). The same hardening covers the BootOrder lookup at the adjacent line. It used to rely on the now-removed `bootnum` guard for safety. The helpers are stdin-driven and use bash regex, so they're easy to test in bats without exercising the real efibootmgr binary. Added 9 unit tests across normal cases, hex-character boot numbers, multi-match selection, missing label, missing BootOrder line, empty input, and an empty label argument. The empty-label case would otherwise falsely match `BootCurrent` via the hex regex, capturing "C". The helper now guards it explicitly. Verified manually against real efibootmgr output (GRUB entry at Boot0001, BootOrder 0006,0001,2001,2002,2003). Both helpers parsed correctly. VM integration not re-run for this small post-bootloader change. The next scheduled `make test-install` exercises the green path.
* feat: PrivateTmp=yes drop-in for systemd-tmpfiles on ZFS-rootCraig Jennings2026-04-211-0/+68
| | | | | | | | | | | | | | | | | | | | | | On ZFS-on-root, statx() across sibling services' /var/tmp/systemd-private-*/tmp mounts returns errno 132 (ENOTNAM). This produces 10-30 journal errors per boot and causes systemd-tmpfiles-clean.service to fail every periodic run (exit 73 / CANTCREAT). Running tmpfiles inside its own mount namespace avoids traversing sibling private-tmp paths. install_zfs() now calls configure_tmpfiles_private_tmp() between configure_zfs_tools and sync_efi_partitions, so the genesis snapshot captures the drop-ins. Btrfs path is untouched — errno 132 is ZFS-specific. The drop-in file-writing is factored into install_dropin() in lib/common.sh (service, name, root; body from stdin). Six bats tests exercise path, content, directory permissions, idempotent overwrite, empty content, and special-character preservation. Full root-cause write-up and verification steps in docs/zfs-tmpfiles-private-tmp-fix.md.
* refactor: merge install_base and install_base_btrfsCraig Jennings2026-04-131-0/+63
| | | | | | | | | | | | | | | | Extract the pacstrap package list into pacstrap_packages(filesystem) in lib/common.sh (common + filesystem-specific). install_base() now dispatches on FILESYSTEM for both the archzfs-repo-append and the package list. install_base_btrfs() deleted; install_btrfs() call site updated to invoke install_base. Old: 49 + 38 lines of ~95% copy-paste. New: 32 lines + a 20-line pure helper. 7 bats tests cover: zfs has zfs-dkms/zfs-utils, btrfs has btrfs-progs + grub + grub-btrfs + snapper + snap-pac, each flavor excludes the other's specifics, common packages are in both, unknown filesystem returns status 1, output is one-per-line. make test: 65/65.
* refactor: unify get_{luks,zfs}_passphrase and get_root_passwordCraig Jennings2026-04-131-0/+29
| | | | | | | | | | | | | | | Extract the prompt/confirm/min-length loop into prompt_password() in lib/common.sh using a nameref for the output variable, so UI output stays on the terminal (no command-substitution capture) and the three callers collapse from ~30 lines each to a single helper call. - get_luks_passphrase() — min 8 chars - get_zfs_passphrase() — min 8 chars - get_root_password() — no min (was unchecked before; preserved) 5 bats tests added: match+min-ok path, length-retry loop, mismatch-retry loop, min_len=0 disables check, empty passphrase when min_len=0. make test: 58/58.
* refactor: extract pure RAID logic to lib/raid.sh with bats coverageCraig Jennings2026-04-121-0/+199
| | | | | | | | | | | | | | | | | | | | Peel the testable pieces of get_raid_level() out of the 1600-line installer monolith into installer/lib/raid.sh: - raid_valid_levels_for_count(count) — replaces the inline option-list builder in get_raid_level() - raid_is_valid(level, count) — useful for unattended-config validation - raid_usable_bytes(level, count, smallest, total) — usable-space math - raid_fault_tolerance(level, count) — max tolerable disk failures archangel now sources lib/raid.sh and uses raid_valid_levels_for_count for the fzf option list. Fzf preview subshell still inlines its own usable-bytes arithmetic (calling exported lib functions across preview subshells is fragile; left for a later pass). 30 bats tests in tests/unit/test_raid.bats cover the full enumeration table, every valid/invalid level-vs-count combo from 2 to 5 disks, mixed-size mirror, and unknown-level error paths. make test: 53/53.
* test: add bats unit tests for common.sh and config.shCraig Jennings2026-04-122-0/+199
23 bats tests covering the pure logic in installer/lib/common.sh (command_exists, require_command, info/warn/error, enable_color, require_root, log) and installer/lib/config.sh (parse_args, load_config, validate_config, check_config). Makefile adds a 'bats' target; 'test' now runs lint + bats (VM integration tests remain under test-install).