Veröffentlicht am

AWS EKS Setup: Terraform, Kosten und DSGVO-Compliance

Teilen:
Authors

TL;DR

  • EKS Control Plane kostet $0.10/h (~73 EUR/Monat) -- der grosse Kostenblock sind die Worker Nodes
  • Terraform mit dem EKS-Modul ist der robusteste Weg fuer produktionsreife Cluster
  • Region eu-central-1 (Frankfurt) fuer DSGVO-Compliance, eu-west-1 (Irland) als guenstigere Alternative bei geringeren Anforderungen
  • IAM Roles for Service Accounts (IRSA) statt Cluster-weiter Node-Rollen -- Least-Privilege-Prinzip
  • Spot Instances fuer Dev/Staging sparen 60-70%, fuer Produktion On-Demand oder Savings Plans nutzen
  • Karpenter statt Cluster Autoscaler fuer schnelleres und kosteneffizienteres Scaling

Was EKS tatsaechlich kostet

Bevor wir ins Setup einsteigen: Eine ehrliche Kostenbetrachtung, denn die Control-Plane-Gebuehr ist nur die Spitze.

KomponenteKosten (eu-central-1)Hinweis
EKS Control Plane~73 EUR/MonatFix, unabhaengig von Cluster-Groesse
Worker Nodes (3x m6i.large)~290 EUR/MonatOn-Demand, 2 vCPU / 8 GB RAM je Node
Worker Nodes (3x m6i.large, Spot)~90-120 EUR/MonatBis 70% Ersparnis, nicht fuer stateful Workloads
NAT Gateway~35 EUR/Monat + TrafficPro AZ, oft unterschaetzt
ALB (Application Load Balancer)~20 EUR/Monat + LCUPro Ingress-Endpunkt
EBS Volumes (100 GB gp3)~9 EUR/MonatPro Persistent Volume
Typischer 3-Node-Cluster~420-500 EUR/MonatOn-Demand, ohne Traffic-Kosten

Tipp: NAT-Gateway-Kosten laufen schnell aus dem Ruder. Pruefen Sie, ob ein NAT-Instance oder VPC-Endpoints fuer S3/ECR guenstiger sind.

VPC und Netzwerk mit Terraform

Ein solides VPC-Setup ist die Grundlage. Verwenden Sie das offizielle Terraform-Modul:

# vpc.tf
module "vpc" {
  source  = "terraform-aws-modules/vpc/aws"
  version = "~> 5.0"

  name = "eks-production"
  cidr = "10.0.0.0/16"

  azs             = ["eu-central-1a", "eu-central-1b", "eu-central-1c"]
  private_subnets = ["10.0.1.0/24", "10.0.2.0/24", "10.0.3.0/24"]
  public_subnets  = ["10.0.101.0/24", "10.0.102.0/24", "10.0.103.0/24"]

  enable_nat_gateway   = true
  single_nat_gateway   = false  # true fuer Dev, false fuer Prod (HA)
  enable_dns_hostnames = true
  enable_dns_support   = true

  # Tags fuer den AWS Load Balancer Controller
  public_subnet_tags = {
    "kubernetes.io/role/elb" = 1
  }
  private_subnet_tags = {
    "kubernetes.io/role/internal-elb" = 1
  }

  tags = {
    Environment = "production"
    ManagedBy   = "terraform"
  }
}

Wichtig: Fuer Produktion mindestens 3 Availability Zones nutzen. Fuer Dev/Staging genuegt eine AZ mit einem einzelnen NAT Gateway.

EKS-Cluster mit Terraform aufsetzen

# eks.tf
module "eks" {
  source  = "terraform-aws-modules/eks/aws"
  version = "~> 20.0"

  cluster_name    = "production"
  cluster_version = "1.31"

  vpc_id     = module.vpc.vpc_id
  subnet_ids = module.vpc.private_subnets

  # API-Server nur aus dem VPC erreichbar
  cluster_endpoint_public_access  = false
  cluster_endpoint_private_access = true

  # EKS Add-ons
  cluster_addons = {
    coredns                = { most_recent = true }
    kube-proxy             = { most_recent = true }
    vpc-cni                = { most_recent = true }
    aws-ebs-csi-driver     = { most_recent = true }
  }

