#!/usr/bin/env bash set -euo pipefail # ============================================================================== # MongoDB Offline Volume Backup Script (Standalone Docker) # ============================================================================== # # PURPOSE: # Creates an offline backup of the complete mongo-volume directory. # The database server is stopped during the backup to ensure consistency. # # WHEN TO USE: # - For standalone Docker deployments (not Docker Swarm) # - When you need a complete volume backup (entire MongoDB data directory) # - For disaster recovery scenarios # - When consistency is critical and downtime is acceptable # # BACKUP TYPE: # - Offline (cold) backup - DB server is stopped during backup # - Volume-level backup - entire mongo-volume directory # - Creates compressed tarball (.tar.gz) of the volume # # OUTPUT: # - Backup files stored in: ./mongo-backup/ # - Filename format: mongo-volume-backup-YYYY-MM-DD-HH-MM.tar.gz # - Log file: ./mongo-backup/db-backup-standalone.log # - Automatic rotation: keeps newest 7 backups (configurable via KEEP env var) # # USAGE: # ./db-backup--standalone.sh # KEEP=10 ./db-backup--standalone.sh # Keep 10 backups instead of 7 # # NOTE: # The MongoDB container will be stopped and restarted automatically. # Expect brief downtime during the backup process. # # ============================================================================== # Configuration SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" BACKUP_DIR="${BACKUP_DIR:-$SCRIPT_DIR/mongo-backup}" LOG_FILE="$BACKUP_DIR/db-backup-standalone.log" MONGO_SERVICE="mongo" COMPOSE_FILE="$SCRIPT_DIR/docker-compose-standalone.yaml" # Initialize log file (overwrite if exists) mkdir -p "$(dirname "$LOG_FILE")" > "$LOG_FILE" # Function to log messages log() { local timestamp=$(date '+%Y-%m-%d %H:%M:%S') echo "[$timestamp] $*" | tee -a "$LOG_FILE" } # stop mongo container while we copy its volume log "Stopping MongoDB container..." docker compose -f "$COMPOSE_FILE" stop "$MONGO_SERVICE" # timestamp for filename TIMESTAMP=$(date +"%Y-%m-%d-%H-%M") # backup directory and retention (can be overridden via env) KEEP="${KEEP:-7}" mkdir -p "$BACKUP_DIR" BACKUP_FILE="$BACKUP_DIR/mongo-volume-backup-$TIMESTAMP.tar.gz" log "Creating backup: $BACKUP_FILE" sudo tar -czvpf "$BACKUP_FILE" mongo-volume log "Backup created successfully." # rotate old backups: keep only the newest $KEEP files if [ "$KEEP" -gt 0 ]; then log "Rotating backups, keeping the newest $KEEP files." # gather files sorted newest-first mapfile -t files < <(ls -1t "$BACKUP_DIR"/mongo-volume-backup-*.tar.gz 2>/dev/null || true) if [ "${#files[@]}" -gt "$KEEP" ]; then for f in "${files[@]:$KEEP}"; do log "Removing old backup: $f" rm -f -- "$f" done fi log "Rotation completed." else log "Backup rotation disabled (KEEP=$KEEP)." fi log "Starting MongoDB container..." docker compose -f "$COMPOSE_FILE" start "$MONGO_SERVICE" log "Database backup process completed successfully."