104 lines
2.4 KiB
HCL
104 lines
2.4 KiB
HCL
# talos-platform – gemeinsame Cluster-Dienste für Produktion (Talos)
|
||
# Hier liegt alles, was ALLE Apps brauchen. Apps (boday_tf, ...) bringen nur ihr eigenes Chart mit.
|
||
|
||
terraform {
|
||
required_providers {
|
||
kubernetes = {
|
||
source = "hashicorp/kubernetes"
|
||
version = "~> 2.26"
|
||
}
|
||
helm = {
|
||
source = "hashicorp/helm"
|
||
version = "~> 2.12"
|
||
}
|
||
}
|
||
|
||
backend "consul" {
|
||
address = "consul:8500"
|
||
path = "terraform/states/talos_platform"
|
||
}
|
||
}
|
||
|
||
variable "kubeconfig_path" {
|
||
type = string
|
||
default = "./talos_kubeconfig"
|
||
}
|
||
|
||
# Version des Traefik-Helm-Charts (traefik/traefik). Bewusst pinnen, damit Updates geplant passieren.
|
||
variable "traefik_chart_version" {
|
||
type = string
|
||
}
|
||
|
||
provider "kubernetes" {
|
||
config_path = var.kubeconfig_path
|
||
}
|
||
|
||
provider "helm" {
|
||
kubernetes {
|
||
config_path = var.kubeconfig_path
|
||
}
|
||
}
|
||
|
||
# Feste IP für Traefik aus dem MetalLB-Pool. Auf diese IP zeigt das OPNsense-Portforwarding (80/443).
|
||
variable "traefik_lb_ip" {
|
||
type = string
|
||
}
|
||
|
||
# Kein hostPort mehr -> der Talos-Standard (PSA "baseline") reicht
|
||
resource "kubernetes_namespace" "traefik" {
|
||
metadata {
|
||
name = "traefik"
|
||
}
|
||
}
|
||
|
||
# Traefik hinter einem MetalLB-LoadBalancer: VIP wandert bei Node-Ausfall auf den anderen Node
|
||
resource "helm_release" "traefik" {
|
||
name = "traefik"
|
||
repository = "https://traefik.github.io/charts"
|
||
chart = "traefik"
|
||
version = var.traefik_chart_version
|
||
namespace = kubernetes_namespace.traefik.metadata[0].name
|
||
|
||
values = [yamlencode({
|
||
deployment = { replicas = 2 }
|
||
|
||
# Je ein Pod pro Node
|
||
topologySpreadConstraints = [{
|
||
maxSkew = 1
|
||
topologyKey = "kubernetes.io/hostname"
|
||
whenUnsatisfiable = "DoNotSchedule"
|
||
labelSelector = {
|
||
matchLabels = {
|
||
"app.kubernetes.io/name" = "traefik"
|
||
"app.kubernetes.io/instance" = "traefik-traefik"
|
||
}
|
||
}
|
||
}]
|
||
|
||
service = {
|
||
type = "LoadBalancer"
|
||
annotations = {
|
||
"metallb.io/loadBalancerIPs" = var.traefik_lb_ip
|
||
}
|
||
spec = {
|
||
# Echte Client-IP bleibt erhalten (Django-Logs, CrowdSec)
|
||
externalTrafficPolicy = "Local"
|
||
}
|
||
}
|
||
|
||
ingressClass = {
|
||
enabled = true
|
||
isDefaultClass = true
|
||
name = "traefik"
|
||
}
|
||
|
||
providers = {
|
||
kubernetesIngress = { enabled = true }
|
||
kubernetesCRD = { enabled = true }
|
||
}
|
||
})]
|
||
}
|
||
|
||
output "traefik_lb_ip" {
|
||
value = var.traefik_lb_ip
|
||
}
|