BorgBackup & Borgmatic Server Backup Setup
You manage 20–50 servers and spend hours each day manually checking backups. One day an archive turns out to be corrupted, and restoration takes a day instead of an hour. Sound familiar? BorgBackup with Borgmatic solves the problem declaratively: deduplication, encryption, and automatic verification. We implement this stack turnkey so you can sleep easy.
Why Borg saves up to 60% space
rsync copies whole files when attributes or content change. Borg uses content-defined chunking: it splits files into chunks using the CDC algorithm and stores unique chunks only once. A typical daily increment is 1–3% of the full volume. For directories with logs or databases, this is a radical space saving. Our clients save up to 60% on storage costs compared to classic solutions.
How to set up Borgmatic in 1 day
Installation and repository initialization are the first stage. Our engineer creates SSH keys with restrictions, configures borg serve, and initializes an encrypted repository.
# On the backup server (where we write)
apt-get install borgbackup
# On the client
apt-get install borgbackup borgmatic
# Create an SSH key for backup
ssh-keygen -t ed25519 -C "backup@client-server" -f /root/.ssh/borg_backup -N ""
# On the backup server, add the key to authorized_keys with restrictions
echo 'command="borg serve --restrict-to-path /mnt/backups/client1",restrict ssh-ed25519 AAAA...' \
>> /home/borg/.ssh/authorized_keys
# Initialize the repository
borg init --encryption=repokey-blake2 \
borg@backup-server:/mnt/backups/client1repokey-blake2 — the encryption key is stored in the repository (protected by passphrase). Alternative keyfile — key on the client, needs separate backup.
Borgmatic configuration
---
# /etc/borgmatic/config.yaml
repositories:
- path: borg@backup-server:/mnt/backups/client1
label: remote-backup
source_directories:
- /etc
- /home
- /var/www
- /var/lib
exclude_patterns:
- /var/lib/lxcfs
- /var/lib/docker/overlay2
- '*.pyc'
- '*/__pycache__'
- '*/node_modules'
storage:
encryption_passphrase: "your-strong-passphrase"
compression: zstd,3
archive_name_format: '{hostname}-{now:%Y-%m-%d-%H%M%S}'
retention:
keep_daily: 7
keep_weekly: 4
keep_monthly: 6
keep_yearly: 1
consistency:
checks:
- name: repository
frequency: 2 weeks
- name: archives
frequency: 1 month
- name: data
frequency: 3 months
hooks:
before_backup:
- /usr/local/bin/pre-backup.sh
after_backup:
- curl -fsS -m 10 --retry 5 https://hc-ping.com/YOUR-UUID
on_error:
- echo "Backup failed on $(hostname)" | mail -s "Borg backup error" [email protected]
consistency.checks.data — full data verification (decryption and hash check). Expensive operation, run no more than once a quarter. archives — checks archive metadata, cheaper.
The after_backup hook pings Healthchecks.io — an external backup monitoring service. If the ping doesn't arrive within the expected window, an alert is triggered. This is simpler than building custom monitoring.
Systemd timer
Schedule backup execution. Use borgmatic --init to automatically create a systemd unit or manually via a timer.
# Automatic timer
borgmatic --init
systemctl enable --now borgmatic.timer
# Or manual timer
cat > /etc/systemd/system/borgmatic.timer <<EOF
[Timer]
OnCalendar=*-*-* 01:00:00
Persistent=true
[Install]
WantedBy=timers.target
EOF
systemctl enable --now borgmatic.timer Pre-backup hook for databases
If PostgreSQL runs on the server, dump before backup:
#!/bin/bash
# /usr/local/bin/pre-backup.sh
set -euo pipefail
sudo -u postgres pg_dumpall --globals-only > /var/backups/pg_globals.sql
sudo -u postgres pg_dump mydb | gzip > /var/backups/mydb.sql.gz
Borg will pick up these files as part of the backup of /var/backups. This is a logical dump on top of physical — redundant, but guarantees recovery of a single table without restoring the whole server.
How to restore data from backup: step-by-step
# List archives
borgmatic list
# Restore entire latest archive
borgmatic extract --archive latest
# Restore a specific file to a different directory
borgmatic extract --archive latest \
--path /etc/nginx/nginx.conf \
--destination /tmp/restoreRestoration can be done on a different server: just change the destination and mount the repository via SSH. This is a key capability for Disaster Recovery.
Comparison: Borg vs rsync
| Parameter | Borg | rsync |
|---|---|---|
| Deduplication | Chunk-level (CDC) | No, copies whole files |
| Increment | 1–3% volume | 10–50% on metadata changes |
| Encryption | Built-in, AES-256 | Usually via SSH |
| Full restore speed | 1–5 min per 10 GB | 5–20 min per 10 GB |
Retention scheme example
| Copy type | Retention | Frequency | Space used (on 500 GB) |
|---|---|---|---|
| Daily | 7 days | 1/day | ~15 GB |
| Weekly | 4 weeks | 1/week | ~5 GB |
| Monthly | 6 months | 1/month | ~3 GB |
| Full (yearly) | 1 year | 1/year | ~500 GB |
Common mistakes when setting up Borg
-
Insufficient check frequency: archives can silently corrupt. Schedule
datachecks at least quarterly. - Weak encryption passphrase: use a passphrase 20+ characters long.
-
Ignoring hooks: without
after_backup, you won't know if a backup failed.
We recommend adding archive_name_format: '{hostname}-{now:%Y-%m-%d}' to the config for easy identification. And always test restore after deployment — it's the only way to be sure the backup works. If you need a solution for multiple servers, contact us — we'll prepare a unified config with centralized monitoring.
What the work includes
- Audit of current infrastructure and storage selection
- Installation and configuration of BorgBackup/Borgmatic on servers
- Creation of SSH keys and restrictions (restrict)
- Schedule setup via systemd timer or crontab
- Integration with Healthchecks.io or your monitoring
- Writing hooks for database dumps
- Retention and integrity check configuration
- Documentation and training for your team
- Restore test according to checklist
Why choose us
our team — 5+ years of DevOps experience, over 50 backup projects. We guarantee no surprises during recovery: all settings are documented, and we conduct a restore drill after deployment.
Setup time: 1–2 days for a single server, up to 3 days for a cluster. Cost is calculated individually — storage savings pay for setup in under 3 months.
Want reliable backup? Contact us — we'll assess your project. Or write to us, and we'll prepare a config in an hour.
More about Borg: BorgBackup documentation







