Zum Inhalt

Best Practices

Diese Seite sammelt bewährte Praktiken für den Betrieb von Workloads auf der ayedo Kubernetes Distribution. Die Einhaltung dieser Best Practices verbessert Sicherheit, Zuverlässigkeit und Wartbarkeit Ihrer Anwendungen.

Sicherheit

Verwenden Sie nicht-privilegierte Container

Warum: Privilegierte Container haben vollen Zugriff auf den Host und stellen ein erhebliches Sicherheitsrisiko dar.

Wie:

apiVersion: v1
kind: Pod
metadata:
  name: secure-pod
spec:
  securityContext:
    runAsNonRoot: true
    runAsUser: 1000
  containers:
  - name: app
    image: myapp:latest
    securityContext:
      allowPrivilegeEscalation: false
      capabilities:
        drop:
        - ALL
      readOnlyRootFilesystem: true

Enforcement: Nutzen Sie Kyverno, um privilegierte Container automatisch zu verbieten.

Weitere Informationen:

Implementieren Sie Network Policies

Warum: Network Policies ermöglichen Mikrosegmentierung und reduzieren die Angriffsfläche.

Wie:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default-deny-all
  namespace: production
spec:
  podSelector: {}
  policyTypes:
  - Ingress
  - Egress

Empfehlung: Starten Sie mit "Deny All" und öffnen Sie nur explizit benötigte Verbindungen.

Weitere Informationen:

Nutzen Sie Secrets Management

Warum: Credentials sollten niemals in Code oder ConfigMaps gespeichert werden.

Wie:

Verwenden Sie HashiCorp Vault mit dem External Secrets Operator:

apiVersion: external-secrets.io/v1beta1
kind: ExternalSecret
metadata:
  name: database-credentials
spec:
  secretStoreRef:
    name: vault
    kind: SecretStore
  target:
    name: db-credentials
  data:
  - secretKey: password
    remoteRef:
      key: database/prod
      property: password

Best Practices:

  • Secrets niemals in Git committen
  • External Secrets Operator für automatische Synchronisation
  • Vault für zentrale Secrets-Verwaltung
  • Regelmäßige Rotation von Credentials
  • Least-Privilege Access Policies

Weitere Informationen:

Scannen Sie Container Images

Warum: Container Images können Schwachstellen (CVEs) enthalten, die ausgenutzt werden können.

Wie:

Nutzen Sie Harbor mit aktiviertem Vulnerability Scanning:

  1. Pushen Sie Images in die Harbor Registry
  2. Harbor scannt automatisch auf Schwachstellen
  3. Implementieren Sie eine Policy, die vulnerable Images ablehnt

Admission Control:

apiVersion: v1
kind: Policy
metadata:
  name: block-vulnerable-images
spec:
  rules:
  - name: check-vulnerabilities
    match:
      resources:
        kinds:
        - Pod
    validate:
      message: "Image hat kritische Schwachstellen"
      pattern:
        spec:
          containers:
          - image: "harbor.ayedo.de/*"

Weitere Informationen:

Implementieren Sie Pod Security Standards

Warum: Pod Security Standards definieren unterschiedliche Isolations-Level für Pods.

Empfohlene Profile:

  • Privileged: Nur für Infrastruktur-Workloads
  • Baseline: Minimale Einschränkungen für typische Workloads
  • Restricted: Strengste Einschränkungen (empfohlen für Production)

Namespace-Level Enforcement:

apiVersion: v1
kind: Namespace
metadata:
  name: production
  labels:
    pod-security.kubernetes.io/enforce: restricted
    pod-security.kubernetes.io/audit: restricted
    pod-security.kubernetes.io/warn: restricted

Zuverlässigkeit

Definieren Sie Resource Requests und Limits

Warum: Verhindert Resource-Starvation und ermöglicht effektives Scheduling.

Wie:

apiVersion: v1
kind: Pod
metadata:
  name: myapp
spec:
  containers:
  - name: app
    image: myapp:latest
    resources:
      requests:
        memory: "256Mi"
        cpu: "100m"
      limits:
        memory: "512Mi"
        cpu: "500m"

Empfehlung:

  • Requests: Basierend auf durchschnittlicher Auslastung
  • Limits: 1.5-2x der Requests für Memory, 2-4x für CPU

Weitere Informationen:

Implementieren Sie Health Checks

Warum: Kubernetes kann fehlerhafte Pods automatisch neu starten.

Wie:

