{ config, lib, pkgs, ... }: with lib; let hostname = config.instance.hostname; has-attrs = set: length (attrNames set) > 0; host-keypairs = if (hasAttr hostname config.fudo.secrets.files.host-ssh-keypairs) then config.fudo.secrets.files.host-ssh-keypairs.${hostname} else []; sshfp-filename = host: keypair: "ssh-${host}-${keypair.key-type}.sshfp-record"; dns-sshfp-records = host: keypair: let filename = sshfp-filename host keypair; in pkgs.stdenv.mkDerivation { name = "${host}-sshfp-record"; phases = [ "installPhase" ]; buildInputs = with pkgs; [ openssh ]; installPhase = '' mkdir $out ssh-keygen -r REMOVEME -f "${keypair.public-key}" | sed 's/^REMOVEME IN SSHFP //' > $out/${filename} ''; }; read-lines = filename: splitString "\n" (fileContents filename); host-cfg = config.fudo.hosts.${hostname}; in { config = { fudo = { secrets.host-secrets.${hostname} = listToAttrs (map (keypair: nameValuePair "host-${keypair.key-type}-private-key" { source-file = keypair.private-key; target-file = "/var/run/ssh/private/host-${keypair.key-type}-private-key"; user = "root"; }) host-keypairs); hosts = mapAttrs (hostname: keypairs: { ssh-pubkeys = map (keypair: keypair.public-key) keypairs; ssh-fingerprints = concatMap (keypair: let fingerprint-derivation = dns-sshfp-records hostname keypair; filename = sshfp-filename hostname keypair; in read-lines "${fingerprint-derivation}/${filename}") keypairs; }) config.fudo.secrets.files.host-ssh-keypairs; }; services.openssh.hostKeys = map (keypair: { path = "/var/run/ssh/private/host-${keypair.key-type}-private-key"; type = keypair.key-type; }) host-keypairs; programs.ssh.knownHosts = let keyed-hosts = filterAttrs (h: o: o.ssh-pubkeys != []) config.fudo.hosts; crossProduct = f: list0: list1: concatMap (el0: map (el1: f el0 el1) list1) list0; all-hostnames = hostname: opts: [ hostname ] ++ (crossProduct (host: domain: "${host}.${domain}") ([ hostname ] ++ opts.aliases) ([ opts.domain ] ++ opts.extra-domains)); in mapAttrs (hostname: hostOpts: { publicKeyFile = builtins.head hostOpts.ssh-pubkeys; hostNames = all-hostnames hostname host-cfg; }) keyed-hosts; }; }