SSD Nodes Learn 8GB RAM — $66/yr
Guides Matt ConnorBy Matt Connor

Restic vs BorgBackup: which one to run

Restic reaches S3 and object storage on its own. Borg wants its binary on the far end and pays that back with speed over SSH. How to pick, with commands.

Restic vs BorgBackup, in one paragraph

Restic and BorgBackup both do the same core job: deduplicated, encrypted, incremental backups of a Linux server. The difference that decides the choice is where the backup lands. Restic speaks S3 and other object storage APIs natively, so a bucket is a first-class target with nothing installed at the far end. Borg needs the borg program installed on the machine holding the repository, because a Borg repository is served by a process, not by a filesystem or an API. If your target is object storage, that is already the answer. If your target is a second Linux box you control, Borg is in play and often faster.

Everything else is a smaller difference. Both split files with content defined chunking, so a 40 GB directory that changed by 200 MB uploads roughly 200 MB. Both encrypt on the client. Both mount a snapshot with FUSE (filesystem in userspace) so you can copy one file out. As of July 2026 restic is at 0.19.1 and Borg's stable series is 1.4, at 1.4.5. Borg 2.0 has been in beta for years and is still marked as testing only, so 1.4 is what you should deploy today.

The repository model is the real difference

A restic repository is a directory of files: config, keys/, snapshots/, index/, and data/ full of pack files. Nothing else is needed to read it. That is why restic can drive so many backends. Any store that can put, get, list and delete blobs can hold a restic repository, which is how one binary supports local paths, SFTP, its own REST server, S3, Backblaze B2, Azure, Google Cloud Storage, and anything rclone can reach.

A Borg repository is also files on disk, but Borg never talks to it over a dumb transport. For a remote repository, Borg starts borg serve on the far side over SSH and speaks its own protocol to that process. The server side does real work: it holds the repository, applies the transaction, and answers index questions. This is why Borg has no S3 backend and why the project has not added one. There is no process to run inside a bucket.

That single design fact produces most of the practical differences below.

# restic: the repository is a URL, and the backend is part of it
restic -r /srv/restic-repo init
restic -r sftp:backup@198.51.100.20:/srv/restic-repo init
restic -r s3:s3.us-east-1.amazonaws.com/my-backup-bucket init
# borg: a local path, or user@host:path, with borg installed on that host
borg init --encryption=repokey-blake2 /srv/borg/vps1
borg init --encryption=repokey-blake2 backup@198.51.100.20:/srv/borg/vps1

Encryption: one of them can be turned off

Restic is always encrypted. There is no unencrypted mode. restic init asks for a password, derives a key from it with scrypt, and every pack file written after that is encrypted and authenticated. Lose the password and the data is gone, because no recovery path exists by design.

Borg makes encryption a choice at repository creation, and the choice is permanent. borg init --encryption=repokey keeps the encrypted key inside the repository, so the passphrase alone can restore. --encryption=keyfile keeps the key on the client in ~/.config/borg/keys/, so someone who steals the whole repository still has nothing, and so you must back that key file up separately or your archives are unreadable. Each mode has a -blake2 variant that authenticates with BLAKE2b instead of HMAC-SHA256, which is faster on hardware without SHA acceleration. --encryption=none also exists, and it is a real choice when the repository sits on an encrypted disk you own.

The practical rule: repokey-blake2 for a normal server backup, keyfile when the repository lives somewhere you do not fully trust, and never none on a rented machine.

Compression, and why restic got it late

Borg has compressed since the beginning. The default is lz4, chosen because it is fast enough to leave on for everything. zstd accepts levels 1 to 22 and defaults to 3, zlib and lzma are there for cases where you care more about bytes than minutes, and auto runs a heuristic per chunk so already compressed data is not squeezed twice.

borg create --compression zstd,3 --stats --progress \
  /srv/borg/vps1::'{hostname}-{now}' /etc /home /srv

Restic had no compression at all until repository format 2, which needs restic 0.14.0 or newer. Format 2 is the default for a new repository now, and compression is set with --compression at values auto, off or max. An old format 1 repository stays uncompressed until you migrate it. So if your restic repository predates 0.14 and you never migrated, you are still paying full size for text, logs and database dumps.

Remote targets: S3 versus SSH

This is where the choice usually gets made.

Restic reaching S3 needs credentials in the environment and nothing else running anywhere. The same pattern works against a bucket you host yourself, which is a common pairing: run MinIO for an S3 API on your own VPS and point restic at it.

export AWS_ACCESS_KEY_ID=...
export AWS_SECRET_ACCESS_KEY=...
export RESTIC_REPOSITORY=s3:https://objects.example.com/backups
export RESTIC_PASSWORD_FILE=/root/.restic-pass
restic init
restic backup /etc /home /srv --exclude-caches

Borg reaching a remote repository needs SSH plus a Borg install on the far side, and it wants the version there to be compatible with the client. That is friction if the far side is not yours. It is nothing if the far side is a second server you already administer, and it buys you the strongest control against ransomware that either tool offers: an append only SSH key. Force the key to run borg serve and the client can add archives but cannot delete them, so a compromised machine cannot wipe its own history.

command="borg serve --append-only --restrict-to-path /srv/borg/vps1",restrict ssh-ed25519 AAAA...

Restic has an equivalent only when you run its own REST server, which supports an append only mode. Against plain S3 you get the same effect from bucket policy or object lock, which is the provider's job and not restic's. Lock the transport down as well, because the SSH side of this deserves the same care as any other login: apply key only SSH with a restricted authorized_keys entry to the backup account.

