{ pkgs, lib, config, hostName, ... }:
let hosts = {
  mermet = rec {
    ipv4 = "192.168.42.1";
    ips = ["${ipv4}/24"];
    listenPort = 43642;
    peersAnnouncing.enable = true;
    peer = {
      publicKey = "XbTEP2X71LBTjmdmySdiOpQJ+uIomcXvg1aiQGUtWBI=";
      allowedIPs = [ "${ipv4}/32" ];
      endpoint = "80.67.180.129:${toString listenPort}";
      endpointsUpdater.enable = true;
    };
  };
  losurdo = rec {
    ipv4 = "192.168.42.2";
    ips = ["${ipv4}/24"];
    listenPort = 43643;
    persistentKeepalive = 10;
    peer = {
      publicKey = "xsFFep3k8z0pXgUOz4aryOF8l/KPBSOd4WQA26BkXy0=";
      allowedIPs = [ "${ipv4}/32" ];
    };
  };
  oignon = rec {
    ipv4 = "192.168.42.3";
    ips = ["${ipv4}/24"];
    #persistentKeepalive = 10;
    peer = {
      publicKey = "tE4fzqDrr7BgfOo9tWgGnpu3v0JRDEUZbJnm9e2F/GA=";
      allowedIPs = [ "${ipv4}/32" ];
      #persistentKeepalive = 25;
      #dynamicEndpointRefreshSeconds = 60;
    };
  };
  patate = rec {
    ipv4 = "192.168.42.4";
    ips = ["${ipv4}/24"];
    #persistentKeepalive = 10;
    peer = {
      publicKey = "gaEz7nvJTk4h3DGOpeZXSWmYDDrc5xQkuJ28sGrksx4=";
      allowedIPs = [ "${ipv4}/32" ];
      #persistentKeepalive = 25;
      #dynamicEndpointRefreshSeconds = 60;
    };
  };
}; in
{
networking.wireguard.interfaces.wg-intra = lib.recursiveUpdate
  (removeAttrs hosts.${hostName} ["ipv4" "persistentKeepalive" "peer"])
  {
    peers =
      lib.mapAttrsToList (peerName: peer: lib.recursiveUpdate
        { persistentKeepalive = hosts.${hostName}.persistentKeepalive or null; }
        peer.peer
      ) (removeAttrs hosts [hostName]);
  };
networking.hosts = lib.mapAttrs' (hostName: host:
  lib.nameValuePair host.ipv4 [ "${hostName}.wg" ]) hosts;
services.fail2ban.ignoreIP = lib.concatMap
  (host: host.peer.allowedIPs)
  (lib.attrValues hosts);
}