  # Managed Node Groups
  eks_managed_node_groups = {
    # System-Workloads (Monitoring, Ingress, etc.)
    system = {
      instance_types = ["m6i.large"]
      min_size       = 2
      max_size       = 4
      desired_size   = 2

      labels = {
        role = "system"
      }

      taints = [{
        key    = "CriticalAddonsOnly"
        effect = "NO_SCHEDULE"
      }]
    }

    # Application-Workloads
    application = {
      instance_types = ["m6i.xlarge", "m7i.xlarge"]
      min_size       = 2
      max_size       = 10
      desired_size   = 3
      capacity_type  = "ON_DEMAND"

      labels = {
        role = "application"
      }
    }

    # Spot-Nodes fuer nicht-kritische Workloads
    spot = {
      instance_types = ["m6i.large", "m5.large", "m7i.large"]
      min_size       = 0
      max_size       = 8
      desired_size   = 0
      capacity_type  = "SPOT"

      labels = {
        role = "spot"
      }

      taints = [{
        key    = "spot"
        value  = "true"
        effect = "NO_SCHEDULE"
      }]
    }
  }

  tags = {
    Environment = "production"
    ManagedBy   = "terraform"
  }
}

IAM Roles for Service Accounts (IRSA)

Statt einer breiten Node-Rolle erhaelt jeder Kubernetes-ServiceAccount nur die AWS-Berechtigungen, die er braucht:

# irsa.tf -- Beispiel: S3-Zugriff fuer eine Backup-Anwendung
module "irsa_backup" {
  source  = "terraform-aws-modules/iam/aws//modules/iam-role-for-service-accounts-eks"
  version = "~> 5.0"

  role_name = "eks-backup-role"

  oidc_providers = {
    main = {
      provider_arn               = module.eks.oidc_provider_arn
      namespace_service_accounts = ["backup:backup-sa"]
    }
  }

  role_policy_arns = {
    s3 = aws_iam_policy.backup_s3.arn
  }
}

resource "aws_iam_policy" "backup_s3" {
  name = "eks-backup-s3-access"
  policy = jsonencode({
    Version = "2012-10-17"
    Statement = [{
      Effect = "Allow"
      Action = [
        "s3:PutObject",
        "s3:GetObject",
        "s3:ListBucket"
      ]
      Resource = [
        "arn:aws:s3:::mein-backup-bucket",
        "arn:aws:s3:::mein-backup-bucket/*"
      ]
    }]
  })
}

Im Kubernetes-Manifest wird die Rolle ueber eine Annotation referenziert:

apiVersion: v1
kind: ServiceAccount
metadata:
  name: backup-sa
  namespace: backup
  annotations:
    eks.amazonaws.com/role-arn: arn:aws:iam::123456789012:role/eks-backup-role

AWS Load Balancer Controller

Der ALB Ingress Controller ersetzt den klassischen Kubernetes-Service vom Typ LoadBalancer und erstellt AWS Application Load Balancer:

# ingress.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: api-ingress
  namespace: production
  annotations:
    kubernetes.io/ingress.class: alb
    alb.ingress.kubernetes.io/scheme: internet-facing
    alb.ingress.kubernetes.io/target-type: ip
    alb.ingress.kubernetes.io/certificate-arn: arn:aws:acm:eu-central-1:123456789012:certificate/abc-123
    alb.ingress.kubernetes.io/ssl-policy: ELBSecurityPolicy-TLS13-1-2-2021-06
    alb.ingress.kubernetes.io/listen-ports: '[{"HTTPS":443}]'
    alb.ingress.kubernetes.io/ssl-redirect: "443"
spec:
  rules:
    - host: api.mein-unternehmen.de
      http:
        paths:
          - path: /
            pathType: Prefix
            backend:
              service:
                name: api-service
                port:
                  number: 80

Karpenter statt Cluster Autoscaler

Karpenter ist der Nachfolger des Cluster Autoscalers und bietet schnelleres Scaling mit besserer Instance-Auswahl:

# karpenter-nodepool.yaml
apiVersion: karpenter.sh/v1
kind: NodePool
metadata:
  name: default
spec:
  template:
    spec:
      requirements:
        - key: kubernetes.io/arch
          operator: In
          values: ["amd64"]
        - key: karpenter.sh/capacity-type
          operator: In
          values: ["on-demand", "spot"]
        - key: karpenter.k8s.aws/instance-category
          operator: In
          values: ["m", "c", "r"]
        - key: karpenter.k8s.aws/instance-generation
          operator: Gt
          values: ["5"]
      nodeClassRef:
        group: karpenter.k8s.aws
        kind: EC2NodeClass
        name: default
  limits:
    cpu: "100"
    memory: 400Gi
  disruption:
    consolidationPolicy: WhenEmptyOrUnderutilized
    consolidateAfter: 1m

Karpenter waehlt automatisch den guenstigsten Instance-Typ, der die Pod-Anforderungen erfuellt, und konsolidiert unterbelegte Nodes.

DSGVO-Compliance: Was Sie beachten muessen

Datenlokalitaet

  • Region eu-central-1 (Frankfurt) verwenden -- Daten bleiben in Deutschland
  • ECR-Images, S3-Buckets und RDS-Instanzen in derselben Region halten
  • CloudTrail-Logs nicht in US-Regionen replizieren

