Skip to content

Instantly share code, notes, and snippets.

@danielchc
Last active November 21, 2023 20:04
Show Gist options
  • Save danielchc/d316bec6ef9602e37715acef2b01d922 to your computer and use it in GitHub Desktop.
Save danielchc/d316bec6ef9602e37715acef2b01d922 to your computer and use it in GitHub Desktop.
Backup of the vCenter Server Appliance
#!/bin/bash
#######################################################################################
#
# vCenter Backup - vcsa_backup.sh
# Create a Backup of the vCenter Server Appliance
# 1.0 - [21/11/2023] danielchc
#
#######################################################################################
function echo_log () {
echo -e "[$(date +%Y-%m-%d-%H-%M-%S)] $1"
}
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
ENV_FILE="$SCRIPT_DIR/$1"
if [ ! -f $ENV_FILE ];then
echo_log "The backup job failed. File $ENV_FILE does not exists."
exit 1
fi
#Load variables
source $ENV_FILE
TIME=$(date +%Y-%m-%d-%H-%M-%S)
VC_HOSTNAME=$(echo $VC_ADDRESS|cut -d'.' -f1)
# Backup folder
BACKUP_DIR="$BACKUP_FOLDER/$VC_HOSTNAME/"
# Log folder
LOG_DIR="$SCRIPT_DIR/logs/$VC_HOSTNAME/"
BACKUP_LOGFILE="$LOG_DIR/${TIME}.log"
# Create backup folder if not exists
[[ ! -d $LOG_DIR ]] && mkdir -p $LOG_DIR
# Log in vCSA
cookies=$(curl --silent --output /dev/null -u "$VC_USER:$VC_PASSWORD" -X POST -k -c - "https://$VC_ADDRESS/rest/com/vmware/cis/session")
# Set payload
task=$(cat << EOF
{ "piece":
{
"location_type":"$PROTOCOL",
"comment":"Automatic backup $TIME",
"parts":["seat"],
"location":"$SCP_ADDRESS/$BACKUP_DIR/$TIME",
"location_user":"$SCP_USER",
"location_password":"$SCP_PASSWORD"
}
}
EOF
)
# Get job ID
job=$(curl -s -k --cookie <(echo "$cookies") \
-H 'Accept:application/json' \
-H 'Content-Type:application/json' \
-X POST \
--data @<(echo "$task") \
"https://$VC_ADDRESS/rest/appliance/recovery/backup/job" \
2>>$BACKUP_LOGFILE)
ID=$(echo "$job" | awk '{if (match($0,/"id":"\w+-\w+-\w+"/)) print substr($0, RSTART+6, RLENGTH-7);}')
echo_log "$job" >> $BACKUP_LOGFILE
if [ "$ID" == "" ]; then
echo_log "Failed to start backup job. Check log for more details." | tee -a $BACKUP_LOGFILE
exit 1
fi
echo_log "Backup started with job id: $ID" | tee -a $BACKUP_LOGFILE
# Wait for the backup to finish
STATUS="INPROGRESS"
ERROR_COUNT=0
until [[ "$STATUS" == "SUCCEEDED" || "$STATUS" == "FAILED" || "$ERROR_COUNT" -gt "$ERROR_TOLERANCE" ]]
do
sleep 10s
response=$(curl --silent -k --cookie <(echo "$cookies") \
-H 'Accept:application/json' \
--globoff \
"https://$VC_ADDRESS/rest/appliance/recovery/backup/job/$ID" \
)
STATUS=$(echo $response | awk '{if (match($0,/"state":"\w+"/)) print substr($0, RSTART+9, RLENGTH-10);}')
PROGRESS=$(echo $response | awk '{if (match($0,/"progress":[0-9]+/)) print substr($0, RSTART+11, RLENGTH-11);}')
echo_log "$response" >> $BACKUP_LOGFILE
echo_log "Backup job state: [${PROGRESS}%] $STATUS"
if [ "$STATUS" == "" ]; then
ERROR_COUNT=$((ERROR_COUNT+1))
echo_log "WARNING: Last request response was empty [$ERROR_COUNT/$ERROR_TOLERANCE]" | tee -a $BACKUP_LOGFILE
fi
done
last_jobs=$(find /$BACKUP_DIR/* -maxdepth 0 -type d -ctime +$DAYS_TO_KEEP -printf "%f\n" | tr "\n" " ")
if [ "$STATUS" != "SUCCEEDED" ]; then
echo_log "The backup job failed. Last status was $STATUS. Check log for more details." | tee -a $BACKUP_LOGFILE
exit 1
fi
# Delete previous jobs
echo_log "The backup task finished successfully." | tee -a $BACKUP_LOGFILE
echo_log "Deleting last jobs: $last_jobs" | tee -a $BACKUP_LOGFILE
find /$BACKUP_DIR/* -maxdepth 1 -type d -ctime +$DAYS_TO_KEEP -exec rm -rf {} +
exit 0
# If you use vCSA 6.5 change PROTOCOL to "SCP"
VC_ADDRESS="vcsaFQDN.vsphere.local"
VC_USER="administrator@vsphere.local"
VC_PASSWORD=""
SCP_ADDRESS=""
PROTOCOL="SFTP"
BACKUP_FOLDER="/mnt/backup"
SCP_USER=""
SCP_PASSWORD=""
DAYS_TO_KEEP=7
ERROR_TOLERANCE=10
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment