Commit ff8bb8794a38

Vincent Demeester <vincent@sbr.pm>
2026-02-13 15:53:46
fix(ssh,dns): improved SSH key configuration and added okinawa to public DNS
- Refactored home openssh.nix to make host-specific FIDO2 key usage explicit - Removed conditional lib.mkIf from base config, moved to host-specific overrides - Created kyushuOverrides for service-specific FIDO2 keys - Kept okinawaOverrides for single id_ed25519_sk key usage - Added okinawa to sbr.pm DNS zone machineList for proper VPN IP resolution Previously okinawa.sbr.pm resolved to wildcard 167.99.17.238 instead of VPN IP 10.100.0.14.
1 parent d39f5c5
Changed files (2)
home
common
systems
common
services
home/common/shell/openssh.nix
@@ -35,12 +35,15 @@ in
           "kerkouane.vpn".identityFile = "~/.ssh/id_critical_infra_sk";
           "kerkouane.sbr.pm".identityFile = "~/.ssh/id_critical_infra_sk";
         };
-        # Special case for aomi
-        aomiOverrides = lib.optionalAttrs isAomi {
-          "kerkouane.vpn" = {
-            identityFile = "~/.ssh/id_ed25519";
-            identitiesOnly = true;
-          };
+        # Kyushu uses service-specific FIDO2 keys
+        kyushuOverrides = lib.optionalAttrs hasFido2Keys {
+          "github.com".identityFile = "~/.ssh/id_github_sk";
+          "gitlab.com".identityFile = "~/.ssh/id_gitlab_sk";
+          "codeberg.org".identityFile = "~/.ssh/id_codeberg_sk";
+          "git.sr.ht".identityFile = "~/.ssh/id_srht_sk";
+          "*.redhat.com".identityFile = "~/.ssh/id_redhat_sk";
+          "192.168.1.*".identityFile = "~/.ssh/id_homelab_sk";
+          "10.100.0.*".identityFile = "~/.ssh/id_homelab_sk";
         };
         # Okinawa uses a single FIDO2 key (id_ed25519_sk) for everything
         okinawaOverrides = lib.optionalAttrs isOkinawa {
@@ -50,135 +53,148 @@ in
           "git.sr.ht".identityFile = "~/.ssh/id_ed25519_sk";
           "*.redhat.com".identityFile = "~/.ssh/id_ed25519_sk";
         };
-      in
-      lib.recursiveUpdate (
-        {
-          "*" = {
-            serverAliveInterval = 60;
-            hashKnownHosts = true;
-            userKnownHostsFile = "${config.home.homeDirectory}/.ssh/known_hosts";
-            # "yes" adds keys without confirmation; FIDO2 touch-required keys still enforce touch at hardware level
-            addKeysToAgent = "yes";
-            controlMaster = "auto";
-            controlPersist = "10m";
-            controlPath = "${config.home.homeDirectory}/.ssh/master-%C";
+        # Special case for aomi
+        aomiOverrides = lib.optionalAttrs isAomi {
+          "kerkouane.vpn" = {
+            identityFile = "~/.ssh/id_ed25519";
+            identitiesOnly = true;
           };
-          # Shpool session aliases (https://bower.sh/you-might-not-need-tmux)
-          # Usage: ssh <host>/<session-name>
-          # Example: ssh rhea.home/music, ssh aomi.home/dev
-        }
-        // (
-          # Generate shpool session aliases for each machine dynamically
-          let
-            inherit (pkgs) lib;
-            # Critical infra hosts that need touch-required key
-            criticalInfraHosts = [
-              "athena.home"
-              "athena.vpn"
-              "athena.sbr.pm"
-              "demeter.home"
-              "demeter.vpn"
-              "demeter.sbr.pm"
-              "kerkouane.vpn"
-              "kerkouane.sbr.pm"
-            ];
-            isCriticalInfra = id: builtins.elem id criticalInfraHosts;
-            mkShpoolAliases =
-              _: machine:
-              let
-                # Get hostname identifiers (e.g., "rhea.home", "rhea.vpn", "rhea.sbr.pm")
-                identifiers = builtins.filter (
-                  x: (lib.hasSuffix ".home" x) || (lib.hasSuffix ".vpn" x) || (lib.hasSuffix ".sbr.pm" x)
-                ) (libx.sshHostIdentifier machine);
-                # For each identifier, create a Host block with /* wildcard
-                mkSessionBlock = id: {
-                  name = "${id}/*";
-                  value = {
-                    hostname =
-                      if (lib.hasSuffix ".vpn" id) then
-                        builtins.head machine.net.vpn.ips
-                      else if (lib.hasSuffix ".home" id) then
-                        builtins.head machine.net.ips
-                      else
-                        id;
-                    # Use critical infra key for critical hosts, homelab key for others
-                    identityFile = if isCriticalInfra id then "~/.ssh/id_critical_infra_sk" else "~/.ssh/id_homelab_sk";
-                    identitiesOnly = true;
-                    extraOptions = {
-                      RemoteCommand = "shpool-ssh-wrapper $(echo '%k' | cut -d/ -f2-)";
-                      RequestTTY = "yes";
+        };
+      in
+      lib.recursiveUpdate
+        (
+          {
+            "*" = {
+              serverAliveInterval = 60;
+              hashKnownHosts = true;
+              userKnownHostsFile = "${config.home.homeDirectory}/.ssh/known_hosts";
+              # "yes" adds keys without confirmation; FIDO2 touch-required keys still enforce touch at hardware level
+              addKeysToAgent = "yes";
+              controlMaster = "auto";
+              controlPersist = "10m";
+              controlPath = "${config.home.homeDirectory}/.ssh/master-%C";
+            };
+            # Shpool session aliases (https://bower.sh/you-might-not-need-tmux)
+            # Usage: ssh <host>/<session-name>
+            # Example: ssh rhea.home/music, ssh aomi.home/dev
+          }
+          // (
+            # Generate shpool session aliases for each machine dynamically
+            let
+              inherit (pkgs) lib;
+              # Critical infra hosts that need touch-required key
+              criticalInfraHosts = [
+                "athena.home"
+                "athena.vpn"
+                "athena.sbr.pm"
+                "demeter.home"
+                "demeter.vpn"
+                "demeter.sbr.pm"
+                "kerkouane.vpn"
+                "kerkouane.sbr.pm"
+              ];
+              isCriticalInfra = id: builtins.elem id criticalInfraHosts;
+              mkShpoolAliases =
+                _: machine:
+                let
+                  # Get hostname identifiers (e.g., "rhea.home", "rhea.vpn", "rhea.sbr.pm")
+                  identifiers = builtins.filter (
+                    x: (lib.hasSuffix ".home" x) || (lib.hasSuffix ".vpn" x) || (lib.hasSuffix ".sbr.pm" x)
+                  ) (libx.sshHostIdentifier machine);
+                  # For each identifier, create a Host block with /* wildcard
+                  mkSessionBlock = id: {
+                    name = "${id}/*";
+                    value = {
+                      hostname =
+                        if (lib.hasSuffix ".vpn" id) then
+                          builtins.head machine.net.vpn.ips
+                        else if (lib.hasSuffix ".home" id) then
+                          builtins.head machine.net.ips
+                        else
+                          id;
+                      # Use critical infra key for critical hosts, homelab key for others
+                      identityFile = if isCriticalInfra id then "~/.ssh/id_critical_infra_sk" else "~/.ssh/id_homelab_sk";
+                      identitiesOnly = true;
+                      extraOptions = {
+                        RemoteCommand = "shpool-ssh-wrapper $(echo '%k' | cut -d/ -f2-)";
+                        RequestTTY = "yes";
+                      };
                     };
                   };
-                };
-              in
-              builtins.listToAttrs (map mkSessionBlock identifiers);
-          in
-          # Merge all shpool aliases for all machines
-          lib.attrsets.mergeAttrsList (lib.attrsets.mapAttrsToList mkShpoolAliases globals.machines)
+                in
+                builtins.listToAttrs (map mkSessionBlock identifiers);
+            in
+            # Merge all shpool aliases for all machines
+            lib.attrsets.mergeAttrsList (lib.attrsets.mapAttrsToList mkShpoolAliases globals.machines)
+          )
+          # Generated configs for all machines (sets default id_homelab_sk)
+          // libx.sshConfigs globals.machines
+          # External hosts (new entries, not overrides)
+          // {
+            "github.com" = {
+              hostname = "github.com";
+              user = "git";
+              # identityFile set by host-specific overrides
+              extraOptions = {
+                controlMaster = "auto";
+                controlPersist = "360";
+              };
+            };
+            "gitlab.com" = {
+              hostname = "gitlab.com";
+              user = "git";
+              # identityFile set by host-specific overrides
+              extraOptions = {
+                controlMaster = "auto";
+                controlPersist = "360";
+              };
+            };
+            "codeberg.org" = {
+              hostname = "codeberg.org";
+              user = "git";
+              # identityFile set by host-specific overrides
+              extraOptions = {
+                controlMaster = "auto";
+                controlPersist = "360";
+              };
+            };
+            "git.sr.ht" = {
+              hostname = "git.sr.ht";
+              user = "git";
+              # identityFile set by host-specific overrides
+              extraOptions = {
+                controlMaster = "auto";
+                controlPersist = "360";
+              };
+            };
+            "*.redhat.com" = {
+              user = "vdemeest";
+              # identityFile set by host-specific overrides
+            };
+            "bootstrap.ospqa.com" = {
+              forwardAgent = true;
+            };
+            "192.168.1.*" = {
+              forwardAgent = true;
+              identitiesOnly = true;
+              # identityFile set by host-specific overrides (kyushu only)
+              extraOptions = {
+                StrictHostKeyChecking = "no";
+                UserKnownHostsFile = "/dev/null";
+              };
+            };
+            "10.100.0.*" = {
+              forwardAgent = true;
+              identitiesOnly = true;
+              # identityFile set by host-specific overrides (kyushu only)
+            };
+          }
         )
-        # Generated configs for all machines (sets default id_homelab_sk)
-        // libx.sshConfigs globals.machines
-        # External hosts (new entries, not overrides)
-        // {
-          "github.com" = {
-            hostname = "github.com";
-            user = "git";
-            identityFile = lib.mkIf hasFido2Keys "~/.ssh/id_github_sk";
-            extraOptions = {
-              controlMaster = "auto";
-              controlPersist = "360";
-            };
-          };
-          "gitlab.com" = {
-            hostname = "gitlab.com";
-            user = "git";
-            identityFile = lib.mkIf hasFido2Keys "~/.ssh/id_gitlab_sk";
-            extraOptions = {
-              controlMaster = "auto";
-              controlPersist = "360";
-            };
-          };
-          "codeberg.org" = {
-            hostname = "codeberg.org";
-            user = "git";
-            identityFile = lib.mkIf hasFido2Keys "~/.ssh/id_codeberg_sk";
-            extraOptions = {
-              controlMaster = "auto";
-              controlPersist = "360";
-            };
-          };
-          "git.sr.ht" = {
-            hostname = "git.sr.ht";
-            user = "git";
-            identityFile = lib.mkIf hasFido2Keys "~/.ssh/id_srht_sk";
-            extraOptions = {
-              controlMaster = "auto";
-              controlPersist = "360";
-            };
-          };
-          "*.redhat.com" = {
-            user = "vdemeest";
-            identityFile = lib.mkIf hasFido2Keys "~/.ssh/id_redhat_sk";
-          };
-          "bootstrap.ospqa.com" = {
-            forwardAgent = true;
-          };
-          "192.168.1.*" = {
-            forwardAgent = true;
-            identitiesOnly = true;
-            identityFile = lib.mkIf hasFido2Keys "~/.ssh/id_homelab_sk";
-            extraOptions = {
-              StrictHostKeyChecking = "no";
-              UserKnownHostsFile = "/dev/null";
-            };
-          };
-          "10.100.0.*" = {
-            forwardAgent = true;
-            identitiesOnly = true;
-            identityFile = lib.mkIf hasFido2Keys "~/.ssh/id_homelab_sk";
-          };
-        }
-      ) (lib.recursiveUpdate criticalInfraOverrides (lib.recursiveUpdate aomiOverrides okinawaOverrides));
+        (
+          lib.recursiveUpdate criticalInfraOverrides (
+            lib.recursiveUpdate kyushuOverrides (lib.recursiveUpdate okinawaOverrides aomiOverrides)
+          )
+        );
     extraConfig = ''
       # IdentityAgent /run/user/1000/yubikey-agent/yubikey-agent.sock
       GlobalKnownHostsFile ~/.ssh/ssh_known_hosts ~/.ssh/ssh_known_hosts.redhat ~/.ssh/ssh_known_hosts.mutable
systems/common/services/dns/sbr.pm-common.nix
@@ -45,6 +45,7 @@ let
     "kerkouane"
     "aomi"
     "kyushu"
+    "okinawa"
     "wakasu"
   ];