Générateur K8s StatefulSet

Générateur de YAML StatefulSet et Headless Service Kubernetes

Générez des manifestes Kubernetes StatefulSet de qualité production avec Headless Service associé, volumeClaimTemplates persistants, réplicas et podManagementPolicy.

Préréglages
Configuration de StatefulSet et service
Les pods avec ordinal >= partition seront mis à jour en premier (Canary)
Nombre de pods indisponibles pendant le déploiement
:
:
# ============================================================================
# Kubernetes StatefulSet: postgres-ha
# Generated via ToolsAA - 100% Client-Side Stateful Workload Builder
# Headless Network Domain: postgres-ha-headless.database.svc.cluster.local
# Pod Stable FQDN: postgres-ha-[0..2].postgres-ha-headless.database.svc.cluster.local
# ============================================================================
apiVersion: apps/v1
kind: StatefulSet
metadata:
  name: postgres-ha
  namespace: database
  labels:
    app: "postgres-ha"
    tier: "database"
    app.kubernetes.io/managed-by: toolsaa
  annotations:
    cluster.toolsaa.com/role: "primary-replica"
spec:
  serviceName: "postgres-ha-headless"
  replicas: 3
  podManagementPolicy: OrderedReady
  updateStrategy:
    type: RollingUpdate
    rollingUpdate:
      partition: 0
      maxUnavailable: 1
  revisionHistoryLimit: 10
  minReadySeconds: 10
  persistentVolumeClaimRetentionPolicy:
    whenDeleted: Retain
    whenScaled: Retain
  selector:
    matchLabels:
      app: "postgres-ha"
  template:
    metadata:
      labels:
        app: "postgres-ha"
        tier: "database"
      annotations:
        prometheus.io/scrape: "true"
        prometheus.io/port: "9187"
    spec:
      serviceAccountName: postgres-sa
      terminationGracePeriodSeconds: 120
      securityContext:
        runAsNonRoot: true
        runAsUser: 999
        runAsGroup: 999
        fsGroup: 999
        fsGroupChangePolicy: "OnRootMismatch"
      affinity:
        podAntiAffinity:
          preferredDuringSchedulingIgnoredDuringExecution:
          - weight: 100
            podAffinityTerm:
              labelSelector:
                matchExpressions:
                - key: app
                  operator: In
                  values: ["postgres-ha"]
              topologyKey: "kubernetes.io/hostname"
      nodeSelector:
        node-role.kubernetes.io/database: "true"
      containers:
      - name: postgres
        image: postgres:16-alpine
        imagePullPolicy: IfNotPresent
        securityContext:
          allowPrivilegeEscalation: false
          capabilities:
            drop:
            - ALL
        ports:
        - name: postgresql
          containerPort: 5432
          protocol: TCP
        env:
        - name: POD_NAME
          valueFrom:
            fieldRef:
              fieldPath: metadata.name
        - name: POD_IP
          valueFrom:
            fieldRef:
              fieldPath: status.podIP
        - name: POSTGRES_DB
          value: "app_production"
        - name: POSTGRES_USER
          value: "postgres"
        - name: PGDATA
          value: "/var/lib/postgresql/data/pgdata"
        resources:
          requests:
            cpu: "500m"
            memory: "1Gi"
          limits:
            cpu: "2000m"
            memory: "4Gi"
        volumeMounts:
        - name: pgdata
          mountPath: "/var/lib/postgresql/data"
        livenessProbe:
          exec:
            command:
            - "pg_isready"
            - "-U"
            - "postgres"
          initialDelaySeconds: 30
          periodSeconds: 10
          timeoutSeconds: 5
          successThreshold: 1
          failureThreshold: 3
        readinessProbe:
          exec:
            command:
            - "pg_isready"
            - "-U"
            - "postgres"
            - "-h"
            - "127.0.0.1"
          initialDelaySeconds: 15
          periodSeconds: 5
          timeoutSeconds: 3
          successThreshold: 1
          failureThreshold: 3
        startupProbe:
          exec:
            command:
            - "pg_isready"
            - "-U"
            - "postgres"
          initialDelaySeconds: 10
          periodSeconds: 5
          timeoutSeconds: 3
          successThreshold: 1
          failureThreshold: 15
  volumeClaimTemplates:
  - metadata:
      name: pgdata
      labels:
        app: "postgres-ha"
    spec:
      accessModes: ["ReadWriteOnce"]
      storageClassName: "gp3"
      resources:
        requests:
          storage: 50Gi
