> ## Documentation Index
> Fetch the complete documentation index at: https://docs.shiftlabs.dev/llms.txt
> Use this file to discover all available pages before exploring further.

# StatefulSets

> Manage stateful applications with stable identities and persistent storage

StatefulSets manage stateful applications that require stable network identities, persistent storage, and ordered deployment. They are ideal for databases, message queues, and other applications that maintain state.

## Key Concepts

<CardGroup cols={2}>
  <Card title="StatefulSet" icon="database">
    A controller that manages pods with stable identities and persistent storage.
  </Card>

  <Card title="Stable Identity" icon="fingerprint">
    Each pod gets a persistent hostname (e.g., mysql-0, mysql-1) that survives restarts.
  </Card>

  <Card title="Headless Service" icon="server">
    A service that provides DNS entries for each pod without load balancing.
  </Card>

  <Card title="VolumeClaimTemplate" icon="hard-drive">
    Template for creating PersistentVolumeClaims for each pod automatically.
  </Card>
</CardGroup>

## Required Permissions

| Action              | Permission                                     |
| ------------------- | ---------------------------------------------- |
| View statefulsets   | `iam:project:infrastructure:kubernetes:read`   |
| Scale statefulset   | `iam:project:infrastructure:kubernetes:write`  |
| Restart statefulset | `iam:project:infrastructure:kubernetes:write`  |
| Create statefulset  | `iam:project:infrastructure:kubernetes:write`  |
| Edit statefulset    | `iam:project:infrastructure:kubernetes:write`  |
| Delete statefulset  | `iam:project:infrastructure:kubernetes:delete` |

## StatefulSet Status Values

| Status          | Description                   |
| --------------- | ----------------------------- |
| **Running**     | All replicas are ready        |
| **Updating**    | Rolling update in progress    |
| **NotReady**    | Some replicas are not ready   |
| **Scaled to 0** | StatefulSet has zero replicas |
| **Unknown**     | Status cannot be determined   |

## StatefulSet Metrics

| Metric        | Description                         |
| ------------- | ----------------------------------- |
| **Replicas**  | Desired number of pods              |
| **Ready**     | Pods that are ready (ready/desired) |
| **Current**   | Pods with current spec version      |
| **Updated**   | Pods updated to latest template     |
| **Available** | Pods available for service          |

## How to View StatefulSets

<Steps>
  <Step title="Select Cluster">
    Choose a cluster from the cluster dropdown.
  </Step>

  <Step title="Select Namespace">
    Choose a namespace or select "all" to view StatefulSets across all namespaces.
  </Step>

  <Step title="Filter and Search">
    Use the search box to find StatefulSets by name, or filter by status.
  </Step>
</Steps>

## How to View StatefulSet Details

<Steps>
  <Step title="Find the StatefulSet">
    Locate the StatefulSet in the list.
  </Step>

  <Step title="Click StatefulSet Name">
    Click on the StatefulSet name to open the detail drawer.
  </Step>

  <Step title="Review Details">
    View StatefulSet information including:

    * Pod status and ordinal indices
    * Container specifications
    * Headless service name
    * Volume claim templates
    * Update strategy configuration
  </Step>
</Steps>

## How to Scale a StatefulSet

<Steps>
  <Step title="Find the StatefulSet">
    Locate the StatefulSet in the list.
  </Step>

  <Step title="Open Actions Menu">
    Click the actions menu (three dots) on the StatefulSet row.
  </Step>

  <Step title="Click Scale">
    Select **Scale** to open the scale dialog.
  </Step>

  <Step title="Set Replica Count">
    Enter the desired number of replicas.
  </Step>

  <Step title="Apply">
    Click **Scale** to apply the change.
  </Step>
</Steps>

**Scaling behavior:**

* **Scale up**: New pods are created in order (pod-0, pod-1, pod-2...)
* **Scale down**: Pods are terminated in reverse order (highest ordinal first)
* Each pod must be Running and Ready before the next is created/terminated

<Warning>
  Scaling down does NOT delete PersistentVolumeClaims. Data persists and will be reattached if you scale back up.
</Warning>

## How to Restart a StatefulSet

Restart triggers a rolling restart of all pods.

<Steps>
  <Step title="Find the StatefulSet">
    Locate the StatefulSet in the list.
  </Step>

  <Step title="Open Actions Menu">
    Click the actions menu on the StatefulSet row.
  </Step>

  <Step title="Click Restart">
    Select **Restart** from the menu.
  </Step>

  <Step title="Monitor">
    Watch the status change to Updating as pods are replaced in order.
  </Step>
</Steps>

<Info>
  Restart performs an ordered rolling restart. By default, pods are updated one at a time in reverse ordinal order (highest to lowest).
</Info>

## How to Create a StatefulSet

<Steps>
  <Step title="Click Create StatefulSet">
    Click the **Create StatefulSet** button in the page header.
  </Step>

  <Step title="Write YAML">
    Enter the StatefulSet manifest in YAML format. Include:

    * `serviceName` pointing to a headless service
    * `volumeClaimTemplates` if persistent storage is needed
  </Step>

  <Step title="Select Namespace">
    Choose the target namespace for the StatefulSet.
  </Step>

  <Step title="Create">
    Click **Create** to apply the manifest.
  </Step>
</Steps>

<Tip>
  Create the headless service before the StatefulSet. The service must have `clusterIP: None` and selectors matching the StatefulSet pods.
</Tip>

## How to Edit a StatefulSet

<Steps>
  <Step title="Open Actions Menu">
    Click the actions menu on the StatefulSet row.
  </Step>

  <Step title="Click Edit YAML">
    Select **Edit YAML** to open the editor.
  </Step>

  <Step title="Modify Spec">
    Edit the StatefulSet specification. Common changes:

    * Container image (triggers rolling update)
    * Resource requests/limits
    * Environment variables
    * Replica count
  </Step>

  <Step title="Save">
    Click **Update** to apply changes.
  </Step>
</Steps>

<Warning>
  Some StatefulSet fields are immutable after creation: `serviceName`, `podManagementPolicy`, and `volumeClaimTemplates`. To change these, delete and recreate the StatefulSet.
</Warning>

## How to Delete a StatefulSet

<Steps>
  <Step title="Open Actions Menu">
    Click the actions menu on the StatefulSet row.
  </Step>

  <Step title="Click Delete">
    Select **Delete** from the menu.
  </Step>

  <Step title="Confirm">
    Confirm the deletion.
  </Step>
</Steps>

<Warning>
  Deleting a StatefulSet removes the controller and pods but does NOT delete PersistentVolumeClaims. You must manually delete PVCs to free storage.
</Warning>

## Update Strategies

StatefulSets support two update strategies:

| Strategy          | Description                                                                    |
| ----------------- | ------------------------------------------------------------------------------ |
| **RollingUpdate** | Updates pods in reverse ordinal order (default). Configurable via `partition`. |
| **OnDelete**      | Only updates pods when they are manually deleted.                              |

**RollingUpdate with partition:**

* Pods with ordinal >= partition are updated
* Pods with ordinal \< partition are not updated
* Useful for canary deployments

```yaml theme={null}
updateStrategy:
  type: RollingUpdate
  rollingUpdate:
    partition: 2  # Only update pods 2, 3, 4... Leave 0, 1 on old version
```

## Pod Management Policy

| Policy           | Description                                         |
| ---------------- | --------------------------------------------------- |
| **OrderedReady** | Create/delete pods one at a time in order (default) |
| **Parallel**     | Create/delete all pods simultaneously               |

<Info>
  OrderedReady is recommended for most stateful applications. Use Parallel only when pods don't depend on each other.
</Info>

## Troubleshooting

<AccordionGroup>
  <Accordion title="StatefulSet stuck in Updating">
    * A pod may be failing readiness checks
    * Check pod events and logs for errors
    * Verify PVC is bound and storage is available
    * Check if previous pod terminated cleanly
  </Accordion>

  <Accordion title="Pods not starting in order">
    * Previous pod must be Running and Ready first
    * Check pod events for scheduling issues
    * Verify PVC binding if using persistent storage
    * Check headless service exists and selectors match
  </Accordion>

  <Accordion title="PVC not being created">
    * Verify `volumeClaimTemplates` is correctly defined
    * Check StorageClass exists and is default or specified
    * Verify storage provisioner is working
    * Check for quota limits on PVCs
  </Accordion>

  <Accordion title="Data lost after pod restart">
    * Ensure PVC is correctly mounted in pod spec
    * Verify data is written to the mounted path, not container filesystem
    * Check PVC still exists and is bound
  </Accordion>

  <Accordion title="Cannot connect to pods via headless service">
    * Verify headless service has `clusterIP: None`
    * Check service selector matches pod labels
    * Use full DNS name: `pod-0.service-name.namespace.svc.cluster.local`
    * Verify pods are Ready
  </Accordion>

  <Accordion title="Scale down not deleting pods">
    * Pods are deleted in reverse order, one at a time
    * Each pod must terminate before the next begins
    * Check for pods stuck in Terminating state
    * Verify no finalizers blocking deletion
  </Accordion>
</AccordionGroup>

## FAQ

<AccordionGroup>
  <Accordion title="What's the difference between StatefulSet and Deployment?">
    **Deployments** are for stateless applications where pods are interchangeable. **StatefulSets** provide stable identities, ordered operations, and persistent storage for stateful applications like databases.
  </Accordion>

  <Accordion title="Why do StatefulSets need a headless service?">
    The headless service provides DNS entries for each pod (e.g., `mysql-0.mysql.default.svc.cluster.local`). This allows clients to connect to specific pods by name, which is essential for stateful applications.
  </Accordion>

  <Accordion title="Are PVCs deleted when I delete a StatefulSet?">
    No. PersistentVolumeClaims are preserved to prevent data loss. You must manually delete PVCs if you want to free the storage.
  </Accordion>

  <Accordion title="How do I perform a canary update?">
    Use the `partition` field in RollingUpdate strategy. Set partition to N to only update pods with ordinal >= N, leaving lower ordinals on the old version for testing.
  </Accordion>

  <Accordion title="Can I scale a StatefulSet to zero?">
    Yes. Scaling to zero terminates all pods but preserves PVCs. When you scale back up, pods reattach to their original PVCs with data intact.
  </Accordion>

  <Accordion title="Why are pods created one at a time?">
    OrderedReady policy ensures each pod is Running and Ready before creating the next. This is crucial for applications like databases where initialization order matters.
  </Accordion>

  <Accordion title="How do I update the volumeClaimTemplate?">
    VolumeClaimTemplates are immutable. To change storage configuration, you must delete the StatefulSet (with orphan policy to keep pods), update the manifest, and recreate it.
  </Accordion>

  <Accordion title="What happens to my data if a node fails?">
    If using dynamically provisioned storage, the PVC remains bound. When the pod is rescheduled to another node, it reattaches to the same PV (if the storage supports it) or waits for the node to recover.
  </Accordion>
</AccordionGroup>
