Skip to content

itefixnet/docker-volume-backup-borg

Folders and files

NameName
Last commit message
Last commit date

Latest commit

Β 

History

17 Commits
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 

Repository files navigation

Docker Volume Backup with Borg

A Docker container setup for backing up Docker volumes from specific containers using BorgBackup.

Developed for OpsBay - Personal Ops Stack

Features

  • πŸ”’ Encrypted backups using Borg's repokey-blake2 encryption
  • 🎯 Target specific containers by name
  • πŸ“¦ Automatically discovers and backs up all volumes mounted on target containers
  • πŸ—œοΈ LZ4 compression for fast backups
  • πŸ”„ Automatic pruning with configurable retention policy
  • 🐳 Minimal Alpine-based image

Prerequisites

  • Docker installed
  • Access to /var/run/docker.sock (to inspect containers)
  • Access to /var/lib/docker/volumes (to read volume data)

Docker Hub Image

A ready-to-use Docker image is available at Docker Hub:

docker pull itefixnet/docker-volume-backup-borg:latest

Quick Start

  1. Clone or create the project directory

  2. Create environment file

    cp .env.example .env
  3. Configure environment variables in .env:

    BORG_PASSPHRASE=your-secure-passphrase-here
    BORG_REPO=ssh://user@backup-server.example.com/path/to/borg-repo
    BACKUP_CONTAINERS=container1,container2,container3
    STOP_CONTAINERS=postgres,mysql
    TZ=UTC
  4. Build the container

    docker build -t docker-volume-backup-borg .
  5. Setup SSH keys for remote backup (if using SSH repository)

    # Generate SSH key if you don't have one
    ssh-keygen -t ed25519 -f ~/.ssh/borg_backup_key
    
    # Copy public key to backup server
    ssh-copy-id -i ~/.ssh/borg_backup_key.pub user@backup-server.example.com
  6. Run a backup

    Using default SSH keys from ~/.ssh:

    docker run --rm \
      --env-file .env \
      -v /var/run/docker.sock:/var/run/docker.sock \
      -v /var/lib/docker/volumes:/var/lib/docker/volumes:ro \
      -v ~/.ssh:/root/.ssh:ro \
      docker-volume-backup-borg

    Or with a specific SSH key:

    docker run --rm \
      --env-file .env \
      -e BORG_RSH="ssh -i /root/.ssh/borg_backup_key" \
      -v /var/run/docker.sock:/var/run/docker.sock \
      -v /var/lib/docker/volumes:/var/lib/docker/volumes:ro \
      -v ~/.ssh/borg_backup_key:/root/.ssh/borg_backup_key:ro \
      docker-volume-backup-borg

    Note: The Docker socket is mounted read-write (not :ro) to allow stopping/starting containers when STOP_CONTAINERS is set.

Configuration

Environment Variables

Variable Required Default Description
BORG_PASSPHRASE Yes - Passphrase for encrypting the Borg repository
BORG_REPO Yes - Borg repository location (SSH URL or local path)
BORG_RSH No ssh SSH command to use (set to ssh -i /root/.ssh/keyname for specific key)
BACKUP_CONTAINERS Yes - Comma-separated list of container names to backup
STOP_CONTAINERS No - Comma-separated list of containers to stop before backup (leave empty for none)
KEEP_DAILY No 7 Number of daily backups to keep
KEEP_WEEKLY No 4 Number of weekly backups to keep
KEEP_MONTHLY No 6 Number of monthly backups to keep
TZ No UTC Timezone for backup timestamps

Volume Mounts

The following volumes are mounted in the container:

  • /var/run/docker.sock - Docker socket to inspect and optionally stop/start containers
  • /var/lib/docker/volumes - Docker volumes directory (read-only) to access volume data
  • ~/.ssh - SSH keys (read-only) for authentication to remote Borg repository

Usage

Manual Backup

Run a one-time backup:

docker run --rm \
  --env-file .env \
  -v /var/run/docker.sock:/var/run/docker.sock \
  -v /var/lib/docker/volumes:/var/lib/docker/volumes:ro \
  -v ~/.ssh:/root/.ssh:ro \
  docker-volume-backup-borg backup

Note: backup is the default command and can be omitted.

Consistent Backups (Stopping Specific Containers)

For applications where consistency is critical (databases, etc.), specify which containers to stop during backup:

docker run --rm \
  -e STOP_CONTAINERS=postgres,mysql \
  --env-file .env \
  -v /var/run/docker.sock:/var/run/docker.sock \
  -v /var/lib/docker/volumes:/var/lib/docker/volumes:ro \
  -v ~/.ssh:/root/.ssh:ro \
  docker-volume-backup-borg

Each specified container will be stopped immediately before backing up its volumes, then restarted right after. This minimizes downtime - containers are only down for their own backup duration, not the entire backup run. If an error occurs, containers are automatically restarted via cleanup trap. Other containers in BACKUP_CONTAINERS will continue running throughout.

Scheduled Backups with Cron

Add a cron job on your host system:

# Edit crontab
crontab -e

# Add entry (daily backup at 2 AM)
0 2 * * * cd /path/to/docker-volume-backup-borg && docker run --rm --env-file .env -v /var/run/docker.sock:/var/run/docker.sock -v /var/lib/docker/volumes:/var/lib/docker/volumes:ro -v ~/.ssh:/root/.ssh:ro docker-volume-backup-borg >> backup.log 2>&1

List Backups

List all archives in the repository:

docker run --rm \
  --env-file .env \
  -v ~/.ssh:/root/.ssh:ro \
  docker-volume-backup-borg list

List contents of a specific archive:

docker run --rm \
  --env-file .env \
  -v ~/.ssh:/root/.ssh:ro \
  docker-volume-backup-borg list ARCHIVE_NAME

Repository Info

Show repository statistics:

docker run --rm \
  --env-file .env \
  -v ~/.ssh:/root/.ssh:ro \
  docker-volume-backup-borg info

Show specific archive info:

docker run --rm \
  --env-file .env \
  -v ~/.ssh:/root/.ssh:ro \
  docker-volume-backup-borg info ARCHIVE_NAME

Restore a Backup

  1. List available backups:

    docker run --rm \
      --env-file .env \
      -v ~/.ssh:/root/.ssh:ro \
      docker-volume-backup-borg list
  2. Extract a backup to current directory:

    docker run --rm \
      --env-file .env \
      -v ~/.ssh:/root/.ssh:ro \
      -v $(pwd):/restore \
      -w /restore \
      docker-volume-backup-borg \
      extract ARCHIVE_NAME
  3. Or mount and explore:

    docker run --rm -it \
      --env-file .env \
      --cap-add SYS_ADMIN \
      --device /dev/fuse \
      -v ~/.ssh:/root/.ssh:ro \
      docker-volume-backup-borg \
      borg mount $BORG_REPO /mnt

How It Works

  1. The backup script connects to the Docker daemon via the Docker socket
  2. For each specified container:
    • If listed in STOP_CONTAINERS, stops the container for consistency
    • Discovers all mounted volumes
    • Backs up each volume using Borg with compression and encryption
    • Prunes old backups for each volume independently based on retention policy
    • Restarts the container immediately (minimizing downtime)
  3. Compacts the repository to reclaim space
  4. Any containers not restarted due to errors are automatically restarted via cleanup trap

Backup Location

Backups are stored on the remote server specified in BORG_REPO. The Borg repository will be initialized automatically on the first run.

Important:

  • Keep your BORG_PASSPHRASE safe! Without it, you cannot restore your backups.
  • Ensure your SSH keys have proper permissions (chmod 600 ~/.ssh/borg_backup_key)
  • For local backups, use BORG_REPO=/backups/borg-repo and mount -v ./borg-repo:/backups/borg-repo

Security Considerations

  • The container needs access to Docker socket and volumes directory (privileged access)
  • Run on trusted systems only
  • Protect the .env file (contains passphrase)
  • Consider storing the Borg repository on a separate disk or remote location
  • Regularly test backup restoration

Troubleshooting

"Permission denied" errors

Ensure the container has access to /var/lib/docker/volumes. You may need to run with appropriate privileges or adjust volume mount paths based on your Docker installation.

Borg repository location

On some systems, Docker volumes may be stored in a different location. Update the volume mount path in your docker run command accordingly (e.g., -v /path/to/volumes:/var/lib/docker/volumes:ro).

Container not found

Verify container names with:

docker ps --format "{{.Names}}"

Advanced Configuration

Custom Backup Script

You can modify backup.sh to:

  • Stop containers before backup (for consistency)
  • Send notifications on backup completion
  • Upload backups to remote storage
  • Add pre/post-backup hooks

Local Borg Repository

To use a local repository instead of remote:

  1. Update BORG_REPO in .env:

    BORG_REPO=/backups/borg-repo
  2. Mount local directory instead of SSH keys:

    docker run --rm \
      --env-file .env \
      -v /var/run/docker.sock:/var/run/docker.sock \
      -v /var/lib/docker/volumes:/var/lib/docker/volumes:ro \
      -v ./borg-repo:/backups/borg-repo \
      docker-volume-backup-borg

License

BSD 2-Clause License - See LICENSE file for details.

About

Developed for OpsBay - Personal Ops Stack.

About

A Docker container setup for backing up Docker volumes from specific containers using BorgBackup.

Resources

License

Stars

Watchers

Forks

Releases

No releases published