From 93a58e18f67d576220d780263f67c8195c26985f Mon Sep 17 00:00:00 2001 From: Padreug Date: Sun, 28 Jun 2026 06:48:38 +0200 Subject: [PATCH] feat: live ISO image configuration Co-Authored-By: Claude Opus 4.8 --- iso.nix | 565 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 565 insertions(+) create mode 100644 iso.nix diff --git a/iso.nix b/iso.nix new file mode 100644 index 0000000..d21a0ce --- /dev/null +++ b/iso.nix @@ -0,0 +1,565 @@ +# Omnixient NixOS Live ISO Configuration +# This creates a bootable ISO image with Omnixient pre-installed + +{ + config, + pkgs, + lib, + modulesPath, + settings, + ... +}: + +{ + imports = [ + # Include the basic ISO image module (without Calamares to avoid conflicts) + "${modulesPath}/installer/cd-dvd/installation-cd-minimal.nix" + + # Omnixient modules (lib must be first to provide helpers) + ./modules/lib.nix + ./modules/core.nix + ./modules/colors.nix + ./modules/security.nix + ./modules/fastfetch.nix + ./modules/walker.nix + ./modules/scripts.nix + ./modules/menus.nix + ./modules/desktop/hyprland.nix + ./modules/packages.nix + # development.nix moved to the development pack (omni.packs.development), + # which the ISO doesn't load — it ran the minimal preset (coding off), so + # the module was inactive here anyway. + ./modules/themes/tokyo-night.nix # Default theme for ISO + ./modules/users.nix + ./modules/services.nix + ./modules/hardware + + # Pre-create the home-manager activation script's expected + # directory tree on first boot. Without this the live ISO + # would crash `home-manager-user.service` exactly the way the + # main host did before commit efafd8c — this module is also + # imported by lib/mksystem.nix so the bootstrap stays + # consistent across both code paths. + ./modules/home-manager-bootstrap.nix + ]; + + # ISO-specific configuration + isoImage = { + # ISO image settings + volumeID = "OMNI_${lib.toUpper config.system.nixos.label}"; + + # Boot configuration + makeEfiBootable = true; + makeUsbBootable = true; + + # Include additional files + includeSystemBuildDependencies = false; + + # Squeeze a few % extra out of squashfs (zstd 22 vs default + # 19). Slower to compress but saves ~80-120 MB on a ~4 GB + # image. Decompression speed at boot is identical. + squashfsCompression = "zstd -Xcompression-level 22"; + + # Boot splash (optional) + splashImage = if builtins.pathExists ./assets/logo.png then ./assets/logo.png else null; + + # Desktop entry for installer + contents = [ + { + source = pkgs.writeText "omni-install.desktop" '' + [Desktop Entry] + Name=Install Omnixient + Comment=Install Omnixient NixOS to your computer + Exec=gnome-terminal -- sudo omni-installer + Icon=system-software-install + Terminal=false + Type=Application + Categories=System; + StartupNotify=true + ''; + target = "etc/xdg/autostart/omni-install.desktop"; + } + ]; + }; + + # System configuration for live ISO + system.stateVersion = settings.stateVersion; + + # Allow unfree packages + nixpkgs.config.allowUnfree = true; + + # ISO size diet — overrides for the main host config so we don't + # blow past the "fits on a 4 GB USB" target. The main host + # configurations keep their full font and doc sets; these mkForce + # blocks only apply to the ISO build. + + # Drop the 10-font Nerd Font set from modules/packages.nix down + # to one (jetbrains-mono — referenced by waybar/alacritty). Drop + # CJK fonts (~500 MB of Chinese/Japanese/Korean glyphs nobody on + # a US-locale live ISO needs). Keep the basics: noto for general + # text, emoji for unicode, jetbrains-mono in both regular and + # nerd flavours for terminal/editor, font-awesome for waybar + # icons. + fonts.packages = lib.mkForce ( + with pkgs; + [ + nerd-fonts.jetbrains-mono # waybar icons + terminal + jetbrains-mono # editor / IDE + noto-fonts-color-emoji # unicode emoji + font-awesome # waybar fontawesome glyphs + # noto-fonts and liberation_ttf dropped to fit the 3.6 GiB + # USB. Body text falls back to jetbrains-mono which is fine + # for an installer session. + ] + ); + + # Drop documentation outputs (~700 MB + change). cachix-doc + # pulls in 696 MB of Haskell ghc-doc on its own; doc.enable is + # the upstream switch that opts every package into shipping its + # HTML/info manuals into the live system path. + documentation = { + doc.enable = lib.mkForce false; + info.enable = lib.mkForce false; + nixos.enable = lib.mkForce false; + # man pages stay enabled — they are tiny and useful in the + # live session for `man nixos-install` etc. + }; + + # ISO image filename + image.fileName = "omni-${config.system.nixos.label}-${pkgs.stdenv.hostPlatform.system}.iso"; + + # Enable flakes + nix = { + settings = { + experimental-features = [ + "nix-command" + "flakes" + ]; + auto-optimise-store = true; + + # Binary caches + substituters = [ + "https://cache.nixos.org" + "https://nix-community.cachix.org" + "https://hyprland.cachix.org" + ]; + trusted-public-keys = [ + "cache.nixos.org-1:6NCHdD59X431o0gWypbMrAURkbJ16ZPMQFGspcDShjY=" + "nix-community.cachix.org-1:mB9FSh9qf2dCimDSUo8Zy7bkq5CX+/rkCWyvRCYg3Fs=" + "hyprland.cachix.org-1:a7pgxzMz7+chwVL3/pzj6jIBMioiJM7ypFP8PwtkuGc=" + ]; + }; + }; + + # Networking + networking = { + hostName = "omni-live"; + networkmanager.enable = true; + networkmanager.wifi.backend = "iwd"; + wireless.iwd.enable = true; + + # Enable firewall but allow common services for live session + firewall = { + enable = true; + allowedTCPPorts = [ + 22 + 80 + 443 + 3000 + 8080 + ]; + }; + }; + + # Pre-configured WiFi for live session auto-connect. + networking.networkmanager.ensureProfiles.profiles.live-wifi = { + connection = { + id = "Cathare"; + type = "wifi"; + autoconnect = "true"; + autoconnect-priority = "100"; + }; + wifi = { + ssid = "Cathare"; + mode = "infrastructure"; + }; + wifi-security = { + key-mgmt = "wpa-psk"; + psk = "DruidLife"; + }; + ipv4.method = "auto"; + ipv6.method = "auto"; + }; + + # Timezone and locale + time.timeZone = "UTC"; # Will be configured during installation + i18n = { + defaultLocale = "en_US.UTF-8"; + extraLocaleSettings = { + LC_ADDRESS = "en_US.UTF-8"; + LC_IDENTIFICATION = "en_US.UTF-8"; + LC_MEASUREMENT = "en_US.UTF-8"; + LC_MONETARY = "en_US.UTF-8"; + LC_NAME = "en_US.UTF-8"; + LC_NUMERIC = "en_US.UTF-8"; + LC_PAPER = "en_US.UTF-8"; + LC_TELEPHONE = "en_US.UTF-8"; + LC_TIME = "en_US.UTF-8"; + }; + }; + + # Sound configuration + services.pulseaudio.enable = false; + security.rtkit.enable = true; + services.pipewire = { + enable = true; + alsa.enable = true; + alsa.support32Bit = true; + pulse.enable = true; + jack.enable = true; + }; + + # Override display manager configuration for ISO + services = { + # Disable greetd from main config + greetd.enable = lib.mkForce false; + + # Enable auto-login for live session + getty.autologinUser = "nixos"; + + # Keep X11 disabled - pure Wayland + xserver.enable = lib.mkForce false; + }; + + # Live user configuration is handled by modules/users.nix + # The nixos user will be created automatically since omni.user = "nixos" + # Remove any conflicting password settings + users.users.nixos = { + initialPassword = lib.mkForce ""; # Empty password for live session + password = lib.mkForce null; + hashedPassword = lib.mkForce null; + hashedPasswordFile = lib.mkForce null; + initialHashedPassword = lib.mkForce null; + }; + + # Disable firefox from home.nix for the live ISO — its closure + # adds 321 MB. Users can `nix-shell -p firefox` if they need a + # browser during the live session. + home-manager.users.nixos.programs.firefox.enable = lib.mkForce false; + + # Replace papirus-icon-theme (444 MB) with the already-present + # adwaita-icon-theme (~50 MB) to fit the 3.6 GiB USB target. + # Papirus is purely cosmetic; adwaita provides full icon + # coverage for GTK apps, thunar, etc. The installed system can + # switch back to papirus via `omni.theme` after install. + nixpkgs.overlays = [ + (_self: super: { + # Swap papirus (444 MB) for adwaita (already present, ~50 MB) + papirus-icon-theme = super.adwaita-icon-theme; + # Stub out packages that have no use on a live installer + # session — saves ~175 MB of closure to fit the 3.6 GiB USB. + rclone = super.hello; # cloud sync (88 MB) + mesa-demos = super.hello; # glxgears/glxinfo (62 MB) + cachix = super.hello; # binary cache tool (25 MB) + # Intel OpenCL compute runtime (292 MB via IGC). Display + # works fine without it via mesa/i915; only GPU compute + # (which nobody uses on a live installer) needs it. + intel-compute-runtime = super.hello; + }) + ]; + + # Auto-start Hyprland on tty1 for the live session user. + # Uses programs.bash.interactiveShellInit instead of profile.d because + # getty autologin spawns a non-login shell, so /etc/profile.d/ is + # never sourced. + programs.bash.interactiveShellInit = '' + if [[ "$(tty)" == "/dev/tty1" && "$USER" == "nixos" && -z "$WAYLAND_DISPLAY" ]]; then + export XDG_SESSION_TYPE=wayland + export XDG_SESSION_DESKTOP=Hyprland + export XDG_CURRENT_DESKTOP=Hyprland + exec ${pkgs.hyprland}/bin/Hyprland + fi + ''; + + # Sudo configuration for live user + security.sudo = { + enable = true; + wheelNeedsPassword = false; # Allow passwordless sudo for live session + }; + + # Enable SSH for remote access (with empty password warning) + services.openssh = { + enable = true; + settings = { + PermitRootLogin = "no"; + PasswordAuthentication = lib.mkForce true; # Override core.nix setting for ISO + PermitEmptyPasswords = lib.mkForce true; # For live session only + }; + }; + + # Omnixient configuration for ISO + omni = { + enable = true; + user = "nixos"; # Live session user + theme = "tokyo-night"; + desktop.enable = true; + displayManager = "gdm"; # Override default for live session + + # `minimal` preset for the live ISO. The `everything` preset + # pulls in vscode, libreoffice, slack, discord, steam, docker, + # virt-manager, etc. — together adding 6-8 GB to the ISO and + # blowing past the "fits on a 4 GB USB" target. The live + # session is a tour-of-omni + installer, not a full dev box; + # users get the full feature set after they install. + preset = "minimal"; + + # Security configuration (relaxed for live session) + security = { + enable = true; + fingerprint.enable = false; + fido2.enable = false; + systemHardening = { + enable = false; # Disable hardening for live session compatibility + faillock.enable = false; + }; + }; + + # Package configuration + packages = { + # Don't exclude anything for the live session showcase + exclude = [ ]; + }; + }; + + # Additional ISO packages — kept lean to fit on a 4 GB USB. + # Drops: + # - gnome-disk-utility, nautilus, gnome-terminal: omni already + # ships kitty/alacritty + thunar via the desktop module, so + # these GNOME duplicates are dead weight (~500 MB). + # - vim: nvim (via lazyvim-nix) is the editor; nano is kept as + # a tiny fallback for users uncomfortable with modal editors. + # - neofetch: omni already includes fastfetch via its module. + environment.systemPackages = with pkgs; [ + # Installation tools + gparted + + # Text editors for configuration + nano + + # Network tools + wget + curl + + # System information + lshw + + # NOTE: firefox was dropped to meet the 4 GB USB target. + # Its closure adds ~321 MB which pushes the compressed ISO + # past 3.6 GB. Users can `nix-shell -p firefox` in the live + # session if they need a browser for docs during install. + + # Omnixient installer script + (pkgs.writeShellScriptBin "omni-installer" '' + #!/usr/bin/env bash + set -e + + echo "🚀 Omnixient NixOS Installer" + echo "=========================" + echo "" + echo "This will guide you through installing Omnixient NixOS to your computer." + echo "" + echo "⚠️ WARNING: This will modify your disk partitions!" + echo "" + + read -p "Do you want to continue? (y/N): " -n 1 -r + echo + + if [[ ! $REPLY =~ ^[Yy]$ ]]; then + echo "Installation cancelled." + exit 1 + fi + + # Launch the graphical installer + echo "🖥️ Launching graphical installer..." + echo " Follow the on-screen instructions to install Omnixient." + echo "" + + # Use Calamares if available, otherwise provide manual instructions + if command -v calamares &> /dev/null; then + sudo calamares + else + echo "📝 Manual Installation Instructions:" + echo "" + echo "1. Partition your disk with gparted or fdisk" + echo "2. Mount your root partition to /mnt" + echo "3. Generate hardware configuration:" + echo " sudo nixos-generate-config --root /mnt" + echo "" + echo "4. Download Omnixient configuration:" + echo " cd /mnt/etc/nixos" + echo " sudo git clone https://git.atitlan.io/aiolabs/omnixient.git ." + echo "" + echo "5. Edit configuration.nix to set your username and theme" + echo "" + echo "6. Install NixOS:" + echo " sudo nixos-install --flake /mnt/etc/nixos#omni" + echo "" + echo "7. Reboot and enjoy Omnixient!" + + read -p "Press Enter to open gparted for disk partitioning..." + sudo gparted + fi + '') + + # Demo scripts + (pkgs.writeShellScriptBin "omni-demo" '' + #!/usr/bin/env bash + echo "🎨 Omnixient Live Demo" + echo "==================" + echo "" + echo "Welcome to Omnixient NixOS Live Session!" + echo "" + echo "Available commands:" + echo " omni-installer - Install Omnixient to your computer" + echo " omni-info - Show system information" + echo " omni-theme - Change theme (temporary for live session)" + echo " omni-demo - Show this demo" + echo "" + echo "Key features to try:" + echo " • Hyprland window manager with modern animations" + echo " • Multiple themes (tokyo-night, catppuccin, gruvbox, etc.)" + echo " • Development tools and environments" + echo " • Multimedia and productivity applications" + echo "" + echo "To install Omnixient permanently, run: omni-installer" + echo "" + '') + ]; + + # Services for live session + services = { + # Enable printing support + printing.enable = true; + + # Enable Bluetooth + blueman.enable = true; + + # Enable location services + geoclue2.enable = true; + + # Enable automatic time synchronization + timesyncd.enable = true; + }; + + # Hardware support — `enableRedistributableFirmware` instead of + # `enableAllFirmware` to keep the ISO under 4 GB. The "all" + # variant pulls in non-redistributable blobs that add ~2-3 GB + # for relatively niche wifi/bluetooth chips. Most modern hardware + # works with the redistributable set; users on edge-case wifi + # can opt in via `hardware.enableAllFirmware = true` after + # install. + hardware = { + enableRedistributableFirmware = true; + + # Graphics drivers + graphics = { + enable = true; + enable32Bit = true; + }; + + # Bluetooth + bluetooth = { + enable = true; + powerOnBoot = true; + }; + }; + + # Boot configuration for ISO + boot = { + # Support for various filesystems + supportedFilesystems = [ + "btrfs" + "ext4" + "xfs" + "ntfs" + "fat32" + "exfat" + ]; + + # Include lots of modules for hardware compatibility + initrd.availableKernelModules = [ + # Storage + "ahci" + "xhci_pci" + "nvme" + "usb_storage" + "sd_mod" + "rtsx_pci_sdmmc" + # Graphics + "amdgpu" + "radeon" + "nouveau" + "i915" + # Network + "r8169" + "e1000e" + "iwlwifi" + "ath9k" + "ath10k_pci" + "rtw88_8822ce" + ]; + + # Kernel parameters for better hardware compatibility + kernelParams = [ + "boot.shell_on_fail" + "i915.modeset=1" + "nouveau.modeset=1" + "radeon.modeset=1" + "amdgpu.modeset=1" + ]; + + # Latest kernel for better hardware support (MT7925 + # bluetooth, newer AMD GPUs, etc.). + kernelPackages = pkgs.linuxPackages_latest; + + # Plymouth disabled for ISO to avoid potential issues + plymouth.enable = false; + }; + + # Auto-login is configured above in services.displayManager + + # Automatically start Omnixient demo on login + environment.loginShellInit = '' + # Show demo information on first login + if [ -f /home/nixos/.first-login ]; then + omni-demo + rm /home/nixos/.first-login + fi + ''; + + # Create first-login marker + system.activationScripts.createFirstLoginMarker = '' + touch /home/nixos/.first-login + chown nixos:users /home/nixos/.first-login + ''; + + # Disable some services that might cause issues in live session + systemd.services = { + # Disable networkd-wait-online to speed up boot + systemd-networkd-wait-online.enable = false; + + # Disable some hardware services that might not be needed + fwupd.enable = false; + }; + + # Memory and performance optimizations for live session + boot.kernel.sysctl = { + # Use more aggressive memory reclaim + "vm.swappiness" = 10; + "vm.vfs_cache_pressure" = 50; + + # Network optimizations + "net.core.default_qdisc" = "fq"; + "net.ipv4.tcp_congestion_control" = "bbr"; + }; +}