apiVersion: v1
kind: Pod
metadata:
  name: myapp
spec:
  containers:
  - name: app
    image: myapp:latest
    livenessProbe:
      httpGet:
        path: /healthz
        port: 8080
      initialDelaySeconds: 30
      periodSeconds: 10
    readinessProbe:
      httpGet:
        path: /ready
        port: 8080
      initialDelaySeconds: 5
      periodSeconds: 5

Best Practices:

  • Liveness: Startet Container bei Deadlocks neu
  • Readiness: Entfernt Pod aus Service bei Nicht-Bereitschaft
  • Startup: Für langsam startende Container (> 30s)

Verwenden Sie Multiple Replicas

Warum: Verhindert Single Point of Failure.

Wie:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: myapp
spec:
  replicas: 3
  selector:
    matchLabels:
      app: myapp
  template:
    metadata:
      labels:
        app: myapp
    spec:
      affinity:
        podAntiAffinity:
          requiredDuringSchedulingIgnoredDuringExecution:
          - labelSelector:
              matchExpressions:
              - key: app
                operator: In
                values:
                - myapp
            topologyKey: kubernetes.io/hostname

Empfehlung:

  • Mindestens 3 Replicas für Production
  • Pod Anti-Affinity zur Verteilung auf verschiedene Nodes
  • Pod Disruption Budgets für kontrollierte Updates

Implementieren Sie Horizontal Pod Autoscaling

Warum: Automatische Skalierung basierend auf Last.

Wie:

apiVersion: autoscaling/v2
kind: HorizontalPodAutoscaler
metadata:
  name: myapp
spec:
  scaleTargetRef:
    apiVersion: apps/v1
    kind: Deployment
    name: myapp
  minReplicas: 3
  maxReplicas: 10
  metrics:
  - type: Resource
    resource:
      name: cpu
      target:
        type: Utilization
        averageUtilization: 70
  - type: Resource
    resource:
      name: memory
      target:
        type: Utilization
        averageUtilization: 80

Konfigurieren Sie Backups

Warum: Disaster Recovery und Datensicherheit.

Wie:

Nutzen Sie Velero für automatische Backups:

apiVersion: velero.io/v1
kind: Schedule
metadata:
  name: daily-backup
  namespace: velero
spec:
  schedule: "0 2 * * *"  # Täglich um 2:00 Uhr
  template:
    includedNamespaces:
    - production
    - staging
    ttl: 720h  # 30 Tage

Best Practices:

  • Täglich Backups für Production
  • Geografisch getrennte Backup-Speicherung
  • Regelmäßige Recovery-Tests

Weitere Informationen:

Observability

Implementieren Sie Structured Logging

Warum: Strukturierte Logs sind leichter zu durchsuchen und zu analysieren.

Wie:

{
  "timestamp": "2025-11-06T14:30:00Z",
  "level": "INFO",
  "service": "api",
  "message": "Request processed",
  "request_id": "abc-123",
  "user_id": "user-456",
  "duration_ms": 123
}

Best Practices:

  • JSON-Format für Log-Ausgabe
  • Correlation IDs für Request-Tracing
  • Strukturierte Felder für Filterung

Exportieren Sie Metrics

Warum: Metriken ermöglichen proaktives Monitoring und Alerting.

Wie:

Implementieren Sie /metrics Endpoint im Prometheus-Format (VictoriaMetrics ist Prometheus-kompatibel):

http.Handle("/metrics", promhttp.Handler())

Erstellen Sie eine VMServiceScrape Custom Resource für VictoriaMetrics:

apiVersion: operator.victoriametrics.com/v1beta1
kind: VMServiceScrape
metadata:
  name: myapp
  labels:
    app: myapp
spec:
  selector:
    matchLabels:
      app: myapp
  endpoints:
  - port: metrics
    interval: 30s
    path: /metrics

Wichtige Metriken:

  • Request Rate, Errors, Duration (RED)
  • CPU, Memory, Disk (USE)
  • Business Metrics (z.B. Orders/minute)

Weitere Informationen:

Implementieren Sie Distributed Tracing

Warum: Debugging von Performance-Problemen in Microservices.

Tools:

  • Jaeger für Tracing
  • OpenTelemetry für Instrumentation

GitOps

Verwalten Sie Konfiguration in Git

Warum: Version Control, Code Review, Audit Trail.

Wie:

Für Plattform-Komponenten und Infrastruktur:

