What are stateful workloads?

By default, workloads running in Kubernetes are stateless. That means when a pod is restarted, all the data it wrote to its filesystem is lost. Ideally, most workloads should be stateless, as this allows Kubernetes to schedule and reschedule them on different nodes in your cluster without having to “move” your data between them. It also makes it easy for Kubernetes to increase the number of pods in a deployment, for example, to meet the increased demand for an application.

Unfortunately, most non-trivial applications are not stateless, and Kubernetes accommodates these use cases by providing PersistentVolumeClaims that can be attached to your workloads to persist its data.

Stateful workloads on Exoscale SKS

Exoscale offers a managed Kubernetes service called “Scalable Kubernetes Service” or SKS. For many applications it is enough to store data in a managed database such as Exoscale DBaaS or maybe even just to upload the data to Exoscale SOS. However, some workloads do indeed need to write data directly to their filesystem. Kubernetes provides a way to provision PersistentVolumes from the local disk on the nodes it runs. However, this ties a workload’s data to a single node, and it will not be accessible to the workload unless it is always scheduled on that same node. This is why Cloud Providers such as Exoscale provide network attachable storage volumes that integrate with Kubernetes through a component called the “Container Storage Interface” or CSI. The CSI is responsible for provisioning, extending, deleting and snapshotting volumes and provides this functionality through a standardized interface that Kubernetes can communicate with.

In the past, users of Exoscale SKS had to deploy and maintain their storage solutions like Longhorn to get this functionality. But with the introduction of Exoscale Block Storage, we could finally implement our very own CSI. To make it easier for our customers to set up the CSI, we integrated it into SKS as an Addon that can be enabled with one command or click from our Portal UI, our CLI or our terraform provider on both existing and new clusters

How to deploy a stateful application on SKS

Please follow this section in our documentation to enable the CSI on a new or existing cluster.

With a few simple commands, we can now deploy an Nginx server with logs persisted on an Exoscale Block Storage Volume.

First we need a namespace where our application will be located:

kubectl create namespace awesome

We just created a namespace named awesome. Now we create a PersistentVolumeClaim by pasting the following into a file named pvc.yaml

apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: my-pvc
  namespace: awesome
spec:
  accessModes:
  - ReadWriteOnce
  resources:
    requests:
    storage: 100Gi
  storageClassName: exoscale-sbs

Once we apply this manifest, a Block Storage Volume will be provisioned automatically and can later be attached to a workload.

kubectl apply -f pvc.yaml

Paste the following into a file called deployment.yaml

apiVersion: apps/v1
kind: Deployment
metadata:
  name: my-awesome-deployment
  namespace: awesome
spec:
  selector:
    matchLabels:
    app: my-awesome-deployment
  replicas: 1
  template:
    metadata:
    labels:
        app: my-awesome-deployment
    spec:
    containers:
        - name: my-awesome-nginx
        image: nginx
        volumeMounts:
        - mountPath: "/var/log/nginx"
            name: my-awesome-logs
    volumes:
        - name: my-awesome-logs
        persistentVolumeClaim:
            claimName: my-pvc

This will create a deployment that mounts the PersistentVolumeClaim to the Nginx container’s log directory.

kubectl apply -f deployment.yaml

And that’s all there is to it! We have just created a stateful workload on SKS.

To learn more about the Exoscale CSI we recommend studying the Kubernetes documentation on the topic