--- apiVersion: batch/v1 kind: CronJob metadata: name: gcloud-backup namespace: backup spec: schedule: "0 2 15 * *" # at 2:00, the 1. and 15. of every month successfulJobsHistoryLimit: 2 failedJobsHistoryLimit: 2 jobTemplate: spec: template: spec: restartPolicy: Never containers: - name: gcloud-backup image: shirakiya/gcloud-sdk:latest command: ["/bin/bash", "-c", "--"] args: - | ln -s /config/.boto /root/.boto && gsutil -m rsync -x "^(jellyfin|config|webtop|other root folder)/.*$" -U -r -e -d /data gs://kluster-backup # command: # -m multithreaded # -U skip unsupported objects # -e don't follow symlinks # -r recursively follow folder structure # -d deletes files from dst if they are not in src anymore # -n dry runs # This command runs with the knowledge the gs-bucket is set up with versioning. Rsync therefore serves as an incremental backup whose individual stages can be recovered volumeMounts: - mountPath: /data name: backup-nfs-access - mountPath: /config name: gcloud-credentials # entry .boto in the secret is mounted as /root/.boto volumes: - name: backup-nfs-access persistentVolumeClaim: claimName: backup-nfs-access - name: gcloud-credentials secret: secretName: gcloud-credentials optional: false