4.0 KiB

🐍 Python Virtual Environment Backup Script

This Bash script automates the process of backing up Python virtual environments. It performs the following steps:

  1. Locates virtual environments in a specified root directory
  2. Archives them into a compressed .tar.gz file
  3. Transfers the backup to a remote server using rsync
  4. Deletes local backups older than a specified retention period

📦 Features

  • Detects virtual environments by checking for bin/activate
  • Compresses selected environments into a tarball
  • Transfers the backup to a remote server via SSH
  • Deletes backups older than a retention threshold
  • Uses strict error handling to avoid silent failures

⚙️ Configuration

Variable Description
VENV_ROOT Directory where virtual environments are stored
BACKUP_DIR Local directory where the backup tarballs are saved
RETENTION_DAYS Number of days to retain local backups
REMOTE_USER SSH user for the remote backup server
REMOTE_HOST Hostname or IP address of the remote server
REMOTE_PATH Remote directory where backups will be copied via rsync

📝 Script Walkthrough

1. Setup

#!/usr/bin/env bash
set -euo pipefail
  • Enables strict error handling to prevent unnoticed failures.

2. Define Variables

VENV_ROOT="/home/doc"
BACKUP_DIR="$VENV_ROOT/backups"
RETENTION_DAYS=7

REMOTE_USER="root"
REMOTE_HOST="thevault.bounceme.net"
REMOTE_PATH="/mnt/backup3/pythonvenvs"

3. Generate Timestamped Backup Filename

DATE=$(date +'%F_%H-%M-%S')
BACKUP_FILE="$BACKUP_DIR/venvs_backup_$DATE.tar.gz"

4. Ensure Backup Directory Exists

mkdir -p "$BACKUP_DIR"

5. Locate Virtual Environments

mapfile -t VENV_DIRS < <(
  find "$VENV_ROOT" -maxdepth 1 -type d \
    -exec test -f "{}/bin/activate" \; -print
)

If no environments are found, the script exits:

if [ ${#VENV_DIRS[@]} -eq 0 ]; then
  echo "❌ No virtual environments found under $VENV_ROOT"
  exit 1
fi

6. Extract Environment Names and Archive

VENV_NAMES=()
for path in "${VENV_DIRS[@]}"; do
  VENV_NAMES+=( "$(basename "$path")" )
done

echo "🔄 Backing up virtual environments: ${VENV_NAMES[*]}"
tar czf "$BACKUP_FILE" -C "$VENV_ROOT" "${VENV_NAMES[@]}"
echo "✅ Local backup saved to $BACKUP_FILE"

7. Sync Backup to Remote Server

echo "📡 Sending backup to ${REMOTE_USER}@${REMOTE_HOST}:${REMOTE_PATH}/"
rsync -az --progress "$BACKUP_FILE" \
      "${REMOTE_USER}@${REMOTE_HOST}:${REMOTE_PATH}/"

Check if sync was successful:

if [ $? -ne 0 ]; then
  echo "❌ Remote sync failed!"
  exit 1
else
  echo "✅ Remote sync succeeded."
fi

8. Cleanup Old Backups

echo "🗑️ Removing local backups older than $RETENTION_DAYS days..."
find "$BACKUP_DIR" -type f -name "venvs_backup_*.tar.gz" \
     -mtime +$RETENTION_DAYS -delete
echo "🎉 Backup and cleanup complete."

🧪 Example Output

🔄 Backing up virtual environments: venv1 venv2
✅ Local backup saved to /home/doc/backups/venvs_backup_2025-05-01_02-00-00.tar.gz
📡 Sending backup to root@thevault.bounceme.net:/mnt/backup3/pythonvenvs/
✅ Remote sync succeeded.
🗑️ Removing local backups older than 7 days...
🎉 Backup and cleanup complete.

🛡️ Notes

  • Ensure SSH access is set up for passwordless login to the remote host.
  • Confirm that rsync is installed on both the local and remote systems.
  • Consider running this script via cron or systemd for automation.

🖋️ Author

Maintained by Doc. Custom backup tooling for Genesis Hosting infrastructure.