Répliques avec étatOrderedReady
3 Pods avec état

Partition: 0 | Stratégie: RollingUpdate

Modèles de volume (PVC)gp3
50Gi / pod (1 modèles)

Rétention: Retain | fsGroup :: 999

Posture de durcissementNiveau de sécurité A+
100 / 100 Disponibilité

Sondes: 3/3 actives

Génération de manifestes 100% côté client

Aucun transfert vers des serveurs externes. Tous les manifestes StatefulSet, services headless et modèles de PVC sont synthétisés directement dans la mémoire du navigateur.

Cycle de vie ordonné et identité DNS stable

Garantit des identités ordinales uniques, un adressage DNS prévisible via Headless Service, un séquençage OrderedReady et des modèles de volume persistant.

Durcissement de sécurité CIS et exports multiples

Applique des contextes de sécurité non-root, supprime les fonctionnalités Linux et produit des sorties prêtes pour la production pour Helm, Kustomize et kubectl.

Référence technique et guide d'architecture

Guide du Développeur du Générateur de YAML Kubernetes StatefulSet & Headless Service — Guide de référence

Générez des manifestes Kubernetes StatefulSet de qualité production avec Headless Service associé, volumeClaimTemplates persistants, réplicas et podManagementPolicy.

Paramètres clés et contrôles

spec.serviceNamestring

Nom du Headless Service associé (clusterIP: None) régissant l'identité réseau et le routage DNS SRV des ordinaux de pods.

Par défaut : Requis
spec.replicasinteger

Nombre souhaité d'instances de pods avec état (0 à N-1) créées séquentiellement dans l'ordre croissant.

Par défaut : 3
spec.podManagementPolicyenum (OrderedReady | Parallel)

Politique d'ordonnancement du cycle de vie des pods. 'OrderedReady' démarre les pods séquentiellement en attendant leur état Ready ; 'Parallel' crée ou supprime tous les pods simultanément.

Par défaut : OrderedReady
spec.volumeClaimTemplatesarray of objects

Modèles de PersistentVolumeClaim provisionnant dynamiquement un stockage persistant dédié pour chaque indice ordinal de pod.

Par défaut : Requis
spec.updateStrategyobject

Stratégie de mise à jour progressive automatisée avec paramètre optionnel 'partition' pour canary ou mode manuel 'OnDelete'.

Par défaut : RollingUpdate

Conseils de pro et bonnes practices

Un StatefulSet nécessite

Un StatefulSet nécessite impérativement un Headless Service avec 'clusterIP: None'. CoreDNS génère automatiquement des enregistrements A/AAAA et SRV stables au format '<nom-pod>.<nom-service>.<namespace>.svc.cluster.local', cruciaux pour les bases de données répliquées et les clusters Raft.

Définissez

Définissez 'spec.updateStrategy.rollingUpdate.partition' à réplicas - 1 pour déployer la nouvelle image de conteneur uniquement sur le pod à l'ordinal le plus élevé (ex. statefulset-2) en mode canary avant de propager la mise à jour à l'ensemble du cluster.

Kubernetes ne supprime volontairement

Kubernetes ne supprime volontairement jamais les PVCs issus de volumeClaimTemplates lors d'une réduction d'échelle ou de la suppression du StatefulSet. Lors d'un rééchelonnement, les nouveaux pods se réassocient aux mêmes volumes. Depuis K8s 1.27, 'persistentVolumeClaimRetentionPolicy' permet d'automatiser cette gestion.

