GoVC是个人非常喜欢的一个VMware官方工具,其可以通过Bash脚本执行,而且命令简单,无需过多的学习成本,但执行效率却非常高,最近有客户提出,停电时如何快速关闭整个vSAN集群(包括虚拟机和主机)的需求,下面就把通过GoVC制作的脚本分享出来,以供应急时使用。
相关工具介绍
工具名称 | 说明文档 | 备注 |
---|---|---|
vcsim | https://github.com/vmware/govmomi/blob/main/vcsim/README.md | vCenter和ESXi的API模拟器 |
govc | https://github.com/vmware/govmomi/blob/main/govc/USAGE.md | 基于govmomi构建的vSphere命令行工具 |
前置条件
由于GoVC需要调用vSAN执行操作,所以,此脚本,只适用于vSAN集群的vCenter部署在集群外,即有独立的管理集群运行vSAN管理的vCenter; 在关机场景下,如果vCenter在vSAN集群内,需要调整脚本,使其只用于关闭虚拟机,vCenter虚拟机和ESXi主机需要手工关闭; 在开机场景下,如果vCenter在vSAN集群内,需要调整脚本,使其只用于打开除vCenter外的虚拟机;
vCenter需要在vSAN集群外部
vCenter需要在vSAN集群外部
vCenter需要在vSAN集群外部
强烈建议,先用模拟器或测试环境进行测试,再使用。
关闭vSAN集群脚本
#!/bin/bash
# 检查govc是否安装
if ! command -v govc &> /dev/null; then
echo "Error: govc is not installed."
echo "Please download and install govc from https://github.com/vmware/govmomi/releases"
exit 1
fi
# 检查jq是否安装
if ! command -v jq &> /dev/null; then
echo "Error: jq is not installed."
echo "Please download and install jq from https://stedolan.github.io/jq/download/"
exit 1
fi
# 设置ESXi主机的IP地址、用户名和密码
export GOVC_URL='https://192.168.10.10/sdk'
export GOVC_USERNAME='administrator@vsphere.local'
export GOVC_PASSWORD='VMware1!'
# 设置GOVC忽略证书验证
export GOVC_INSECURE=true
# 获取所有虚拟机的列表(排除vCLS虚拟机,其会在主机进入维护模式时关闭)
uuids=$( govc find . -type m |grep -v -E 'vCLS-' | xargs -I{} govc vm.info -json "{}" | jq -r '.VirtualMachines[] | select(.Runtime.PowerState == "poweredOn") | .Config.Uuid')
for uuid in $uuids;do
vm_name=$(govc vm.info -json -vm.uuid=$uuid | jq -r '.VirtualMachines[].Name')
echo "The following virtual machine will powered off: $vm_name "
done
# 关闭所有虚拟机(如果虚拟机运行了VMware Tools,采用操作系统关机,否则采用强制关闭电源)
echo "Do you want to shut down all virtual machines? Enter 'yes' or 'y' to continue."
read response
if [[ "$response" == "yes" || "$response" == "y" ]]
then
for uuid in $uuids;do
# 获取虚拟机的VMTools状态
tools_status=$(govc vm.info -json -vm.uuid=$uuid | jq -r '.VirtualMachines[0].Guest.ToolsStatus')
vm_name=$(govc vm.info -json -vm.uuid=$uuid | jq -r '.VirtualMachines[].Name')
# 根据虚拟机VMTools状态决定关机方式
if [ "$tools_status" == "toolsOk" ]; then
echo "Shutting down $vm_name gracefully..."
govc vm.power -s=true -vm.uuid=$uuid
else
echo "Forcefully powering off $vm_name..."
govc vm.power -off -force -vm.uuid=$uuid
fi
done
else
echo "Operation canceled."
fi
# 确保所有虚拟机关闭完成(避免由于虚拟机未完全关闭,造成下一步进入维护模式出错),
echo "-----------------------------"
echo "检测所有虚拟机关闭完成…… "
echo "-----------------------------"
# 每次检查间隔5秒,共等待20分钟。(如果所有虚拟机关键时间超过20分钟,请调整for循环参数)
for ((i=0;i<240;i++))
do
vms=$(govc find . -type m -runtime.powerState poweredOn |grep -v -E 'vCLS-')
if [ -z "$vms" ]; then
break
fi
sleep 5
done
echo "-----------------------------"
echo " 所有虚拟机关闭完成!!! "
echo "-----------------------------"
echo "Please check that vSAN has no data synchronization (cluster->monitor->vSAN->resync components),Enter 'yes' or 'y' to continue."
read response
if [[ "$response" == "yes" || "$response" == "y" ]]
then
# 将vSAN主机放入维护模式(关闭vSAN集群,需要先将所有主机进入到维护模式)
hosts=$(govc find / -type h -runtime.powerState poweredOn)
for host in $hosts
do
# 修改默认维护模式选项为“不迁移数据”。(避免数据迁移,造成关闭失败)
GOVC_HOST=$(echo $host|sed 's:.*/::')
govc host.esxcli system settings advanced set -o /VSAN/DefaultHostDecommissionMode -s noAction
# 将主机放入维护模式
govc host.maintenance.enter $host
done
else
echo "Operation canceled."
fi
echo "------------------------------"
echo "所有主机进入维护模式完成!!!"
echo "------------------------------"
# 关闭所有ESXi主机
for host in $hosts
do
# 关闭ESXi主机
govc host.shutdown $host
done
# 集群关机完成消息
echo "------------------------------"
echo "所有虚拟机和主机关闭完成!!!"
echo "------------------------------"
开启vSAN集群及虚拟机脚本
#!/bin/bash
# 检查govc是否安装
if ! command -v govc &> /dev/null; then
echo "Error: govc is not installed."
echo "Please download and install govc from https://github.com/vmware/govmomi/releases"
exit 1
fi
# 检查jq是否安装
if ! command -v jq &> /dev/null; then
echo "Error: jq is not installed."
echo "Please download and install jq from https://stedolan.github.io/jq/download/"
exit 1
fi
# 设置ESXi主机的IP地址、用户名和密码
export GOVC_URL='https://192.168.10.10/sdk'
export GOVC_USERNAME='administrator@vsphere.local'
export GOVC_PASSWORD='VMware1!'
# 设置GOVC忽略证书验证
export GOVC_INSECURE=true
# 指定需要跳过的虚拟机列表
skipped_vms=('test02')
echo "Confirm to exit maintenance mode on all hosts,Enter 'yes' or 'y' to continue."
read response
if [[ "$response" == "yes" || "$response" == "y" ]]
then
# 将vSAN主机退出维护模式(开启vSAN集群,需要先将所有主机退出维护模式)
hosts=$(govc find / -type h -runtime.inMaintenanceMode true)
if [ -z "$hosts" ]; then
echo "------------------------------"
echo " 所有主机已退出维护模式!!! "
echo "------------------------------"
else
for host in $hosts
do
# 将主机退出维护模式
govc host.maintenance.exit $host
done
echo "------------------------------"
echo "所有主机退出维护模式完成!!!"
echo "------------------------------"
fi
else
echo "Operation canceled."
fi
# 获取所有虚拟机的列表(排除vCLS虚拟机,其会在主机退出维护模式时自动开机)
uuids=$( govc find . -type m |grep -v -E 'vCLS-' | xargs -I{} govc vm.info -json "{}" | jq -r '.VirtualMachines[] | select(.Runtime.PowerState == "poweredOff") | .Config.Uuid')
for uuid in $uuids;do
vm_name=$(govc vm.info -json -vm.uuid=$uuid | jq -r '.VirtualMachines[].Name')
if [[ "${skipped_vms[@]}" =~ "$vm_name" ]]; then
echo "This virtual machine will remain powered off: $vm_name"
continue
else
echo "The following virtual machine will powered on: $vm_name"
fi
done
# 打开所有虚拟机(针对skipped_vms列表中的虚拟机,不开机)
echo "Do you want to powerOn all virtual machines? Enter 'yes' or 'y' to continue."
read response
if [[ "$response" == "yes" || "$response" == "y" ]]
then
for uuid in $uuids
do
vm_name=$(govc vm.info -json -vm.uuid=$uuid | jq -r '.VirtualMachines[].Name')
# 检查虚拟机是否需要跳过开机
if [[ "${skipped_vms[@]}" =~ "$vm_name" ]]; then
echo "Skipping ${vm_name}..."
continue
fi
# 打开关机状态虚拟机
echo "PoweredOn ${vm_name}..."
govc vm.power -on -vm.uuid=$uuid
done
else
echo "Operation canceled."
fi
echo "-----------------------------"
echo " 所有虚拟机开机完成!!! "
echo "-----------------------------"
完毕
通过以上的脚本,也可以加深对GoVC的理解,以及如何在Bash中使用,当然,如果不会写脚本,也可以借助AI工具完成脚本的编写,例如:ChatGPT。