iac/terraform/firewall.tf
Sergei Poljanski bc8cc75a19 terraform: XMPP and Xray ports on services, no Hetzner backups
Open the ports of the XMPP server and Xray, which move to
asxpio-services, and close 25566 with Minecraft Fossils gone.

Turn off Hetzner's server backups on both hosts: restic now backs up
the data to object storage in two regions, and the server backups cost
20% of each server's price. Disabling them deletes the existing backup
images, so apply that part only after restic has a verified snapshot.

Assisted-by: Claude:opus-5-5
2026-11-12 20:57:52 +04:00

89 lines
2.5 KiB
HCL

# Only ports of services that actually run are open to the internet.
# Everything else is reachable from the private network and WireGuard.
locals {
internal_networks = ["10.10.0.0/20", "10.20.0.0/24"] # VPC, WireGuard
anywhere = ["0.0.0.0/0", "::/0"]
ops_public = [
{ protocol = "tcp", port = "22" }, # git over SSH (Forgejo); shell users are limited by sshd
{ protocol = "tcp", port = "80" }, # Traefik
{ protocol = "tcp", port = "443" }, # Traefik
{ protocol = "udp", port = "60101" }, # WireGuard
]
services_public = [
{ protocol = "tcp", port = "25565" }, # Minecraft (Paper)
{ protocol = "udp", port = "19132" }, # Minecraft Bedrock (Geyser)
{ protocol = "tcp", port = "443" }, # Xray VLESS Reality
{ protocol = "tcp", port = "5222-5223" }, # XMPP clients (STARTTLS, TLS)
{ protocol = "tcp", port = "5269" }, # XMPP servers
{ protocol = "tcp", port = "5443" }, # XMPP WebSocket, host-meta
{ protocol = "tcp", port = "7777" }, # XMPP file transfer proxy
{ protocol = "tcp", port = "8448" }, # Matrix federation (ejabberd)
{ protocol = "tcp", port = "3478" }, # STUN/TURN
{ protocol = "udp", port = "3478" }, # STUN/TURN
{ protocol = "udp", port = "49160-49199" }, # TURN relay
{ protocol = "udp", port = "50000-50099" }, # Telegram gateway calls
]
}
resource "hcloud_firewall" "ops_fw" {
name = "asxpio-ops-fw"
dynamic "rule" {
for_each = ["tcp", "udp"]
content {
direction = "in"
protocol = rule.value
port = "any"
source_ips = local.internal_networks
}
}
rule {
direction = "in"
protocol = "icmp"
source_ips = local.internal_networks
}
dynamic "rule" {
for_each = local.ops_public
content {
direction = "in"
protocol = rule.value.protocol
port = rule.value.port
source_ips = local.anywhere
}
}
}
resource "hcloud_firewall" "services_fw" {
name = "asxpio-services-fw"
dynamic "rule" {
for_each = ["tcp", "udp"]
content {
direction = "in"
protocol = rule.value
port = "any"
source_ips = local.internal_networks
}
}
rule {
direction = "in"
protocol = "icmp"
source_ips = local.internal_networks
}
dynamic "rule" {
for_each = local.services_public
content {
direction = "in"
protocol = rule.value.protocol
port = rule.value.port
source_ips = local.anywhere
}
}
}