Les systèmes distribués avec état tels

Les systèmes distribués avec état tels que ZooKeeper, Kafka ou Cassandra dépendent d'un quorum de réplication. Configurez systématiquement un PodDisruptionBudget avec 'minAvailable: 2' ou 'maxUnavailable: 1' pour empêcher les vidages de nœuds (node drains) de provoquer un split-brain.

Pièges courants et dépannage

Le pod reste bloqué à l'état Pending avec 'persistentvolumeclaim unbound'

Exécutez 'kubectl describe pvc <nom-pvc>'. Vérifiez que la storageClassName configurée existe bien sur le cluster, que le provisionneur CSI dynamique fonctionne et que les accessModes (ex. ReadWriteOnce) sont compatibles avec le pool de stockage sous-jacent.

La mise à jour progressive ou le redimensionnement se bloque sur un pod ordinal précis

Avec la politique 'OrderedReady', Kubernetes interrompt le cycle si le pod ordinal précédent échoue à son test de préparation (readinessProbe). Inspectez les événements avec 'kubectl describe pod <nom>' et corrigez les erreurs du service applicatif.

La découverte entre pairs échoue avec l'erreur 'NXDOMAIN' sur le nom d'hôte Headless

Vérifiez que 'spec.serviceName' dans le StatefulSet correspond exactement au 'metadata.name' du Headless Service. Assurez-vous que le service comporte bien 'clusterIP: None' et que les sélecteurs de labels sont parfaitement concordants.

Foire aux questions (FAQ)

Quelle est la différence fondamentale entre un Deployment et un StatefulSet dans Kubernetes ?▼

Un Deployment gère des pods interchangeables et sans état identifiés par des suffixes aléatoires avec un stockage partagé ou éphémère. Un StatefulSet fournit des identifiants ordinaux uniques et stables (app-0, app-1), un ordre déterministe de démarrage et d'arrêt, un stockage persistant dédié par réplica et des identités réseau DNS prévisibles via un Headless Service.

Pourquoi un StatefulSet nécessite-t-il obligatoirement un Headless Service ('clusterIP: None') ?▼

Les services Kubernetes standard attribuent une adresse IP virtuelle unique (ClusterIP) qui équilibre le trafic de façon aléatoire entre les pods prêts. Les bases de données distribuées requièrent en revanche un adressage direct point à point vers des instances spécifiques (ex. primaire vs réplica). Un Headless Service contourne cette VIP et génère des enregistrements DNS A pointant directement sur l'IP propre de chaque pod.

Que deviennent les PersistentVolumeClaims (PVCs) lorsqu'un StatefulSet est réduit ou supprimé ?▼

Par défaut, Kubernetes ne supprime jamais les PVC créés par volumeClaimTemplates afin de préserver l'intégrité des données stockées. En cas de rééchelonnement vers le haut, les nouveaux pods se rattachent automatiquement à leurs volumes ordinaux respectifs. La suppression d'un stockage devenu obsolète requiert la commande 'kubectl delete pvc'.

Quand doit-on utiliser 'podManagementPolicy: Parallel' au lieu de 'OrderedReady' ?▼

Utilisez 'Parallel' pour les applications avec état capables de gérer le clustering et le consensus de manière autonome sans dépendre d'un démarrage séquentiel, ou lorsque vous souhaitez accélérer considérablement les montées en charge et les mises à jour progressives simultanées.

Comment fonctionne le paramètre 'updateStrategy.rollingUpdate.partition' ?▼

Le paramètre partition établit un seuil ordinal. Seuls les pods dont l'indice ordinal est supérieur ou égal à la valeur de partition sont mis à jour. En définissant partition à réplicas - 1, seul le dernier pod est mis à jour pour servir de test canary. En ramenant ensuite cette valeur à 0, la mise à jour se déploie sur l'ensemble des pods.

Outils et utilitaires connexes

Tous les outils →