Speed: what each design implies

Neither project publishes a benchmark you should trust for your own data, so reason from the mechanism instead.

Borg over SSH is fast on a link with latency because the server side is intelligent. The client asks a question, the remote borg serve process answers it from the repository index, and the transaction commits in one place. Chunk lookups do not turn into network round trips for every small file.

Restic on object storage has no server side, so it must build its picture from index files and pack files it fetches over HTTP. To keep the request count sane it packs many small chunks into larger pack files before uploading, and it keeps a local cache in ~/.cache/restic so the next run does not refetch the whole index. Delete that cache and the next backup is slow while it rebuilds. On a high latency link with millions of small files, this is the case where restic feels slower than Borg on the same data.

On a local disk or a fast LAN the gap mostly closes, and both tools end up limited by how fast they can read and hash the source.

Locking, and backing up several machines

Borg 1.4 takes an exclusive lock on the repository for the whole operation. Two clients writing to one repository at the same time do not work: the second one waits, then fails with a lock timeout. The supported pattern is one repository per client. That also means deduplication only happens inside one machine's repository, so ten near identical servers store ten copies of the same base system.

Restic allows several clients to back up into one repository at the same time, because a backup takes a shared lock and only maintenance work such as prune takes an exclusive one. Ten similar servers pointed at one restic repository deduplicate against each other, and the second server through often stores very little. The cost is blast radius: one password and one repository holding everything, so losing the password loses all ten.

Retention: forget plus prune, versus prune plus compact

Both tools separate "decide what to keep" from "reclaim the space", and both make you run the second step.

restic forget --keep-daily 7 --keep-weekly 5 --keep-monthly 12 --prune
restic check
borg prune --list --glob-archives '{hostname}-*' \
  --keep-daily=7 --keep-weekly=4 --keep-monthly=6 /srv/borg/vps1
borg compact /srv/borg/vps1

The trap is the same in both tools and it is worth stating plainly. In Borg, borg prune removes archives but does not free disk space by itself. Space comes back when borg compact runs, so a cron job that prunes and never compacts leaves a repository that grows forever while the archive list stays short. In restic, forget without --prune only drops snapshot references, and the data stays until a prune runs.

Run restic check after pruning. It verifies the repository structures and tells you if something is damaged, which is far better than learning it during a restore.

Restoring, which is the only test that counts

Both tools mount a snapshot so you can browse it. That is the fastest way to pull one file back.

restic snapshots
restic restore latest --target /tmp/restore --include /etc/nginx
restic mount /mnt/restore
borg list /srv/borg/vps1
borg extract --list /srv/borg/vps1::vps1-2026-07-30T02:00:00 etc/nginx
borg mount /srv/borg/vps1::vps1-2026-07-30T02:00:00 /mnt/restore

Note the path form in borg extract. Paths inside an archive are stored without the leading slash, so etc/nginx is right and /etc/nginx matches nothing and extracts nothing, with no error to tell you why. Extraction also writes into the current working directory, so change into a scratch directory first or you will overwrite live files with old ones.

Whichever tool you pick, the schedule is only half the job. Run a restore into a scratch directory on a timer you actually watch, the same way the full walkthrough in the restic backup guide for a VPS does it with a systemd timer.

Which one wins for which job

Pick restic when the target is object storage, when you want one binary and no software on the far end, when several machines should deduplicate against each other, or when the person restoring may not be you. It is a single static binary with a URL for a repository, and that is hard to beat operationally.

Pick Borg when the target is a Linux box you control, when the link has latency and the dataset is millions of small files, when you want the append only SSH key as a control against ransomware, or when you want compression tuned per job. It is the older tool, its stable series moves slowly, and in backup software that is a feature.

Both are correct answers. The wrong answer is the one you never test. If you already take application level dumps, keep them: the pattern in the Nextcloud on Docker setup with database dumps applies to either tool, because a live database file copied at a random moment is not a backup of a database.

FAQ

Is restic or BorgBackup faster?

On a local disk or a fast LAN they are close, and both end up limited by read and hash speed on the source. Borg tends to win over a high latency SSH link with very many small files, because a borg serve process on the far side answers index questions without a network round trip per chunk. Restic tends to win when the target is object storage, where Borg cannot go at all.

Can BorgBackup back up to S3 or Backblaze B2?

Not directly. A Borg repository is served by the borg serve process over SSH, and no such process runs inside a bucket. People work around it by mounting object storage as a filesystem with rclone, which the Borg project does not recommend, because a mount that drops halfway through a transaction can corrupt the repository. If you need object storage, use restic.

Can I run both tools against the same data?

Yes, and some people do: Borg to a second server for a fast local restore, restic to object storage for the offsite copy. They share nothing, so you pay the read and hash cost twice, and you have two passwords to store safely. Only do this if you have tested both restores.

What happens if I lose the repository password?

The data is unrecoverable in both tools. Restic derives its key from the password with scrypt and there is no bypass. Borg in repokey mode stores the encrypted key inside the repository, so the passphrase alone restores, and in keyfile mode you also need the key file from ~/.config/borg/keys/. Keep the password in a password manager that does not live on the server being backed up, and export the Borg key with borg key export if you use keyfile.

Should I wait for Borg 2.0?

No. As of July 2026 Borg 2.0 is still beta, at 2.0.0b22, and the project labels it as testing only. The stable series is 1.4, currently 1.4.5. Start on 1.4 now. Borg 2 changes the repository format and ships a documented upgrade path, so beginning today does not strand you.