Verwenden Sie Polycrate Workspaces in Git:

# workspace.poly
name: production-platform

blocks:
  - name: cilium
    from: cargo.ayedo.cloud/ayedo/k8s/cilium:1.0.0

  - name: victoriametrics
    from: cargo.ayedo.cloud/ayedo/k8s/victoria-metrics-stack:1.0.0

  - name: harbor
    from: cargo.ayedo.cloud/ayedo/k8s/harbor:2.0.0
    config:
      domain: harbor.example.com

Für Anwendungen (Application Developer):

Nutzen Sie Flux oder ArgoCD:

# ArgoCD Application
apiVersion: argoproj.io/v1alpha1
kind: Application
metadata:
  name: myapp
  namespace: argocd
spec:
  project: default
  source:
    repoURL: https://gitlab.example.com/myteam/myapp
    targetRevision: main
    path: helm
  destination:
    server: https://kubernetes.default.svc
    namespace: production
  syncPolicy:
    automated:
      prune: true
      selfHeal: true

Best Practices:

  • Plattform-Komponenten: Ausschließlich via Polycrate deployen
  • Applications: Via Flux oder ArgoCD deployen (Developer Self-Service)
  • Separate Repositories für Platform (Polycrate) und Applications (GitOps)
  • Branch-basierte Environments (main = prod, develop = staging)
  • Pull Requests für alle Changes
  • Polycrate Workspaces in Git versionieren

Weitere Informationen:

Verwenden Sie Helm Charts

Warum: Templating und Paketierung von Kubernetes-Ressourcen.

Empfehlung:

Nutzen Sie ohMyHelm für standardisierte Deployments:

dependencies:
  - name: ohmyhelm
    alias: myapp
    repository: https://gitlab.com/ayedocloudsolutions/ohmyhelm
    version: 1.13.0

Weitere Informationen:

Namespaces

Verwenden Sie Namespaces zur Trennung

Warum: Logische Isolation und RBAC-Scoping.

Empfohlene Struktur:

production/
├── frontend
├── backend
├── database
staging/
├── frontend
├── backend
├── database
development/
├── *

Best Practices:

  • Umgebungs-basiert: production, staging, development
  • Team-basiert: team-a, team-b
  • App-basiert: app-1, app-2 (bei Multi-Tenancy)

Setzen Sie Resource Quotas

Warum: Verhindert dass ein Namespace alle Cluster-Ressourcen verbraucht.

Wie:

apiVersion: v1
kind: ResourceQuota
metadata:
  name: production-quota
  namespace: production
spec:
  hard:
    requests.cpu: "100"
    requests.memory: "200Gi"
    limits.cpu: "200"
    limits.memory: "400Gi"
    persistentvolumeclaims: "50"

Implementieren Sie Network Policies pro Namespace

Warum: Default Deny auf Namespace-Ebene.

Wie:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: deny-all
  namespace: production
spec:
  podSelector: {}
  policyTypes:
  - Ingress
  - Egress

Deployment-Strategien

Verwenden Sie Rolling Updates

Warum: Zero-Downtime Deployments.

Wie:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: myapp
spec:
  strategy:
    type: RollingUpdate
    rollingUpdate:
      maxSurge: 1
      maxUnavailable: 0
  replicas: 3

Best Practices:

  • maxUnavailable: 0 für Zero-Downtime
  • maxSurge: 1 für kontrolliertes Rollout
  • Health Checks für automatisches Rollback

Testen Sie in Staging

Warum: Probleme vor Production erkennen.

Empfehlung:

  1. Deploy to Staging
  2. Automated Tests (Integration, E2E)
  3. Manual Verification
  4. Promote to Production

Implementieren Sie Canary Deployments

Warum: Graduelle Ausrollung mit geringem Risiko.

Tools:

  • Flux Progressive Delivery
  • Argo Rollouts
  • Flagger

Compliance

Aktivieren Sie Audit Logging

Warum: Nachvollziehbarkeit für Compliance und Forensics.

Wie:

Audit Logging ist standardmäßig aktiviert in der ayedo Kubernetes Distribution.

Weitere Informationen:

Dokumentieren Sie Ihre Architektur

Warum: Wichtig für Audits und Onboarding.

Was dokumentieren:

  • Netzwerk-Topologie
  • Datenflüsse
  • Zugriffskontrollen
  • Backup & Recovery Prozesse

Weiterführende Ressourcen

Support

Für Beratung zu Best Practices: