Skip to content

Instantly share code, notes, and snippets.

@jpluimers
Created May 14, 2021 19:33
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jpluimers/d9cb09dabe57dd2fff614d1a9ce7e1a3 to your computer and use it in GitHub Desktop.
Save jpluimers/d9cb09dabe57dd2fff614d1a9ce7e1a3 to your computer and use it in GitHub Desktop.
#!/bin/sh
######################################################################################
# Create a clone of a running machine on ESXi, without vCenter services available
# Disable networkcards on connecting at startup
# Start the cloned VM
#
# Created by : Jeroen van Schelt
# Creation date : jan 2015
# Tested on : ESXi 5.5 build 1746018
#
#
# To run this script on a regular basis, without user intervention, do the following :
#
# Copy the script to a datastore
# Add the cron job to the root crontab:
# Edit /var/spool/cron/crontabs/root
# Add the line (all on one line)
# 30 1 * * * /vmfs/volumes/BOXSR0089_das1/scripts/hotcloneBOXPC8888vm.sh > /vmfs/volumes/BOXSR0089_das1/scripts/hotcloneBOXPC8888vm.log 2>&1
# Run the command "kill $(cat /var/run/crond.pid)", This will kill the process crond.
#
# Edit /etc/rc.local.d/local.sh, using a command such as "vi /etc/rc.local.d/local.sh".
# At the end of the file, add 3 lines (using "G" then "O" in vi). The first kills crond, the second adds the new cron job to the root crontab file, ad the third restarts crond:
# /bin/kill $(cat /var/run/crond.pid)
# /bin/echo "30 1 * * * /vmfs/volumes/BOXSR0089_das1/scripts/hotcloneBOXPC8888vm.sh > /vmfs/volumes/BOXSR0089_das1/scripts/hotcloneBOXPC8888vm.log 2>&1" >> /var/spool/cron/crontabs/root
# /usr/lib/vmware/busybox/bin/busybox crond
# Save and exit the editor (Press the "Esc" key then ":wq" then press "Return" in vi)
# Run the command "auto-backup.sh" so that the change to /etc/rc.local survives a reboot.
# Run the command "/usr/lib/vmware/busybox/bin/busybox crond"
######################################################################################
# user variables
SourceVM="NameOfSVM"
SourceDS="/vmfs/volumes/NameOfDS"
DestDS="/vmfs/volumes/NameOfDS"
ScriptDIR="$SourceDS/scripts"
######################################################################################
# Do NOT modify anything beyond this point, unless you know what you are doing
######################################################################################
# script variables
DestVM="HotClone_$SourceVM"
ScriptRunTime=$(date "+%Y%m%d_%H%M")
nicfile=$ScriptDIR/nic_$DestVM.txt
diskfile=$ScriptDIR/disk_$DestVM.txt
# create destination directory
mkdir $DestDS/$DestVM
# copy source vmx? files to destination
cp $SourceDS/$SourceVM/$SourceVM.vmx $DestDS/$DestVM/$DestVM.vmx
sed -i "s/$SourceVM/$DestVM/g" $DestDS/$DestVM/$DestVM.vmx
cp $SourceDS/$SourceVM/$SourceVM.vmxf $DestDS/$DestVM/$DestVM.vmxf
sed -i "s/$SourceVM/$DestVM/g" $DestDS/$DestVM/$DestVM.vmxf
# create snapshot from source
lineCount=`expr $(vim-cmd vmsvc/getallvms | wc -l) - 1`
x=0
while [[ $x -ne $lineCount ]]; do
x=`expr $x + 1`
VMID=$(vim-cmd vmsvc/getallvms | tail -$lineCount | awk '{ print $1 }' | sed -n -e "$x"p)
VMNAME=$(vim-cmd vmsvc/getallvms | tail -$lineCount | awk '{ print $2 }' | sed -n -e "$x"p)
if [[ $SourceVM == $VMNAME ]]; then
SourceVMID=$VMID
vim-cmd vmsvc/snapshot.create $SourceVMID HotClone_$ScriptRunTime HotClone_of_$SourceVM 0 0
fi
done
# Search for Disks
rm $diskfile > /dev/null 2>&1
while read line ; do
grep ".vmdk" | awk '{ print $3}' | sed "s/\"//g" >> $diskfile
done < $DestDS/$DestVM/$DestVM.vmx
# copy sourcedisk to destinationdisk (thin provisioned)
while read line ; do
vmkfstools -d thin -i $SourceDS/$SourceVM/$(echo $line | sed "s/$DestVM/$SourceVM/g") $DestDS/$DestVM/$(echo $line | sed 's/-[0-9]*//g')
done < $diskfile
# If Source already had a snapshot, remove snapdata on vmdk filename in vmx-file
sed -i "s/\(.*\)\-.*\(.vmdk\)/\1\2/g" $DestDS/$DestVM/$DestVM.vmx
# Search for nics
rm $nicfile > /dev/null 2>&1
while read line ; do
grep ethernet[0-9].virtualDev | awk '{ print $1}' | sed "s/.virtualDev//g" >> $nicfile
done < $DestDS/$DestVM/$DestVM.vmx
# set nic disconnected at boot
while read line ; do
if [[ -n "$(grep $line.startConnected $DestDS/$DestVM/$DestVM.vmx)" ]]; then
echo "found in $line"
sed -i "s/$line.startConnected = \"TRUE\"/$line.startConnected = \"FALSE\"/g" $DestDS/$DestVM/$DestVM.vmx
else
echo "nothing on $line"
echo $line.startConnected = \"FALSE\" >> $DestDS/$DestVM/$DestVM.vmx
fi
done < $nicfile
# register destination VM in inventory
DestVMID=`vim-cmd solo/registervm $DestDS/$DestVM/$DestVM.vmx`
# Powering up destination virtual machine
vim-cmd vmsvc/power.on $DestVMID &
sleep 15
vim-cmd vmsvc/message $DestVMID _vmx1 2
# Remove HotClone Snapshot from source
SnapToRemove=`vim-cmd vmsvc/snapshot.get $SourceVMID | grep -A 1 HotClone_$ScriptRunTime | grep -e "Id" | awk '{print $4 }'`
vim-cmd vmsvc/snapshot.remove $SourceVMID $SnapToRemove 0
# EOF
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment