default.nix 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372
  1. { inputs, outputs, pkgs, lib, config, ... }:
  2. {
  3. imports = [
  4. outputs.modules.global.nix-config
  5. # inputs.impermanence.nixosModules.impermanence
  6. inputs.disko.nixosModules.disko
  7. ./hardware-configuration.nix
  8. ./disko.nix
  9. # ./secrets.nix
  10. # ./services
  11. ];
  12. # System identification
  13. networking = {
  14. hostName = "odin";
  15. # Generate a unique host ID (you need to replace this with an actual string)
  16. # hostId = "12345678"; # Generate with `head -c 8 /etc/machine-id` and place result here
  17. useDHCP = lib.mkDefault true;
  18. # Firewall configuration for home server
  19. # firewall = {
  20. # enable = true;
  21. # allowedTCPPorts = [
  22. # 22 # SSH
  23. # 80 # HTTP
  24. # 443 # HTTPS
  25. # 2283 # Immich
  26. # ];
  27. # };
  28. };
  29. hardware.fancontrol.enable = true;
  30. hardware.fancontrol.config = ''
  31. # Configuration file generated by pwmconfig, changes will be lost
  32. INTERVAL=10
  33. DEVPATH=
  34. DEVNAME=
  35. FCTEMPS=
  36. FCFANS=
  37. MINTEMP=
  38. MAXTEMP=
  39. MINSTART=
  40. MINSTOP=
  41. '';
  42. # Boot configuration
  43. boot = {
  44. # Use systemd-boot for UEFI systems
  45. loader = {
  46. systemd-boot.enable = true;
  47. efi.canTouchEfiVariables = true;
  48. grub.devices = [ "/dev/nvme0n1" ];
  49. timeout = 3;
  50. };
  51. # Kernel parameters for server workload
  52. kernelParams = [ "rootflags=compress=zstd:1,noatime" ];
  53. # Enable KSM for memory efficiency with containers
  54. kernel.sysctl = {
  55. "kernel.sysrq" = 1;
  56. "vm.swappiness" = 10;
  57. "net.core.default_qdisc" = "cake";
  58. };
  59. };
  60. # # Impermanence: reset root on boot
  61. # initrd.postDeviceCommands = lib.mkAfter ''
  62. # # Get device from disko config
  63. # DEVICE=/dev/disk/by-id/nvme-KINGSTON_SNV3S1000G_50026B7383CC0908-part2
  64. #
  65. # mkdir -p /mnt
  66. # mount -o subvol=/ $DEVICE /mnt
  67. #
  68. # # Create a directory for old roots if it doesn't exist
  69. # mkdir -p /mnt/old-roots
  70. #
  71. # # Move current root to old-roots with timestamp if it exists
  72. # if [[ -e /mnt/@root && ! -e /mnt/@root-blank ]]; then
  73. # timestamp=$(date --date="@$(stat -c %Y /mnt/@root)" "+%Y-%m-%d_%H:%M:%S")
  74. # mv /mnt/@root "/mnt/old-roots/@root-$timestamp"
  75. # fi
  76. #
  77. # # Function to recursively delete subvolumes
  78. # delete_subvolume_recursively() {
  79. # for i in $(btrfs subvolume list -o "$1" | cut -f 9- -d ' '); do
  80. # delete_subvolume_recursively "/mnt/$i"
  81. # done
  82. # btrfs subvolume delete "$1"
  83. # }
  84. #
  85. # # Delete old roots older than 30 days
  86. # for i in $(find /mnt/old-roots/ -maxdepth 1 -mtime +30); do
  87. # delete_subvolume_recursively "$i"
  88. # done
  89. #
  90. # # Create fresh root from blank if needed or create blank if it doesn't exist
  91. # if [[ -e /mnt/@root-blank ]]; then
  92. # btrfs subvolume delete /mnt/@root || true
  93. # btrfs subvolume snapshot /mnt/@root-blank /mnt/@root
  94. # else
  95. # btrfs subvolume create /mnt/@root-blank
  96. # btrfs subvolume create /mnt/@root
  97. # fi
  98. #
  99. # umount /mnt
  100. # '';
  101. # };
  102. #
  103. # # Hardware optimizations
  104. # hardware = {
  105. # enableRedistributableFirmware = true;
  106. # cpu.amd.updateMicrocode = true;
  107. #
  108. # # Enable hardware acceleration for media processing
  109. # opengl = {
  110. # enable = true;
  111. # extraPackages = with pkgs; [
  112. # amdvlk
  113. # rocm-opencl-icd
  114. # ];
  115. # };
  116. # };
  117. #
  118. # # Power management for home server
  119. # powerManagement = {
  120. # enable = true;
  121. # cpuFreqGovernor = "ondemand";
  122. # };
  123. # Services configuration
  124. services = {
  125. # SSH configuration is managed in secrets.nix
  126. openssh = {
  127. enable = true;
  128. settings = {
  129. PasswordAuthentication = false;
  130. PermitRootLogin = "no";
  131. X11Forwarding = false;
  132. };
  133. # hostKeys = [ ];
  134. };
  135. # System monitoring
  136. # smartd = {
  137. # enable = true;
  138. # autodetect = true;
  139. # notifications.mail.enable = false; # Configure if you want email alerts
  140. # };
  141. # # Time synchronization
  142. # timesyncd.enable = true;
  143. #
  144. # # Btrfs maintenance
  145. # btrfs.autoScrub = {
  146. # enable = true;
  147. # interval = "monthly";
  148. # fileSystems = [ "/" ];
  149. # };
  150. # Drive power management and fan control
  151. hddfancontrol = {
  152. enable = false;
  153. settings = {
  154. harddrives =
  155. let
  156. devices = config.disko.device;
  157. in
  158. {
  159. disks = [
  160. devices.storage1.device
  161. devices.storage2.device
  162. devices.storage3.device
  163. ];
  164. pwmPaths = [
  165. "/sys/class/hwmon/hwmon1/pwm1:10:5"
  166. "/sys/class/hwmon/hwmon1/pwm2:10:5"
  167. ];
  168. logVerbosity = "DEBUG";
  169. };
  170. };
  171. };
  172. # Drive spin-down management
  173. # hdparm.devices = [
  174. # {
  175. # device = "/dev/disk/by-id/ata-ST8000VN002-2ZM188_WPV023WG";
  176. # spindownTime = 120; # 10 minutes
  177. # apmLevel = 127;
  178. # }
  179. # {
  180. # device = "/dev/disk/by-id/ata-ST8000VN002-2ZM188_WPV07RMA";
  181. # spindownTime = 120;
  182. # apmLevel = 127;
  183. # }
  184. # {
  185. # device = "/dev/disk/by-id/ata-ST8000VN002-2ZM188_WPV020CG";
  186. # spindownTime = 120;
  187. # apmLevel = 127;
  188. # }
  189. # ];
  190. };
  191. # # Automatic garbage collection
  192. # nix = {
  193. # gc = {
  194. # automatic = true;
  195. # dates = "weekly";
  196. # options = "--delete-older-than 30d";
  197. # };
  198. # optimise.automatic = true;
  199. # };
  200. # # Container runtime
  201. # virtualisation = {
  202. # docker = {
  203. # enable = true;
  204. # storageDriver = "btrfs";
  205. # autoPrune = {
  206. # enable = true;
  207. # dates = "weekly";
  208. # flags = [ "--all" "--force" "--volumes" ];
  209. # };
  210. # };
  211. # };
  212. # System packages
  213. environment.systemPackages = with pkgs; [
  214. # System utilities
  215. htop
  216. btop
  217. iotop
  218. lsof
  219. pciutils
  220. usbutils
  221. # Network tools
  222. curl
  223. wget
  224. rsync
  225. # File system tools
  226. btrfs-progs
  227. xfsprogs
  228. smartmontools
  229. hdparm
  230. # # Container tools
  231. # docker-compose
  232. # Storage management
  233. snapraid
  234. mergerfs
  235. # Monitoring
  236. lm_sensors
  237. nvme-cli
  238. ];
  239. # User configuration
  240. users = {
  241. mutableUsers = false; # Declarative user management
  242. users = {
  243. # Main user account
  244. thomas = {
  245. isNormalUser = true;
  246. extraGroups = [ "wheel" "users" ];
  247. hashedPassword = "$6$jO/t4PtMb4Ky.goy$2diW2qZjswUAVAzRQqOJ7wfGwD9QInJtUfQYEOOp8hkdhAy6wcccYfIG.gEQniStx7ZkxADNQxQ7pyfUiOqll.";
  248. openssh.authorizedKeys.keys = [
  249. "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAACAQC5o7LT5wPYWgI8Mvr6RKOv+BcsbQgU7PCw2hheVu17alwF1uFUsAYV5BVQu+uv9uEm/UDsCNhfM6TwI0A1prdmtBz4pKiwXbj7fcdp6DcVOgTsPfawbXEpivtJvlhEatyTsR26MjHKnqpT0BxPvj6Ug6pvRkCYW5d2bWXiY9murmAX6Q5kSyNunkB8PdRTH+S47f7eOdCJY63VBOkkiG8M7XyPwFCDTYiHhbMZcejIdY9mB6kYnMQVRHDznQWiQxrcaE1fD/TY3db9GDcOVoo2aDBOZX7WT2+me67sU8dEK9+nSyhWDzBbEs8knu87ZlKPFwhl4slenRniKhbf22OpicXArtEcjEj0GyDJH5e+ZCIQ4eSQanA7TxnKFlDuaf+Qqx55UT+ya4vJJeik7nkzbRHaE9IoWhhiOaOnaN6kHIxuxB6z7EL3Gk7f78+I/qBaj5df6fgnXM3JBXKa5bRH2wqoSetJAo6EGpEgmU2huB1ktiGlO7BlF5XwSw6cb/KT7NSIXhncgLkCzsDVXxecVQv1FnPISBcp3+ti01ADVf2trgpPDbNTWV40Rgiefie0o2fc6KWAFfum1j5N3WWU+XVVmRjDmKKHiEJBLNKDAe0rQf+tryPW4c5GIN7aFoB+8dYFAuUyLd7Fu3vhZdmcckN5ryHunEc0dKPIiuoVZw=="
  250. ];
  251. };
  252. };
  253. };
  254. # # File system mounts for impermanence
  255. # fileSystems = {
  256. # # Boot partition
  257. # "/boot" = {
  258. # device = lib.mkDefault "/dev/disk/by-partlabel/disk-main-efi";
  259. # fsType = "vfat";
  260. # };
  261. #
  262. # # Root filesystem
  263. # "/" = {
  264. # device = lib.mkDefault "/dev/disk/by-partlabel/disk-main-root";
  265. # fsType = "btrfs";
  266. # options = [ "subvol=@root" "compress=zstd:1" "noatime" ];
  267. # };
  268. #
  269. # # Nix store
  270. # "/nix" = {
  271. # device = lib.mkDefault "/dev/disk/by-partlabel/disk-main-root";
  272. # fsType = "btrfs";
  273. # options = [ "subvol=@nix" "compress=zstd:1" "noatime" ];
  274. # };
  275. #
  276. # # Home directory
  277. # "/home" = {
  278. # device = lib.mkDefault "/dev/disk/by-partlabel/disk-main-root";
  279. # fsType = "btrfs";
  280. # options = [ "subvol=@home" "compress=zstd:1" "noatime" ];
  281. # };
  282. #
  283. # # Persistent data
  284. # "/persist" = {
  285. # device = lib.mkDefault "/dev/disk/by-partlabel/disk-main-root";
  286. # fsType = "btrfs";
  287. # options = [ "subvol=@persist" "compress=zstd:1" "noatime" ];
  288. # neededForBoot = true;
  289. # };
  290. #
  291. # # Logs
  292. # "/logs" = {
  293. # device = lib.mkDefault "/dev/disk/by-partlabel/disk-main-root";
  294. # fsType = "btrfs";
  295. # options = [ "subvol=@logs" "compress=zstd:1" "noatime" ];
  296. # };
  297. #
  298. # # Services data
  299. # "/services" = {
  300. # device = lib.mkDefault "/dev/disk/by-partlabel/disk-main-root";
  301. # fsType = "btrfs";
  302. # options = [ "subvol=@services" "compress=zstd:1" "noatime" ];
  303. # };
  304. #
  305. # # Database storage - nodatacow for performance
  306. # "/databases" = {
  307. # device = lib.mkDefault "/dev/disk/by-partlabel/disk-main-root";
  308. # fsType = "btrfs";
  309. # options = [ "subvol=@databases" "compress=zstd:1" "noatime" "nodatacow" ];
  310. # };
  311. #
  312. # # Cache storage - nodatacow for performance
  313. # "/cache" = {
  314. # device = lib.mkDefault "/dev/disk/by-partlabel/disk-main-root";
  315. # fsType = "btrfs";
  316. # options = [ "subvol=@cache" "compress=zstd:1" "noatime" "nodatacow" ];
  317. # };
  318. #
  319. # # Container storage - nodatacow for performance
  320. # "/containers" = {
  321. # device = lib.mkDefault "/dev/disk/by-partlabel/disk-main-root";
  322. # fsType = "btrfs";
  323. # options = [ "subvol=@containers" "compress=zstd:1" "noatime" "nodatacow" ];
  324. # };
  325. # };
  326. # # Persistent directories for impermanence
  327. # environment.persistence."/persist" = {
  328. # hideMounts = true;
  329. # directories = [
  330. # "/etc/nixos"
  331. # "/etc/ssh"
  332. # "/var/lib/nixos"
  333. # "/var/lib/systemd"
  334. # "/srv"
  335. # ];
  336. # files = [
  337. # "/etc/machine-id"
  338. # ];
  339. # users.thomas = {
  340. # directories = [
  341. # ".ssh"
  342. # ".config"
  343. # ];
  344. # };
  345. # };
  346. # System state version
  347. system.stateVersion = "25.05";
  348. }