#!/usr/bin/env bash # # OpenClaw Backup Cron Script with Health Check Integration # 集成健康检查的备份脚本 # set -euo pipefail BACKUP_ENV_FILE_PATH="${OPENCLAW_BACKUP_ENV_FILE_PATH:-/root/.env.d/openclaw-backup.env}" BACKUP_LOG_DIR="${OPENCLAW_BACKUP_LOG_DIR:-/var/log/openclaw}" BACKUP_LOG_FILE="${BACKUP_LOG_DIR}/backup.log" HEALTH_CHECK_ENABLED="${OPENCLAW_BACKUP_HEALTH_CHECK_ENABLED:-false}" HEALTH_CHECK_BEFORE="${OPENCLAW_BACKUP_HEALTH_CHECK_BEFORE:-false}" HEALTH_CHECK_AFTER="${OPENCLAW_BACKUP_HEALTH_CHECK_AFTER:-false}" # Timestamp function timestamp() { date '+%Y-%m-%dT%H:%M:%S' } # Logging function - 只写入文件,避免Supervisor双重记录 log() { echo "[$(timestamp)] $*" >> "$BACKUP_LOG_FILE" } is_true() { local value value="$(printf '%s' "${1:-}" | tr '[:upper:]' '[:lower:]')" [[ "$value" == "1" || "$value" == "true" || "$value" == "yes" || "$value" == "on" ]] } # Load environment load_env() { if [[ -f "$BACKUP_ENV_FILE_PATH" ]]; then # shellcheck disable=SC1091 if ! source "$BACKUP_ENV_FILE_PATH"; then log "ERROR: Failed to source $BACKUP_ENV_FILE_PATH" return 1 fi log "INFO: Loaded environment from $BACKUP_ENV_FILE_PATH" else log "WARN: Environment file not found: $BACKUP_ENV_FILE_PATH" fi } # Run health check run_health_check() { if [[ "$HEALTH_CHECK_ENABLED" != "true" ]]; then log "INFO: Health check is disabled" return 0 fi log "INFO: Running pre-backup health check..." if /usr/local/bin/openclaw-backup-health.sh --check >> "$BACKUP_LOG_FILE" 2>&1; then log "INFO: Health check passed" return 0 else log "WARN: Health check failed, attempting repair..." # Try to repair if /usr/local/bin/openclaw-backup-health.sh --repair >> "$BACKUP_LOG_FILE" 2>&1; then log "INFO: Repair successful, retrying health check..." # Retry health check if /usr/local/bin/openclaw-backup-health.sh --check >> "$BACKUP_LOG_FILE" 2>&1; then log "INFO: Health check passed after repair" return 0 else log "ERROR: Health check still failing after repair" return 1 fi else log "ERROR: Repair failed" return 1 fi fi } # Run backup with retry run_backup_with_retry() { local max_retries="${OPENCLAW_BACKUP_MAX_RETRIES:-3}" local retry_count=0 local backup_success=false while [[ $retry_count -lt $max_retries ]]; do ((retry_count++)) log "INFO: Backup attempt $retry_count/$max_retries" local exit_code=0 python3 /opt/openclaw-hf/openclaw_hf/backup.py backup >> "$BACKUP_LOG_FILE" 2>&1 || exit_code=$? if [[ $exit_code -eq 0 ]]; then log "INFO: Backup completed successfully on attempt $retry_count" backup_success=true break else log "ERROR: Backup failed on attempt $retry_count (exit code: $exit_code)" if [[ $retry_count -lt $max_retries ]]; then local retry_delay=$((retry_count * 10)) log "INFO: Waiting ${retry_delay}s before retry..." sleep $retry_delay # Try repair before next attempt log "INFO: Attempting repair before retry..." /usr/local/bin/openclaw-backup-health.sh --repair >> "$BACKUP_LOG_FILE" 2>&1 || true fi fi done if [[ "$backup_success" == "true" ]]; then return 0 else log "ERROR: Backup failed after $max_retries attempts" return 1 fi } # Post-backup health check post_backup_check() { if [[ "$HEALTH_CHECK_AFTER" != "true" ]]; then return 0 fi log "INFO: Running post-backup health check..." # Check if backup file was created if [[ -f "$BACKUP_LOG_FILE" ]]; then local last_backup last_backup=$(grep -i "backup complete" "$BACKUP_LOG_FILE" | tail -1) if [[ -n "$last_backup" ]]; then log "INFO: Post-backup check: Backup log shows completion" return 0 else log "WARN: Post-backup check: No completion found in logs" return 1 fi fi return 0 } # Main backup function main() { # Ensure log directory exists mkdir -p "$BACKUP_LOG_DIR" log "========================================" log "OpenClaw Backup Starting" log "========================================" # Load environment load_env # Check if backup is enabled if ! is_true "${OPENCLAW_BACKUP_ENABLED:-false}"; then log "INFO: Backup is disabled (OPENCLAW_BACKUP_ENABLED=false), skipping" exit 0 fi # Pre-backup health check if [[ "$HEALTH_CHECK_BEFORE" == "true" ]]; then if ! run_health_check; then log "ERROR: Pre-backup health check failed, aborting backup" exit 1 fi fi # Run backup if run_backup_with_retry; then log "INFO: Backup process completed successfully" # Post-backup check post_backup_check log "========================================" log "OpenClaw Backup Finished Successfully" log "========================================" exit 0 else log "ERROR: Backup process failed" # Run emergency repair on complete failure log "INFO: Running emergency repair..." /usr/local/bin/openclaw-backup-health.sh --emergency >> "$BACKUP_LOG_FILE" 2>&1 || true log "========================================" log "OpenClaw Backup Failed" log "========================================" exit 1 fi } # Run main main "$@"