大家好,我是張晉濤。
隨著雲端計算和容器技術的發展,Kubernetes 已經成為了業界的標準和領導者,為使用者提供了一個強大,靈活和可擴充套件的平臺,來部署和管理各種型別的應用。
然而,對於一些難以容器化的應用,例如傳統的企業應用,遺留的系統,或者需要特殊硬體支援的應用,虛擬機器仍然是一個必要和有效的解決方案。
如何在 Kubernetes 上執行和管理虛擬機器,以及如何實現容器和虛擬機器之間的互操作性和一致性,是一個亟待解決的問題。
這就是 KubeVirt 專案誕生的背景和目標。
KubeVirt 是一個開源專案,它使得虛擬機器可以像容器一樣被 Kubernetes 部署,消費和管理。它提供了一個統一的平臺,讓使用者可以根據不同的需求,使用容器或者虛擬機器來構建雲原生應用。KubeVirt 專案於 2016 年啟動,由 Red Hat, IBM, Google, Intel, SUSE 等多家公司和組織共同推動和貢獻。經過 7 年的不懈努力,KubeVirt 於 2023 年 7 月釋出了 v1.0.0 版本,標誌著它已經達到了生產就緒的水平,並且有著健康的社群。(在此之前,它已經被很多公司用到了生產環境)
在這篇中,我將回顧 KubeVirt 的發展歷程,介紹 KubeVirt 的核心功能和優勢,以及分析 KubeVirt 的未來展望和挑戰。
KubeVirt 的發展歷程
KubeVirt 的想法最早可以追溯到 2015 年,在第一屆 KubeCon 上 Red Hat 的工程師 Fabian Deutsch 提出了一個問題:能否在 Kubernetes 上執行虛擬機器?當時的回答是不確定的,但是這個問題引起了很多人的興趣和討論。在接下來的一年裡,Fabian Deutsch 和他的同事開始了一些原型和實驗性的工作,探索了不同的方案和技術。最終,他們選擇了使用 libvirt 和 QEMU 來實現虛擬機器在 Kubernetes 上的執行和管理。
在 2016 年底,KubeVirt 專案正式啟動,並在 GitHub 上開源。專案的主要目標是提供一個 Kubernetes 原生的虛擬化 API 和執行時,讓使用者可以像使用 Pod 和 Deployment 一樣使用 VirtualMachine 和 VirtualMachineInstance 來定義和管理虛擬機器。專案的主要挑戰是如何將虛擬機器與 Kubernetes 的資源模型,排程器,網路,儲存等元件進行整合和協調。
在接下來的幾年裡,KubeVirt 專案經歷了多個階段和版本的迭代和改進。其中一些重要的里程碑包括:
- 2017 年底,KubeVirt 實現了基本的虛擬機器建立和刪除功能,併發布了 v0.1.0 版本。
- 2018 年初,KubeVirt 重新設計了 VirtualMachine 的 API,併發布了 v0.2.0 版本。
- 2018 年中,KubeVirt 相容了 Kubernetes 的網路,以及離線虛擬機器支援,併發布了 v0.3.0 版本。
- 2018 年底,KubeVirt 支援了初始化空 PV,以及 liveness 和 readiness,併發布了 v0.9.0 ~ v0.11.0 版本。
- 2019 年中,KubeVirt 支援了
virtctl migrate
,併發布了 v0.21.0 版本。 - 2022 年初,KubeVirt 移除了舊的對 GPU 裝置的支援,可以透過統一的方式進行定義,併發布了 v0.50.0 版本。
- 2023 年中,KubeVirt 釋出了 v1.0.0 版本。
其實可以看到 KubeVirt 雖然一直沒有釋出 v1.0 版本,但是卻一直保持著比較頻繁的釋出頻率。
在這個過程中,KubeVirt 的社群也不斷地壯大和活躍。截至目前,KubeVirt 的 GitHub 倉庫已經有超過 270 個貢獻者,超過 17k 提交,超過 4.5k star。
KubeVirt 的使用者和合作夥伴也在不斷地增加,包括 IBM, Google, Intel, SUSE, Red Hat, Huawei, VMware, Canonical, Rancher 等多家知名公司和組織。
KubeVirt 的核心功能和優勢
KubeVirt 的核心功能是在 Kubernetes 上執行和管理虛擬機器。為了實現這個功能,KubeVirt 提供了以下幾個方面的解決方案:
虛擬化 API
KubeVirt 定義了一套 Kubernetes 原生的虛擬化 API,讓使用者可以像使用 Pod 和 Deployment 一樣使用 VirtualMachine 和 VirtualMachineInstance 來定義和管理虛擬機器。VirtualMachine 是一種宣告式的資源型別,表示一個期望的虛擬機器狀態。VirtualMachineInstance 是一種實時的資源型別,表示一個正在執行的虛擬機器例項。使用者可以透過 YAML 檔案或者 kubectl 命令來建立,更新,刪除或者查詢這些資源。例如:
apiVersion: kubevirt.io/v1
kind: VirtualMachine
metadata:
annotations:
kubevirt.io/latest-observed-api-version: v1
kubevirt.io/storage-observed-api-version: v1
creationTimestamp: "2023-09-01T00:25:41Z"
finalizers:
- kubevirt.io/virtualMachineControllerFinalize
generation: 1
name: testvm
namespace: default
resourceVersion: "12691"
uid: d5509381-5f21-438b-9440-cb7c9ee82b37
spec:
running: false
template:
metadata:
creationTimestamp: null
labels:
kubevirt.io/domain: testvm
kubevirt.io/size: small
spec:
architecture: amd64
domain:
devices:
disks:
- disk:
bus: virtio
name: containerdisk
- disk:
bus: virtio
name: cloudinitdisk
interfaces:
- masquerade: {}
name: default
machine:
type: q35
resources:
requests:
memory: 64M
networks:
- name: default
pod: {}
volumes:
- containerDisk:
image: quay.io/kubevirt/cirros-container-disk-demo
name: containerdisk
- cloudInitNoCloud:
userDataBase64: SGkuXG4=
name: cloudinitdisk
這個 YAML 檔案定義了一個名為 testvm 的虛擬機器,它有 2 個磁碟。其中一個磁碟是一個容器映象,另一個磁碟是一個雲初始化配置。使用者可以透過 kubectl apply -f testvm.yaml 來建立這個虛擬機器,或者透過 kubectl get vm testvm 來查詢它的狀態。
moelove $ kubectl get vms
NAME AGE STATUS READY
testvm 3m20s Running True
虛擬化執行時
KubeVirt 實現了一套虛擬化執行時,讓使用者可以在 Kubernetes 叢集中的任何節點上執行和管理虛擬機器。KubeVirt 的執行時主要由以下幾個元件構成:
- virt-controller:負責監控和調諧虛擬機器的狀態,以及處理虛擬機器的生命週期事件,如建立,刪除,啟動,停止,遷移等。
- virt-handler:負責在每個節點上執行虛擬機器的操作,如啟動,停止,暫停,恢復等。它也負責與 libvirt 和 QEMU 進行通訊,以及收集和報告虛擬機器的效能指標。
- virt-operator:負責在每個節點上啟動和管理 libvirt 和 QEMU 程式。
- virt-api:負責提供虛擬化 API 的服務端點,以及驗證和轉換使用者的請求。
moelove $ kubectl get pods -n kubevirt
NAME READY STATUS RESTARTS AGE
virt-operator-6c649b9567-m2tbl 1/1 Running 0 6m36s
virt-operator-6c649b9567-kqfnl 1/1 Running 0 6m36s
virt-api-66859f4c8d-tnf68 1/1 Running 0 5m53s
virt-controller-8545966675-wskv9 1/1 Running 0 5m17s
virt-controller-8545966675-z68gb 1/1 Running 0 5m17s
virt-handler-h8zx4 1/1 Running 0 5m17s
KubeVirt 的執行時採用了 Kubernetes 的原生架構和模式,讓使用者可以像管理容器一樣管理虛擬機器。例如:
- 使用者可以使用 kubectl logs 命令來檢視虛擬機器的日誌。
網路解決方案
KubeVirt 支援多種網路外掛和方案,讓使用者可以根據不同的需求,為虛擬機器提供合適的網路連線和配置。KubeVirt 的網路解決方案主要包括以下幾種:
- Pod 網路:這是最簡單和最常用的網路方案,它讓虛擬機器共享 Pod 的網路名稱空間和介面。這樣,虛擬機器就可以像 Pod 一樣訪問叢集內外的網路資源,並且可以被叢集內外的網路資源訪問。
- 多網路:這是一種更靈活和更高階的網路方案,它讓虛擬機器可以有多個網路介面,並且可以連線到不同的網路平面。這樣,虛擬機器就可以根據不同的用途和場景,使用不同的網路策略和配置。例如,一個虛擬機器可以有一個用於管理的網路介面,一個用於資料傳輸的網路介面,和一個用於公網訪問的網路介面。
- 橋接網路:這是一種更接近傳統虛擬化的網路方案,它讓虛擬機器可以直接使用節點上的物理網路介面和地址。這樣,虛擬機器就可以像物理機一樣,與節點上的其他裝置進行通訊,並且可以使用節點上的網路安全和監控工具。
- SR-IOV 網路:這是一種更高效能和更低延遲的網路方案,它讓虛擬機器可以直接使用節點上的物理網路卡的虛擬功能。這樣,虛擬機器就可以繞過軟體層的開銷,直接訪問硬體層的資源,並且可以享受硬體層的加速和最佳化。
儲存解決方案
KubeVirt 支援多種儲存外掛和方案,讓使用者可以根據不同的需求,為虛擬機器提供合適的儲存空間和配置。KubeVirt 的儲存解決方案主要包括以下幾種:
- 容器磁碟:這是一種基於容器映象的儲存方案,它讓虛擬機器可以使用容器映象作為其根磁碟。這樣,虛擬機器就可以像容器一樣,快速地啟動和停止,並且可以享受容器映象的便利和安全性。
- 持久卷:這是一種基於 Kubernetes 的儲存方案,它讓虛擬機器可以使用 Kubernetes 的持久卷(PV)和持久卷宣告(PVC)作為其資料磁碟。這樣,虛擬機器就可以像 Pod 一樣,使用 Kubernetes 的儲存類(StorageClass)來動態地申請和釋放儲存空間,並且可以使用 Kubernetes 的儲存外掛來連線到不同的儲存後端。
- 主機磁碟:這是一種基於節點的儲存方案,它讓虛擬機器可以使用節點上的本地磁碟或者目錄作為其資料磁碟。這樣,虛擬機器就可以利用節點上的儲存效能和容量,並且可以避免網路層的開銷和延遲。
- CDI 磁碟:這是一種基於 CDI(Containerized Data Importer)專案的儲存方案,它讓使用者可以從不同的來源(如 HTTP, S3, Registry 等)匯入或者克隆資料到 Kubernetes 的持久卷中,並且可以自動地轉換資料的格式(如 qcow2, raw, vmdk 等)。這樣,使用者就可以方便地將現有的虛擬機器映象或者資料遷移或者複製到 Kubernetes 中,並且可以使用 KubeVirt 來執行和管理它們。
映象解決方案
KubeVirt 支援多種映象外掛和方案,讓使用者可以根據不同的需求,為虛擬機器提供合適的映象源和配置。KubeVirt 的映象解決方案主要包括以下幾種:
- 容器映象:這是一種基於容器技術的映象方案,它讓使用者可以使用容器映象作為虛擬機器的根磁碟或者 CD-ROM。這樣,使用者就可以利用容器技術的優勢,如輕量級,快速啟動,易於分發,安全隔離等。
- 虛擬機器映象:這是一種基於傳統虛擬化技術的映象方案,它讓使用者可以使用虛擬機器映象作為虛擬機器的初始化配置。
KubeVirt 的未來
如今 KubeVirt 已經發布 v1.0 版本,紅帽作為創始成員,在 OpenShift 虛擬化中攜帶了 KubeVirt。Kubermatic、Rancher、Google、Oracle 等也提供內建 KubeVirt 的產品。Civio、Puzl、Platform9 和其他公司將 KubeVirt 帶到了雲端,並提供託管和自管理的產品。
KubeVirt 的價值已經被大家看到,未來也將會有更多的企業將其應用到自己的環境中,並且推動社群的發展。
我在 2019 年左右曾經嘗試過 KubeVirt,當時它還不是很成熟,所以最終並沒有採納它,現在我覺得我可以再試試如何將它加入到我的系統中了。
歡迎訂閱我的文章公眾號【MoeLove】