← How-Tos
raspberry-pi Aug 19, 2026 ◑ 8 views ◯ 4 min read

Backing Up Self-Hosted Services on Raspberry Pi with Restic and Borg

resticborgbackupbackupraspberry piself hosteddocker volumesincremental backupdeduplicationoff site backupbackblaze b2encryptiondisaster recovery

This site has walked through building a Raspberry Pi NAS, a Jellyfin media server, an Immich photo library, a Vaultwarden password vault, a Home Assistant hub, and a K3s cluster — and none of those guides cover what happens when the SD card or SSD dies, a bad update corrupts a database, or a container's data volume gets wiped by mistake. Imaging the whole SD card to a network share (covered elsewhere on this site) protects the OS and boot config, but it's a blunt instrument for the data actually living inside your self-hosted services — a 30GB Immich photo library or a growing Jellyfin library doesn't need a full disk image taken nightly, it needs proper incremental, deduplicated backup of just the data that changed. That's what Restic and Borg are built for, and neither gets much attention in maker circles despite being the standard tools for exactly this job in the self-hosting world.

Why Not Just rsync or a Cron Copy Job

A plain rsync or cp job to a network share works until you need history — if a database gets corrupted three days ago and nobody noticed until today, a simple mirrored copy has already mirrored the corruption. Restic and Borg both keep space-efficient snapshots: every backup run only stores the data that changed since the last one (via content-defined chunking and deduplication), but each snapshot is still individually restorable as a complete point-in-time copy. A week of daily snapshots of a 30GB photo library might only cost a few hundred MB of extra storage beyond the first full backup, while still letting you restore to any of those seven days independently.

Restic vs Borg

ResticBorgBackupWritten inGo — single static binary, trivial to install on ARMPython — needs a matching Python environment, slightly more setup on a PiRemote backendsS3-compatible (including Backblaze B2, self-hosted MinIO), SFTP, REST server, local, and more — very flexibleSFTP/SSH and local primarily, via Borg's own repo formatEncryptionAlways encrypted client-side by defaultAlways encrypted client-side by defaultDeduplicationContent-defined chunking across the whole repoContent-defined chunking across the whole repo, generally excellent ratiosBest fit for a Pi setupBacking up to cloud object storage (B2, S3) or a REST server on a second machineBacking up to another Pi, NAS, or any SSH-reachable box on the LAN

Either is a solid choice; Restic's single-binary install and native cloud backend support make it the easier starting point if the backup target is off-site cloud storage, while Borg is a very natural fit if the target is another machine on the same network reachable over SSH.

What to Actually Back Up

For a typical Docker Compose self-hosted stack, back up the bind-mounted data directories and any named volumes, not the container images themselves — images are reproducible from your docker-compose.yml and can be re-pulled, but the data inside them (Immich's photo library and Postgres database, Vaultwarden's vault, Home Assistant's config and history database) is not. For anything backed by a database — Postgres for Immich, SQLite for many lighter services — take an application-consistent dump (pg_dump, or an SQLite .backup command) before the file-level backup runs, rather than backing up live database files directly, which risks capturing a mid-write, inconsistent state.

Basic Restic Workflow on a Pi

Verify Restores, Not Just Backups

The single most common backup failure isn't a missing backup — it's a backup nobody ever tested restoring, that turns out to be incomplete or corrupted exactly when it's needed. Both tools support mounting a snapshot as a browsable filesystem (restic mount, borg mount) without doing a full restore, which makes spot-checking painless. Do a real, full test restore to a spare directory at least once after initial setup, and periodically afterward — an untested backup is a hope, not a backup.

Where This Fits with SD Card Imaging

SD card or boot-disk imaging (covered in this site's SD card backup guide) and application-level Restic/Borg backups solve different problems and both are worth having: a disk image gets you back to a bootable system fast after hardware failure, while Restic/Borg snapshots protect the actual data inside your services with history and off-site redundancy that a single disk image copy doesn't provide. A reasonable setup runs both — a weekly or monthly full disk image for fast bare-metal recovery, and nightly Restic or Borg snapshots of the data directories that actually change day to day.

Off-Site Matters

A backup that lives on a second drive plugged into the same Pi, in the same room, protects against drive failure and not much else — fire, theft, and power surges take out both copies together. Point at least one backup target somewhere physically separate: a cheap Backblaze B2 bucket (Restic's per-GB cost there is low enough that a modest self-hosted stack costs pennies a month to protect), a relative's house running a second Pi or NAS reachable over Tailscale or WireGuard, or any other genuinely off-site location.