Benutzer-Werkzeuge

Webseiten-Werkzeuge


 [[anwenderwiki:virtualisierung:kvm:kvm_clone]] 

LV auf zweiten Server klonen

Falls man in der komfortablen Lage ist, zwei Virtualisierungsmaschinen parallel laufen zu haben, kann man recht komfortabel und im laufenden Betrieb ein Snapshot des LVs von Server 1 auf Server 2 übertragen.

Das Skript geht davon aus, dass auf beiden Servern identische VMs mit LVM eingerichtet sind. Außerdem kann man passwortlos per SSH auf die Backup-Maschine zugreifen.

Falls eine Email-Adresse angegeben wird, muss der Email-Versand eingerichtet sein.

Im wesentlichen wird sichergestellt, dass der aktuelle Server der ist, auf dem die VM läuft und diese auf dem Backup-Server nicht läuft. Die Größe wird verglichen und ggf. angepasst.

Es gibt zweifellos noch einige Verbesserungsmöglichkeiten - aber bei uns läuft das erstmal so und macht nachts ein schnelles (ca. 8 minuten) Backup unseres Webservers (~80GB).

Vielleicht ist es (ganz oder in Teilen) hilfreich für irgendjemanden.

#!/bin/bash
# this script assumes, that the target server is passwordless ssh-able
# and that the user has sudo-rights on the local and the target-system
# for mailing functionality install and setup mailutils / ssmtp

# run on one of the kvm hosts
user="serveradmin"
source="<IP ADDRESS OF RUNNING SERVER>"
target="<IP ADDRESS OF BACKUP-MACHINE>"
mailto=""
snapshot="backup"

log="vmbackup.log"

echo "Running vmbackup on $(hostname) at $(date) - syncing $source to $target" | tee "$log"

if [ "$#" -eq 0 ]; then
  echo "X no vm name passed - ABORT" | tee -a "$log"
  exit 1
fi

vm=$1

# check for needed packages/install - local and remote
echo "* apt install needed packages"
sudo apt install -y pigz pv &> /dev/null
ssh $user@$target sudo apt install -y pigz pv &> /dev/null

# check if vm is running locally (it has to)
if [ "$(virsh list | grep $vm | grep -c 'running')" == "1" ]; then
  echo "* vm $vm running on source - OK" | tee -a "$log"
else
  echo "X vm $vm not running on source - ABORT" | tee -a "$log"
  exit 1
fi

# check if vm is running on remote machine (its not allowed to)
if [ "$(virsh -c qemu+ssh://$user@$target/system list | grep $vm | grep -c 'running')" == "1" ]; then
  echo "X vm $vm is running on backup target - ABORT" | tee -a "$log"
  exit 1
else
  echo "* vm $vm not running on remote machine - OK" | tee -a "$log"
fi

# get name and size - local and remote - of lv from vm name (hopefully)
locallvname=$(virsh dumpxml $vm | grep -A 3 '<disk ' | grep source | cut -d "'" -f 2)
locallvsize=$(sudo lvs $locallvname -o LV_SIZE --noheadings --units b --nosuffix | tr -d " " )
remotelvname=$(virsh -c qemu+ssh://$user@$target/system dumpxml $vm | grep -A 3 '<disk ' | grep source | cut -d "'" -f 2)
remotelvsize=$(ssh $user@$target sudo lvs $remotelvname -o LV_SIZE --noheadings --units B --nosuffix | tr -d " " )

# compare sizes
if [ "$locallvsize" != "$remotelvsize" ]; then
  echo "* local size of lv ($locallvsize) differs from remote ($remotelvsize) - resizing remote lv" | tee -a "$log"
  ssh $user@$target sudo lvextend -L ${locallvsize}B $remotelvname
  remotelvsize=$(ssh $user@$target sudo lvs $remotelvname -o LV_SIZE --noheadings --units B --nosuffix | tr -d " " )
  if [ "$locallvsize" != "$remotelvsize" ]; then
    echo "X size still does not matter - GIVING UP" | tee -a "$log"
    break 1
  fi
else
  echo "* local and remote size match - OK" | tee -a "$log"
fi

# create snapshot
if [ "$(sudo lvs | grep -c $snapshot)" != "0" ]; then
  echo "X the snapshot-lv exists - ABORT" | tee -a $log
  exit 1
else
  echo "* create snapshot lv" | tee -a $log
  sudo lvcreate -l100%FREE -s -n $snapshot $locallvname &> /dev/null
  lvsnapshot=$(sudo lvs -o lv_path | grep $snapshot | tr -d " ")
fi

# ssh dd snapshot to other kvm host
echo "* copy snapshot lv to backup lv" | tee -a "$log"
sudo dd if=$lvsnapshot bs=4096 | pv | pigz | ssh $user@$target "pigz -d | sudo dd of=$remotelvname bs=4096"

# delete snapshot lv
echo "* remove snapshot lv"
sudo lvremove -y $lvsnapshot &> /dev/null

echo "* finished backup" | tee -a "$log"

# mail log
if [ "$mailto" != "" ]; then
  echo "* send log by mail"
  mail -s "SCRIPT: vmbackup finished on $(hostname)" $mailto < $log
fi
 [[anwenderwiki:virtualisierung:kvm:kvm_clone]] anwenderwiki/virtualisierung/kvm/kvm_clone.txt · Zuletzt geändert: 2020/03/23 07:23 von thoschi