初始基於K8s的虛擬化技術Kube-virt

根據Garnter的最新預測,到2022年將會有75%的生產應用全部跑在容器環境之上。基於這個預測,其實至少還有25%的架構由於技術原因或是認爲原因都將仍然跑在舊的架構之上,這其中虛擬機又會佔據其中的大部分份額。所以在容器技術尤其是Kubernetes誕生之初,就已經有開源的社區在爲如何使用Kubernetes納管虛擬機作爲一個重要的功能在開發和貢獻。

今天要介紹的主角就是Kube-virt,那麼使用Kube-virt主要會幫我們解決以下兩個問題:
🔹從技術層面,完全的虛擬機納管,可以完美遷移因爲內核版本過於陳舊以及語言問題而無法遷移到容器的部分應用
🔹從管理和運維層面,符合傳統的運維工作方式,以前的SSH 等運維方式可以完美複用

架構

爲什麼kube-virt可以做到讓虛擬機無縫的接入到K8S?
首先,先給大家介紹一下它的整體架構。
在這裏插入圖片描述

  • virt-api
    kubevirt是以CRD形式去管理vm pod, virt-api就是所有虛擬化操作的入口,包括常規的CRD更新驗證以及vm start、stop
  • virt-controlller
    virt-controller會根據vmi CRD,生成對應的virt-lancher pod,並維護CRD的狀態
  • virt-handler
    Virt-handler會以Daemonset形式部署在每個節點上,負責監控節點上每個虛擬機實例狀態變化,一旦檢測到狀態變化,會進行響應並確保相應操作能達到所需(理想)狀態。
    Virt-handler保持集羣級VMI Spec與相應libvirt域之間的同步;報告Libvirt域狀態和集羣Spec的變化;調用以節點爲中心的插件以滿足VMI Spec定義的網絡和存儲要求。
  • virt-launcher
    每個virt-lanuncher pod對應着一個VMI, kubelet只是負責virt-lanuncher pod運行狀態,不會去關心VMI創建情況。
    virt-handler會根據CRD參數配置去通知virt-lanuncher去使用本地libvirtd實例來啓動VMI, virt-lanuncher就會如果pid去管理VMI,pod生命週期結束,virt-lanuncher也會去通知VMI去終止。
    每個virt-lanuncher pod對應一個libvirtd,virt-lanuncher通過libvirtd去管理VM的生命週期,這樣做到去中心化,不再是以前虛擬機那套做法,一個libvirtd去管理多個VM。
  • virtctl
    virctl 是kubevirt自帶類似kubectl命令,它是越過virt-lancher pod這層去直接管理vm,可以控制vm 的start、stop、restart。

總結:kubevirt以CRD形式將VM管理接口接入到kubernetes,通過一個pod去使用libvirtd管理VM方式,實現pod與VM的一對一對應,做到如同容器一般去管理虛擬機,並且做到與容器一樣的資源管理、調度規劃,這個整體與企業Iaas關係不大,也方便企業接入。

流程

上述架構裏其實已經部分簡述了VM的創建流程,以下進行流程梳理:

  1. K8S API 創建VMI CRD對象 virt-controller監聽到VMI創建時,會根據VMI配置生成pod
  2. spec文件,創建virt-launcher pods virt-controller發現virt-launcher
  3. pod創建完畢後,更新VMI CRD狀態
  4. virt-handler監聽到VMI狀態變更,通信virt-launcher去創建虛擬機,並負責虛擬機生命週期管理

存儲

kubevirt 提供很多種存儲方式,存儲就決定了你使用虛擬機鏡像到底什麼內核、什麼版本,以下主要講述我看到三種比較常用的形式

  • registryDisk

定義image來創建虛擬機的root disk。virt-controller會在pod定義中創建registryVolume的container,container中的entry服務負責 將spec.volumes.registryDisk.image轉化爲qcow2格式,路徑爲pod根目錄。
kubevirt 提供了registryDIsk的基礎鏡像:registry-disk-v1alpha, 根據Dockerfile形式去創建虛擬機鏡像,以下是window鏡像demo Dockerfile

FROM kubevirt/registry-disk-v1alpha COPY
Windows—server-2012-datacenter-64bit-cn-syspreped—2018-01-15.qcow2
/disk/windows2012dc.img

這個最終我們構建成鏡像名:windows2012dc:latest , 最終在CRD表現形式是這樣的:

kind: VirtualMachineInstance

spec:
domain:
devices:
disks:
- disk:
bus: virtio
name: registrydisk
volumeName: registryvolume … - name: registryvolume registryDisk:
image: windows2012dc:latest

  • PVC

PVC是持久化存儲鏡像的形式,它會被掛在到pod中,且格式必須滿足/disk/*.img,這樣kubevirt才能夠實現虛擬機存儲。

  • CDI

CDI是kubevirt自己提供的一種形式, 把registryDisk 轉換爲PVC,這個需要消耗時間去講鏡像轉換爲PVC持久化存儲下來。

網絡

虛擬機網絡就是pod網絡,virt-launcher pod網絡的網卡不再掛有pod ip,而是作爲虛擬機的虛擬網卡的與外部網絡通信的交接物理網卡,virt-launcher實現了簡單的單ip dhcp server,就是需要虛擬機中啓動dhclient,virt-launcher 服務會分配給虛擬機。
在這裏插入圖片描述

監控

Kube-handler會去調用當前節點下所有虛擬機的libvirt API,獲取虛擬機的監控指標,並提供metrics 接口,最後通過kubevirt-prometheus-metrics聚合所有節點的kube-handler的指標數據,提供給prometheus使用。

遷移

通過CRD:
VirtualMachineInstanceMigration(VMIM) 來實現動態遷移

apiVersion: kubevirt.io/v1alpha3
kind: VirtualMachineInstanceMigration
metadata:
name: migration-job
spec:
vmiName: vmi-fedora

這種遷移形式其實並沒有指定遷移到哪些節點上,內部邏輯應該只是重新調度virt-lanucher pod, 其中kubeirt-config可以對此進行遷移的相關限制,比如遷移的頻率(同時只能幾個節點進行遷移),遷移的網絡速率(因爲可能實際到數據磁盤複製), 通過VMIM也能查看到遷移進度。

Kubevirt VS Kata Container

當然Kube-virt並不是目前唯一的可以在Kuberentes上實踐虛擬化的技術。我們把它也和目前比較流行的kata container做了一個對比,方便用戶根據實際情況來做選擇。
在這裏插入圖片描述


點擊查看原文
或掃描下方的微信公衆號二維碼查詢
在這裏插入圖片描述

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章