Pattern for Dynamic Backup/Restore of Kubernetes Application Data

The Context

With container technologies likes Docker and Kubernetes, Pod and Container are ephemeral. All data are lost after restart. The way to maintain application data after restart is to attach a volume to the pod.
This doesn't address 1 thing however: the volume need to reside on a storage backend and the volume will inherit the constraint of the storage backend.
Some of those constraints are:

A Possible Approach

The approach described here is to setuup a dynamic backup and restore at directly in the lifecycle of the Pod. The technology supporting this workflow is Restic.

container-backup

Here is how the workflow works:

Use Cases and Limitation

This patten can be useful for some cases:

There are some contraints and limitations that have to be taken into accounts for these kind of workflows. If the local application data is completely ephemeral, or in case of loss of the local data infrastructure, the data loss will depend on the backup frequency. This kind of use can may not be fully implemented depending on the update frequency of the data and on the criticity.

Implementation Example

The following tool is an example of implementation of this workflow: https://github.com/devopsplaybook-io/container-utils/

An exemple of Kubernetes definition can be:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: my-application
  labels:
    app: my-application
spec:
  selector:
    matchLabels:
      app: my-application
  template:
    metadata:
      labels:
        app: my-application
    spec:
      containers:
        - image: my-application
          name: my-application
          volumeMounts:
            - mountPath: /data
              name: pod-volume
        - name: backup
          image: restic/restic:latest
          command: ["sh", "-c"]
          args:
            - wget -O /tmp/container-backup.sh https://raw.githubusercontent.com/devopsplaybook-io/container-utils/init/container-backup.sh && chmod +x /tmp/container-backup.sh && /tmp/container-backup.sh
          volumeMounts:
            - mountPath: /data
              name: pod-volume
          env:
            - name: BACKUP_FOLDER
              value: "/data"
            - name: BACKUP_RESTIC_REPO
              value: "... ..."
            - name: RESTIC_PASSWORD
              value: "... ..."
            - name: BACKUP_DO_PROCESS
              value: "Y"
            - name: BACKUP_DO_START_DELAY
              value: "10800"
            - name: BACKUP_DO_LOOP_FREQUENCY
              value: "10800"
      initContainers:
        - name: init
          image: restic/restic:latest
          command: ["sh", "-c"]
          args:
            - "wget -O /tmp/container-backup.sh https://raw.githubusercontent.com/devopsplaybook-io/container-utils/main/container-backup.sh && chmod +x /tmp/container-backup.sh && /tmp/container-backup.sh"
          volumeMounts:
            - mountPath: /data
              name: pod-volume
          env:
            - name: BACKUP_FOLDER
              value: "/data"
            - name: BACKUP_RESTIC_REPO
              value: "... ..."
            - name: RESTIC_PASSWORD
              value: "... ..."
            - name: BACKUP_DO_RESTORE
              value: "Y"
      volumes:
        - name: pod-volume
          emptyDir: {}