{ config, service_configs, pkgs, ... }: let # DO NOT CHANGE # path is set via a zfs property zfs-key = "/etc/zfs-key"; in { system.activationScripts = { # Copy decrypted ZFS key from agenix to expected location # /etc is on tmpfs due to impermanence, so no persistent storage risk "zfs-key".text = '' #!/bin/sh rm -f ${zfs-key} || true cp ${config.age.secrets.zfs-key.path} ${zfs-key} chmod 0400 ${zfs-key} chown root:root ${zfs-key} ''; }; boot.zfs.package = pkgs.zfs; boot.initrd.kernelModules = [ "zfs" ]; boot.kernelParams = let gb = 32; mb = gb * 1000; kb = mb * 1000; b = kb * 1000; in [ "zfs.zfs_arc_max=${builtins.toString b}" "zfs.zfs_txg_timeout=30" # longer TXG open time = larger sequential writes = better HDD throughput "zfs.zfs_dirty_data_max=8589934592" # 8GB dirty data buffer (default 4GB) for USB HDD write smoothing "zfs.zfs_delay_min_dirty_percent=80" # delay write throttling until 80% dirty (default 60%) "zfs.zfs_vdev_async_write_max_active=30" # more concurrent async writes to vdevs (default 10) ]; boot.supportedFilesystems = [ "zfs" ]; boot.zfs.extraPools = [ service_configs.zpool_ssds service_configs.zpool_hdds ]; services.sanoid = { enable = true; datasets."${service_configs.zpool_ssds}" = { recursive = true; autoprune = true; autosnap = true; hourly = 5; daily = 7; monthly = 3; yearly = 0; }; datasets."${service_configs.zpool_ssds}/services/sql" = { recursive = true; autoprune = true; autosnap = true; hourly = 12; daily = 2; monthly = 0; yearly = 0; }; datasets."${service_configs.zpool_ssds}/services/jellyfin/cache" = { recursive = true; autoprune = true; autosnap = true; hourly = 0; daily = 0; monthly = 0; yearly = 0; }; datasets."${service_configs.zpool_hdds}" = { recursive = true; autoprune = true; autosnap = true; hourly = 0; daily = 0; monthly = 0; yearly = 0; }; }; services.zfs = { autoScrub.enable = true; trim.enable = true; }; }