# Hetzner Cloud firewall rules, keyed by firewall name. Imported by # machines/control/configuration.nix and fed to cnx.hetznerFirewall.firewalls. # # Public SSH (22) is intentionally absent: admin access rides the ZeroTier mesh # (inside UDP 9993), with emergency-access as the console fallback. let world = [ "0.0.0.0/0" "::/0" ]; zerotier = { direction = "in"; protocol = "udp"; port = "9993"; source_ips = world; description = "ZeroTier"; }; ping = { direction = "in"; protocol = "icmp"; source_ips = world; description = "ICMP (ping / PMTUD)"; }; # Inbound mail only. mx1 is the MX for cnx.email, so other servers deliver on # 25. Submission (587/465) and IMAP (993) stay closed until the mail stack and # mailboxes exist — admin access rides the mesh, same as the other hosts. smtp = { direction = "in"; protocol = "tcp"; port = "25"; source_ips = world; description = "SMTP (inbound mail)"; }; dnsRules = [ { direction = "in"; protocol = "udp"; port = "53"; source_ips = world; description = "DNS (UDP)"; } { direction = "in"; protocol = "tcp"; port = "53"; source_ips = world; description = "DNS (TCP)"; } zerotier ping ]; in { "clan-control" = [ zerotier ping ]; "clan-ns1" = dnsRules; "clan-ns2" = dnsRules; "clan-mx1" = [ smtp zerotier ping ]; }