Verschluesselung

# KMS-Key fuer EKS Secrets Encryption
resource "aws_kms_key" "eks" {
  description = "EKS Secrets Encryption Key"
  enable_key_rotation = true
}

# Im EKS-Modul referenzieren:
# cluster_encryption_config = {
#   provider_key_arn = aws_kms_key.eks.arn
#   resources        = ["secrets"]
# }

Logging und Auditierung

EKS Control-Plane-Logs nach CloudWatch aktivieren:

# Im EKS-Modul:
cluster_enabled_log_types = [
  "api",
  "audit",
  "authenticator",
  "controllerManager",
  "scheduler"
]

Besonders die Audit-Logs sind fuer DSGVO-Nachweise wichtig: Sie dokumentieren, wer wann auf welche Ressourcen zugegriffen hat.

Kostenoptimierung in der Praxis

Instance-Typen im Vergleich

InstancevCPURAMOn-Demand (eu-central-1)Spot (ca.)Einsatz
t3.medium24 GB~38 EUR/Monat~12 EURDev, kleine Workloads
m6i.large28 GB~97 EUR/Monat~35 EURStandard-Workloads
m6i.xlarge416 GB~193 EUR/Monat~65 EURGroessere Services
c6i.xlarge48 GB~170 EUR/Monat~55 EURCPU-intensive Workloads
r6i.large216 GB~126 EUR/Monat~42 EURDatenbanken, Caching

Savings Plans

Fuer vorhersehbare Workloads bieten Compute Savings Plans (1 oder 3 Jahre) bis zu 40% Ersparnis gegenueber On-Demand. Im Gegensatz zu Reserved Instances sind sie flexibel ueber Instance-Familien und Regionen hinweg.

Weitere Hebel

  • VPC Endpoints fuer S3 und ECR: spart NAT-Gateway-Traffic-Kosten
  • Spot Instances fuer Batch-Jobs, CI/CD-Runner und nicht-kritische Workloads
  • Right-Sizing mit dem Kubernetes Metrics Server und kubectl top
  • Karpenter Consolidation raeumt unterbelegte Nodes automatisch auf

Vertiefend: Kubernetes Kosten optimieren

Monitoring-Setup

Fuer EKS bietet sich die Kombination aus AWS-nativen und Open-Source-Tools an:

# Amazon CloudWatch Container Insights aktivieren
aws eks create-addon \
  --cluster-name production \
  --addon-name amazon-cloudwatch-observability \
  --region eu-central-1

# Alternativ: Prometheus + Grafana ueber Helm
helm repo add prometheus-community https://prometheus-community.github.io/helm-charts
helm install monitoring prometheus-community/kube-prometheus-stack \
  --namespace monitoring \
  --create-namespace \
  --set grafana.adminPassword=sicheres-passwort

Mehr zum Thema: Kubernetes Monitoring und Observability

EKS-Upgrade-Strategie

EKS-Versionen werden ca. 14 Monate unterstuetzt. Planen Sie Upgrades alle 3-4 Monate ein:

  1. Add-ons pruefen: Kompatibilitaet von VPC-CNI, CoreDNS, kube-proxy mit der neuen Version
  2. Staging zuerst: Cluster-Upgrade auf Staging, 1 Woche Beobachtung
  3. Control Plane upgraden: terraform apply mit neuer cluster_version
  4. Node Groups rollen: Managed Node Groups aktualisieren sich per Rolling Update
  5. Validieren: Smoke Tests, Monitoring pruefen

Weiterführende Artikel


Sie wollen EKS produktionsreif aufsetzen oder einen bestehenden Cluster optimieren? Wir unterstuetzen bei Architektur, Terraform-Setup, Kostenoptimierung und DSGVO-Compliance. Kontaktieren Sie uns fuer ein unverbindliches Erstgespraech.

Kubernetes-Beratung gesucht?

Wir helfen deutschen Unternehmen bei der Kubernetes-Implementierung, Migration und Optimierung. DSGVO-konform und praxiserprobt.

📖 Verwandte Artikel

Weitere interessante Beiträge zu ähnlichen Themen

kubernetesdsgvo

Kubernetes Compliance in Deutschland: Governance-Richtlinien für Enterprise

Sichern Sie Ihre Kubernetes Compliance in Deutschland und stärken Sie die Governance im Enterprise-Umfeld! Dieser umfassende Leitfaden beleuchtet essenzielle Governance-Richtlinien, effektive Automatisierung und bewährte Enterprise Controls für Ihr Unternehmen, um regulatorische Anforderungen wie NIS2 und DSGVO zu erfüllen und gleichzeitig Effizienz und Sicherheit zu maximieren.

Weiterlesen →