Skip to main content

Backups (component)

A Kustomize component that drops a k8up Schedule resource into the app's namespace, pre-pointed at the cluster-wide Restic repository on Hetzner Object Storage with the homelab's standard retention policy. Every app that has stateful PVCs pulls this in; everything else doesn't.

What it composes

The component lands a Schedule resource named <app>-backup-schedule with:

  • Backend — Restic repository on Hetzner S3, repo URL and password resolved via a SOPS-encrypted Secret in the app's namespace.
  • Frequency — every 4 hours on default; per-app patch can override.
  • Retentionkeep_hourly: 24, keep_daily: 7, keep_weekly: 4, keep_monthly: 12.
  • Annotation selector — only PVCs annotated k8up.io/backup: "true" get included. A PVC without the annotation is skipped, allowing per-app opt-in.
  • CheckSchedule — periodically runs restic check against the repository to catch corruption.

The k8up operator itself lives in platform/k8up; this component is the per-app Schedule it reconciles.

How an app uses it

# k8s/apps/talos/<app>/kustomization.yaml
components:
- ../../../components/talos/backups

And mark the PVC for inclusion:

metadata:
annotations:
k8up.io/backup: "true"

That's it — the next k8up reconciliation picks the PVC up and the schedule starts running.

Why uniform schedule, why per-app namespace

  • Uniform schedule across the cluster keeps backup load predictable. A single global k8up Schedule would work too, but spreading them per-namespace lets each app's retention be tuned independently when needed.
  • In the app's namespace means deletion of the namespace also tears down the Schedule. No orphaned backup work for retired apps.
  • PVC annotation as the opt-in is the same flag CNPG uses (k8up.io/backupcommand). Two flags wouldn't be safer; they'd just be more places to forget to set.

Operational notes

Cluster Deployment

Depends on