###### tags: `govc` `vmware` `api` `instantclone` # 使用 GOVC 即時克隆 (Instant Clone) 複製虛擬機 - Part 3 (GOVC) [toc] 有了之前 [Part 1](https://hackmd.io/@farmer87/instantclone) 和 [Part 2](https://hackmd.io/@farmer87/instantclone-2) 測試即時克隆(Instant Clone)的經驗,加上最近頻繁使用到的 [GOVC](https://github.com/vmware/govmomi/tree/master/govc),剛好有提供 **instant clone** 的功能,剛好同事也有需求就測試一下囉。以下僅作重點步驟紀錄,詳細的流程可參考先前資訊。 ## 測試準備 - 準備一台作為 instant clone 來源端的虛擬機器作為母版。這裡還是以取得無障礙的 Linux 發行版本為主。 - 將客製化所需的腳本檔上傳至來源端的虛擬機器。 - 完成動作後,可以關閉虛擬機器。後續會使用 `govc` 來開啟虛擬機器電源。 - 使用 Instant Clone 產生 5 台虛擬機器,完成後連線並確認相關主機及網路狀態。 - 備妥 **GOVC** 程式進行測試 [[GOVC 安裝及基礎測試]](https://hackmd.io/@farmer87/govc)。 ## 測試步驟 ### 連線 vCenter 使用 `govc` 前需要先宣告環境變數,等於要連線 vCenter Server,至少提供以下環境變數。 ```bash export GOVC_URL="https://vcsa" export GOVC_USERNAME="administrator@vsphere.local" export GOVC_PASSWORD="********" export GOVC_INSECURE="true" export GOVC_DATACENTER="Datacenter" export GOVC_CLUSTER="Cluster" export GOVC_DATASTORE="Datastore" ``` ### 確認來源端 VM 電源 作為 Instant Clone 的來源端虛擬機器需為電源開啟狀態,否則無法使用 Instant Clone。  可以使用 `govc vm.info`命令了解虛擬機器狀態概要。目前電源狀態為關閉。(**Power state: poweredOff**) ```bash $ sourceVM='Richard-ic-parentVM' $ govc vm.info ${sourceVM} Name: Richard-ic-parentVM Path: /Datacenter/vm/Richard/ic_workVM/Richard-ic-parentVM UUID: 422bb28c-2bc9-3306-b52f-263a3753b44d Guest name: CentOS 7 (64-bit) Memory: 8192MB CPU: 2 vCPU(s) Power state: poweredOff Boot time: 2021-10-13 07:07:55.031426 +0000 UTC IP address: Host: 10.7.150.2 ``` 使用 **`govc vm.power -on`** 開啟虛擬機器電源。 ```bash $ govc vm.power -on ${sourceVM} Powering on VirtualMachine:vm-3815... OK $ govc vm.info ${sourceVM} Name: Richard-ic-parentVM Path: /Datacenter/vm/Richard/ic_workVM/Richard-ic-parentVM UUID: 422bb28c-2bc9-3306-b52f-263a3753b44d Guest name: CentOS 7 (64-bit) Memory: 8192MB CPU: 2 vCPU(s) Power state: poweredOn Boot time: 2021-10-14 07:13:37.774276 +0000 UTC IP address: 10.7.150.80 Host: 10.7.150.2 ``` ### 執行來源端虛擬機器凍結程式 使用 vSphere Web Client 或是 SSH 連線至來源端虛擬機器 `Richard-ic-parentVM`,執行之前上傳的凍結程式 `customize_ic_centos7.sh`。目的是為了讓之後 Instant Clone 產生的 VM 能夠根據引入的 **`guestinfo.ic.X`** 參數值調整 IP 等網路設定。並且會將母版 VM 進行凍結! **customize_ic_centos7.sh** 部份程式碼: ```bash set -x touch /root/ic-customization.log exec > /root/ic-customization.log 2>&1 echo -e "\n=== Start Pre-Freeze ===" # Disable Wired_connection_1 ifName="Wired connection 1" ifDevice=$(nmcli -t device | grep 'ethernet' | awk -F':' '{print $1}') #ip link set "${ifDevice}" down nmcli con down "${ifName}" echo -e "=== End of Pre-Freeze ===\n" echo -e "Freezing ...\n" vmware-rpctool "instantclone.freeze" ``` 其中在 Linux Guest OS 上使用 **`vmware-rpctool "instantclone.freeze"`** 或是 **`vmtoolsd -cmd "instantclone.freeze"`** 命令可凍結虛擬機。在 Windows Guest OS 上可使用 **`C:\Program Files\VMware\VMware Tools\vmtoolsd.exe --cmd "instantclone.freeze"`** 命令進行凍結。 > **注意** [color=red] > 當虛擬機器被凍結之後,虛擬機管理程序會禁止使用 Guest OS,但虛擬機器仍在運行,以便進行後續 Instant Clone 作業。  之後會根據在執行 Instant Clone 時引入的 **`guestinfo.ic.X`** 參數值透過 VMware Tools 寫入目的端虛擬機器,以便調整 IP 等相關設定。 > $(vmware-rpctool "info-get guestinfo.ic.X) **customize_ic_centos7.sh** 部份程式碼: ```bash ###################################################### # All commands past this point are run on the clones ###################################################### echo -e "\n=== Start Post-Freeze ===" # retrieve networking info passed from script HOSTNAME=$(vmware-rpctool "info-get guestinfo.ic.hostname") IP_ADDRESS=$(vmware-rpctool "info-get guestinfo.ic.ipaddress") NETMASK=$(vmware-rpctool "info-get guestinfo.ic.netmask") GATEWAY=$(vmware-rpctool "info-get guestinfo.ic.gateway") DNS=$(vmware-rpctool "info-get guestinfo.ic.dns") ``` ### 執行 Instant Clone 接著準備使用 **`govc vm.instantclone`** 執行 Instant Clone。並使用 `-e guestinfo.ic.X=<value>` 的方式帶入參數值 > **注意** [color=blue] > 這裡定義的 **`guestinfo.ic.X`** 變數,需要與凍結程式 `customize_ic_centos7.sh` 當中的變數一致。 ```bash $ govc vm.instantclone -h Usage: govc vm.instantclone [OPTIONS] NAME Instant Clone VM to NAME. Examples: govc vm.instantclone -vm source-vm new-vm # Configure ExtraConfig variables on a guest VM: govc vm.instantclone -vm source-vm -e guestinfo.ipaddress=192.168.0.1 -e guestinfo.netmask=255.255.255.0 new-vm # Read the variable set above inside the guest: vmware-rpctool "info-get guestinfo.ipaddress" vmware-rpctool "info-get guestinfo.netmask" ``` 我們可以撰寫個簡單的 BASH 腳本檔 `createInstantCloneVM.sh` 來執行 Instant Clone。 ```bash #!/bin/bash sourceVM='Richard-ic-parentVM' count=5 for ((i=1;i<=${count};i++)); do govc vm.instantclone -vm ${sourceVM} \ -e guestinfo.ic.hostname=ic-${i} \ -e guestinfo.ic.ipaddress=10.7.150.8${i} \ -e guestinfo.ic.netmask=255.255.255.0 \ -e guestinfo.ic.gateway=10.7.150.254 \ -e guestinfo.ic.dns=8.8.8.8 \ "Richard-IC-VM${i}" done ``` 透過 Web Client 觀察生成狀態,的確在秒級的速度下完成 5 台虛擬機器的建立。  ### 檢視虛擬機器狀態 由 Web Client 觀察由 Instant Clone 產生虛擬機器的狀態。  連線至虛擬機器檢視網路設定調整項目。  ## 進階探索 ### 凍結狀態 可以透過 `govc vm.info` 命令查詢剛剛提到 `Runtime.InstantCloneFrozen` 狀態。 在執行凍結程式之前,Instant Clone 來源端虛擬機器尚未被凍結。 ```bash $ govc vm.info -json ${sourceVM} | jq '.VirtualMachines[].Runtime.InstantCloneFrozen' false ``` 使用 SSH 連線 Instant Clone 來源端虛擬機器,遠端執行凍結程式 `customize_ic_centos7.sh`。 ```bash $ sshpass -p ${password} ssh ${user}@${sourceVM} './customize_ic_centos7.sh' +-+-+-+-+-+-+-+-+-+-+-+-+-++-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-++-+-+-+ L I N U X V M I M A G E S . C O M +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ User Name: centos Password: centos (sudo su -) + touch /root/ic-customization.log + exec ``` 再次查詢虛擬機器的凍結狀態,此時 `Runtime.InstantCloneFrozen: True` 顯示**已被凍結**。 ```bash $ govc vm.info -json ${sourceVM} | jq '.VirtualMachines[].Runtime.InstantCloneFrozen' true ``` ### 虛擬機器佈署摘要 來源端虛擬機器 **Richard-ic-parentVM** ```bash $ govc vm.info Richard-ic-parentVM Name: Richard-ic-parentVM Path: /Datacenter/vm/Richard/ic_workVM/Richard-ic-parentVM UUID: 422bb28c-2bc9-3306-b52f-263a3753b44d Guest name: CentOS 7 (64-bit) Memory: 8192MB CPU: 2 vCPU(s) Power state: poweredOn Boot time: 2021-10-14 07:13:37.774276 +0000 UTC IP address: Host: 10.7.150.2 ``` 目的端虛擬機器 **Richard-IC-VM1** ```bash $ govc vm.info Richard-IC-VM1 Name: Richard-IC-VM1 Path: /Datacenter/vm/Richard/ic_workVM/Richard-IC-VM1 UUID: 422bf33d-9b76-5bc3-6e80-8852b04971cc Guest name: CentOS 7 (64-bit) Memory: 8192MB CPU: 2 vCPU(s) Power state: poweredOn Boot time: <nil> IP address: 10.7.150.81 Host: 10.7.150.2 ``` **Richard-IC-VM2** ```bash $ govc vm.info Richard-IC-VM2 Name: Richard-IC-VM2 Path: /Datacenter/vm/Richard/ic_workVM/Richard-IC-VM2 UUID: 422bb35a-a328-20cf-e731-e65a8b43587e Guest name: CentOS 7 (64-bit) Memory: 8192MB CPU: 2 vCPU(s) Power state: poweredOn Boot time: <nil> IP address: 10.7.150.82 Host: 10.7.150.2 ``` **Richard-IC-VM3** ```bash govc vm.info Richard-IC-VM3 Name: Richard-IC-VM3 Path: /Datacenter/vm/Richard/ic_workVM/Richard-IC-VM3 UUID: 422b9260-c58d-9423-6f5e-c3f40796240c Guest name: CentOS 7 (64-bit) Memory: 8192MB CPU: 2 vCPU(s) Power state: poweredOn Boot time: <nil> IP address: 10.7.150.83 Host: 10.7.150.2 ``` **Richard-IC-VM4** ```bash $ govc vm.info Richard-IC-VM4 Name: Richard-IC-VM4 Path: /Datacenter/vm/Richard/ic_workVM/Richard-IC-VM4 UUID: 422b152a-2dcd-af5c-db85-c93fe87e509e Guest name: CentOS 7 (64-bit) Memory: 8192MB CPU: 2 vCPU(s) Power state: poweredOn Boot time: <nil> IP address: 10.7.150.84 Host: 10.7.150.2 ``` **Richard-IC-VM5** ```bash $ govc vm.info Richard-IC-VM5 Name: Richard-IC-VM5 Path: /Datacenter/vm/Richard/ic_workVM/Richard-IC-VM5 UUID: 422b2562-be45-0e9b-76e5-e1eacada5f31 Guest name: CentOS 7 (64-bit) Memory: 8192MB CPU: 2 vCPU(s) Power state: poweredOn Boot time: <nil> IP address: 10.7.150.85 Host: 10.7.150.2 ``` ### Instant Clone 虛擬機器關聯 從 Web Client 顯示來源端虛擬機器 `Richard-ic-parentVM` 目前使用的磁碟路徑: **`[VNXe_Datastore_Sales2] Richard-ic-parentVM/Richard-ic-parentVM-000012.vmdk`**  可以使用以下 govc 命令進行查詢較為方便。 ```bash $ govc vm.info -json ${sourceVM} | jq '.VirtualMachines[] | .Config.Hardware.Device[]| select (.Backing.Parent != null) | .Backing.FileName' "[VNXe_Datastore_Sales2] Richard-ic-parentVM/Richard-ic-parentVM-000012.vmdk" ``` 以下是目前使用磁碟的親屬關係磁碟: **`[VNXe_Datastore_Sales2] Richard-ic-parentVM/Richard-ic-parentVM-000011.vmdk`** ```bash $ govc vm.info -json ${sourceVM} | jq '.VirtualMachines[] | .Config.Hardware.Device[]| select (.Backing.Parent != null) | .Backing.Parent.FileName' "[VNXe_Datastore_Sales2] Richard-ic-parentVM/Richard-ic-parentVM-000011.vmdk" ``` 使用同樣的方式,我們來檢視一下透過 Instant Clone 產生的**目的端虛擬機器與來源端虛擬機器的關係**。 **Richard-IC-VM1** - 目前使用的磁碟 ```bash $ govc vm.info -json ${targetVM1} | jq '.VirtualMachines[] | .Config.Hardware.Device[]| select (.Backing.Parent != null) | .Backing.FileName' "[VNXe_Datastore_Sales2] Richard-IC-VM1/Richard-IC-VM1-000011.vmdk" ``` - 親屬關係磁碟 注意一下 **`[VNXe_Datastore_Sales2] Richard-ic-parentVM/Richard-ic-parentVM-000011.vmdk`** 就是來源端虛擬機器的磁碟路徑! ```bash govc vm.info -json ${targetVM1} | jq '.VirtualMachines[] | .Config.Hardware.Device[]| select (.Backing.Parent != null) | .Backing.Parent.FileName' "[VNXe_Datastore_Sales2] Richard-ic-parentVM/Richard-ic-parentVM-000011.vmdk" ``` 其他透過 Instant Clone 產生的虛擬機器的親屬關係磁碟也是相同的。 **Richard-IC-VM2** ```bash $ govc vm.info -json ${targetVM2} | jq '.VirtualMachines[] | .Config.Hardware.Device[]| select (.Backing.Parent != null) | .Backing.Parent.FileName' "[VNXe_Datastore_Sales2] Richard-ic-parentVM/Richard-ic-parentVM-000011.vmdk" ``` **Richard-IC-VM3** ```bash $ govc vm.info -json ${targetVM3} | jq '.VirtualMachines[] | .Config.Hardware.Device[]| select (.Backing.Parent != null) | .Backing.Parent.FileName' "[VNXe_Datastore_Sales2] Richard-ic-parentVM/Richard-ic-parentVM-000011.vmdk" ``` **Richard-IC-VM4** ```bash $ govc vm.info -json ${targetVM4} | jq '.VirtualMachines[] | .Config.Hardware.Device[]| select (.Backing.Parent != null) | .Backing.Parent.FileName' "[VNXe_Datastore_Sales2] Richard-ic-parentVM/Richard-ic-parentVM-000011.vmdk" ``` **Richard-IC-VM5** ```bash $ govc vm.info -json ${targetVM5} | jq '.VirtualMachines[] | .Config.Hardware.Device[]| select (.Backing.Parent != null) | .Backing.Parent.FileName' "[VNXe_Datastore_Sales2] Richard-ic-parentVM/Richard-ic-parentVM-000011.vmdk" ``` 請回憶凍結模式的架構圖。  ## 清理測試環境 最後還是用 GOVC 來清理剛剛生成的 VM。這個命令要小心喔,按下 Enter 就直接執行了! `for ((i=1;i<=5;i++));do govc vm.destroy Richard-IC-VM${i}; done`  ## 其他分享 ### [GOVC 安裝及基礎測試](https://hackmd.io/@farmer87/govc) ### [使用 GOVC 開啟/關閉 ESXi 主機服務](https://hackmd.io/@farmer87/govc_services) ### [使用 GOVC 更新 ESXi 主機 root 密碼](https://hackmd.io/@farmer87/govc_account_update) ### [使用 GOVC 安裝 Fedora CoreOS 於 vSphere 環境](https://hackmd.io/@farmer87/govc-coreos) --- ### [使用即時克隆 (Instant Clone) 複製虛擬機 - Part 1](https://hackmd.io/@farmer87/instantclone) ### [使用即時克隆 (Instant Clone) 複製虛擬機 - Part 2](https://hackmd.io/@farmer87/instantclone-2)
×
Sign in
Email
Password
Forgot password
or
By clicking below, you agree to our
terms of service
.
Sign in via Facebook
Sign in via Twitter
Sign in via GitHub
Sign in via Dropbox
Sign in with Wallet
Wallet (
)
Connect another wallet
New to HackMD?
Sign up