StorageClass & PVC

A StorageClass defines how volumes are provisioned; a PersistentVolumeClaim requests one for a pod.

Syntaxkubectl get storageclass

Kubernetes separates what storage you want from how it's created. Two objects make this work:

  • StorageClass — a template that says which provisioner to use and with what settings (for EBS: volume type, IOPS, encryption).
  • PersistentVolumeClaim (PVC) — a pod's request for a volume of a given size and class. The CSI driver dynamically creates the real volume to satisfy it.

Dynamic provisioning flow

  1. You define a StorageClass once.
  2. A pod references a PVC.
  3. The driver provisions a matching EBS/EFS volume and binds it.

Set a default StorageClass so PVCs without an explicit class still get storage.

Example

Example · yaml
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
  name: gp3
provisioner: ebs.csi.aws.com
volumeBindingMode: WaitForFirstConsumer
parameters:
  type: gp3
  encrypted: "true"
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: data
spec:
  accessModes: ["ReadWriteOnce"]
  storageClassName: gp3
  resources:
    requests:
      storage: 20Gi

When to use it

  • A platform team sets a default StorageClass so developers can create PVCs without specifying a storage backend, and all volumes use gp3 EBS automatically.
  • A stateful application team uses WaitForFirstConsumer binding mode to ensure EBS volumes are always created in the same Availability Zone as the pod.
  • A data team uses StorageClass parameters to provision high-IOPS io2 volumes for database pods while sharing a single cluster with teams using cheaper gp3.

More examples

Mark a StorageClass as default

Sets the ebs-gp3 StorageClass as the cluster default so PVCs without a storageClassName annotation are automatically fulfilled by it.

Example · bash
kubectl patch storageclass ebs-gp3 \
  -p '{"metadata": {"annotations": {"storageclass.kubernetes.io/is-default-class": "true"}}}'

StatefulSet with volumeClaimTemplates

A StatefulSet with a volumeClaimTemplate that auto-provisions a dedicated 20 GiB EBS PVC per replica using the ebs-gp3 StorageClass.

Example · yaml
apiVersion: apps/v1
kind: StatefulSet
metadata:
  name: postgres
spec:
  serviceName: postgres
  replicas: 1
  selector:
    matchLabels:
      app: postgres
  template:
    metadata:
      labels:
        app: postgres
    spec:
      containers:
      - name: postgres
        image: postgres:16
        volumeMounts:
        - name: data
          mountPath: /var/lib/postgresql/data
  volumeClaimTemplates:
  - metadata:
      name: data
    spec:
      accessModes: [ReadWriteOnce]
      storageClassName: ebs-gp3
      resources:
        requests:
          storage: 20Gi

Inspect PVC and bound PV

Shows the PVC binding status and the underlying PersistentVolume created by the CSI driver, confirming the StorageClass provisioned the volume correctly.

Example · bash
kubectl get pvc postgres-data
kubectl describe pvc postgres-data
kubectl get pv $(kubectl get pvc postgres-data -o jsonpath='{.spec.volumeName}')

Discussion

  • Be the first to comment on this lesson.