做者:Patrick Ohly(英特爾)linux
愈來愈多過去是Kubernetes組件的一部分,如今搬到在Kubernetes以外開發。例如,存儲驅動程序曾經被編譯成Kubernetes二進制文件,而後被轉移到主機上的獨立Flexvolume二進制文件中,如今做爲容器存儲接口(Container Storage Interface,CSI)驅動程序提供,這些驅動程序部署在Kubernetes集羣內部的pod中。git
這對於處理此類組件的開發者來講是一個挑戰:如何在這樣的外部組件上對Kubernetes集羣進行端到端(E2E)測試?用於測試Kubernetes自己的E2E框架具備全部必要的功能。可是,嘗試在Kubernetes以外使用它很困難,只有經過仔細選擇大量依賴項的正確版本才能實現。在Kubernetes 1.13中,E2E測試變得更加簡單。github
這篇博客文章總結了Kubernetes 1.13的變化。對於CSI驅動程序開發者,它將涵蓋使存儲測試可用於測試第三方CSI驅動程序。如何使用它們將基於兩個Intel CSI驅動程序顯示:json
測試這些驅動程序是大多數這些加強功能的主要動機。後端
E2E測試包括幾個階段:api
全部如下加強都遵循相同的基本模式:它們使E2E框架在Kubernetes以外更有用和更容易使用,而不會改變原始Kubernetes e2e.test二進制文件的行爲。架構
使用Kubernetes <= 1.12的E2E框架很困難的主要緣由是依賴於特定於提供者的SDK,這些SDK使用了大量的軟件包。只是編譯它已經不簡單。併發
許多這些軟件包僅在某些測試中須要。例如,測試預配置卷的安裝必須首先經過一些非Kubernetes API,直接與特定存儲後端通訊,以管理員相同的方式配置這樣的卷。框架
如今有嘗試從核心Kubernetes中刪除特定於雲供應商的測試。在PR#68483中採用的方法能夠看做是朝着這個目標邁出的一步:不是當即剝離代碼並打破全部依賴它的測試,全部特定於雲供應商的代碼都被移動到test/e2e/framework/providers下的可選包中。而後,E2E框架經過每一個供應商包單獨實現的接口訪問它。ssh
E2E測試套件的做者決定將哪些軟件包導入測試套件。而後經過--provider命令行標誌激活供應商支持。1.13和1.14中的Kubernetes e2e.test二進制文件仍然支持與1.12中相同的供應商程序。也能夠不包含任何包,這意味着只有通用供應上程序可用:
測試可能必須在運行時讀取其餘文件,例如.yaml清單。可是Kubernetes e2e.test二進制文件應該是可用的而且徹底獨立,由於這簡化了發佈和運行它。Kubernetes構建系統中的解決方案是使用go-bindata將test/e2e/testing-manifests下的全部文件連接到二進制文件中。E2E框架過去對go-bindata的輸出有很強的依賴性,如今bindata支持是可選的。經過testfiles包訪問文件時,將從不一樣的源檢索文件:
e2e.test二進制文件採用控制測試執行的附加參數。2016年,開始嘗試用Viper配置文件替換全部E2E命令行參數。可是這種努力停滯不前,這使得開發者沒有明確指導他們應該如何處理特定於測試的參數。
v1.12中的方法是將全部標誌添加到中央test/e2e/framework/test_context.go,這對於獨立於框架開發的測試不行。自PR#69105以來,建議使用普通標誌包在其本身的源代碼中定義其參數。標記名稱必須是分層的,點分隔不一樣的級別,例如my.test.parameter,而且必須是惟一的。標誌包強制執行惟一性,第二次註冊標誌時會發生混亂。新的配置包簡化了多個選項的定義,這些選項存儲在單個結構中。
總而言之,這就是如今如何處理參數:
可是,最近有人指出,比較可取且有可能不將測試設置公開爲命令行標誌,只能經過配置文件設置它們。關於這個有一個開放的bug和一個待定的PR。
Viper支持獲得了加強。與供應商支持同樣,它是徹底可選的。它經過導入viperconfig包被拉入e2e.test二進制文件,並在解析正常的命令行標誌後調用它。這已經實現,以便當標誌出如今Viper配置文件中時,也能夠設置全部能夠經過命令行標誌設置的變量。例如,Kubernetes v1.13 e2e.test二進制文件接受--viper-config=/tmp/my-config.yaml,該文件將my.test.parameter設置爲具備此內容的值:my: test: parameter: value
在較舊的Kubernetes版本中,該選項只能從當前目錄加載文件,後綴必須省略,實際上只能經過這種方式設置幾個參數。請注意Viper的一個限制仍然存在:它經過匹配已知標誌的配置文件條目,而不會發出有關未知配置文件條目的警告,從而不會檢測到錯別字。Kubernetes的更好的配置文件解析器仍在開發中。
在Kubernetes 1.12中,有一些支持從.yaml文件加載單個項目,可是而後建立該項目必須經過手寫代碼完成。如今,框架提供新方法加載具備多個項目的.yaml文件、修補這些項目(例如,設置爲當前測試建立的命名空間)以及建立它們。這目前用於爲每一個測試從新部署CSI驅動程序,這些驅動程序來自徹底相同的.yaml文件,這些文件也用於經過kubectl進行部署。若是CSI驅動程序支持以不一樣的名稱運行,則測試徹底獨立而且能夠並行運行。
可是,從新部署驅動程序會下降測試執行速度,而且不會涵蓋針對驅動程序的併發操做。更現實的測試場景是在啓動測試集羣時部署驅動程序一次,而後針對該部署運行全部測試。最終,Kubernetes E2E測試將轉移到該模型,一旦更清楚如何擴展測試集羣的啓動,包括安裝CSI驅動程序等其餘實體。
可以使用Kubernetes以外的框架能夠構建自定義測試套件。可是沒有測試的測試套件仍然沒用。一些現有的測試,特別是用於存儲的測試,能夠應用於樹外組件。感謝Masaki Kimura所作的工做,Kubernetes 1.13中的存儲測試被定義爲能夠針對不一樣的驅動程序屢次實例化它們。
但歷史有重複的習慣。與供應商程序同樣,定義這些測試的程序包也提取了全部樹內存儲後端的驅動程序定義,這反過來又拉取了比所需更多的附加程序包。這在Kubernetes 1.14進行了修復。
某些存儲測試依賴於羣集的功能(如在支持XFS的主機上運行)或驅動程序(如支持塊卷)。在測試運行時檢查這些條件,致使在不滿意時跳過測試。好的是這記錄解釋了爲何測試沒有運行。
開始測試很慢,特別是當它必須首先部署CSI驅動程序時,在其餘狀況下也差很少。在快速集羣上測量爲測試建立命名空間的時間爲5秒,而且會產生大量噪聲測試輸出。原本能夠解決這個問題,經過跳過不支持的測試的定義,而後報告爲何測試甚至不是測試套件的一部分變得棘手。這種方法已不被考慮,而是採用從新組織存儲測試套件的方式,以便在進行更昂貴的測試設置步驟以前首先檢查條件。
一樣的PR還將測試重寫,接近傳統的Ginkgo測試,測試用例及其局部變量在一個函數中。
構建自定義E2E測試套件仍然是至關多的工做。將在Kubernetes 1.14測試檔案中分發的e2e.test二進制文件將可以測試已安裝的存儲驅動程序,而無需重建測試套件。有關詳細說明,請參閱本自述文件。
第一步是設置定義測試套件的必要樣板代碼。在Kubernetes E2E中,這是在e2e.go和e2e_test.go文件中完成的。它也能夠在e2e_test.go文件中完成。Kubernetes在e2e_test.go中導入全部各類供應商程序、樹內測試、Viper配置支持和bindata文件。e2e.go控制實際執行,包括一些集羣準備和指標收集。
一個更簡單的起點是來自PMEM-CSI的e2e_[test].go文件。它不使用任何供應商程序,沒有Viper,沒有bindata,只導入存儲測試。
與PMEM-CSI同樣,OIM會丟棄全部額外功能,但有點複雜,由於它將自定義集羣啓動直接集成到測試套件中,在這種狀況下很是有用,由於一些額外的組件必須在主機端運行。經過直接在E2E二進制文件中運行它們,使用dlv進行交互式調試變得更加容易。
這兩個CSI驅動程序都遵循Kubernetes示例,並使用test/e2e目錄做爲其測試套件,但也可使用任何其餘目錄和其餘文件名。
測試由導入測試套件的包定義。E2E測試惟一特有的是,它們使用framework.NewDefaultFramework實例化一個framework.Framework指針(一般稱爲f)。此變量在每一個測試的BeforeEach中從新初始化,並在AfterEach中釋放。它在運行時有一個f.ClientSet和f.Namespace(而且只在運行時!),能夠由測試使用。
PMEM-CSI存儲測試導Kubernetes存儲測試套件,併爲必須已安裝在測試集羣中的PMEM-CSI驅動程序設置一個供應測試實例。存儲測試套件更改存儲類以使用不一樣的文件系統類型運行測試。因爲此要求,存儲類是從.yaml文件建立的。
解釋框架中可用的全部各類實用方法超出了本博文的範圍。閱讀現有測試和框架的源代碼是一個很好的入門方法。
即便消除了許多沒必要要的依賴關係,提供Kubernetes代碼仍然不是一件容易的事。k8s.io/kubernetes並不意味着包含在其餘項目中,也沒有以dep等工具理解的方式定義其依賴關係。其餘k8s.io包應包含在內,但不遵循語義版本控制或不標記任何版本(k8s.io/kube-openapi,k8s.io/utils)。
PMEM-CSI使用dep。它的Gopkg.toml文件是一個很好的起點。它啓用了修剪(默認狀況下未在dep中啓用)並將某些項目鎖定到與所使用的Kubernetes版本兼容的版本上。當dep沒有選擇兼容的版本時,檢查Kubernetes的Godeps.json有助於肯定哪一個版本多是正確的版本。
go test ./test/e2e -args -help是測試測試套件編譯的最快方法。
一旦編譯完成而且已經設置了集羣,go test -timeout=0 -v ./test/e2e -ginkgo.v命令將運行全部測試。要並行運行測試,請使用ginkgo -p ./test/e2e命令。
Kubernetes E2E框架由測試SIG的testing-commons子項目全部。請參閱該頁面以獲取聯繫信息。
有各類任務,包括但不限於:
特別感謝本文的審閱者:
KubeCon + CloudNativeCon + Open Source Summit大會日期:
KubeCon + CloudNativeCon + Open Source Summit贊助方案
KubeCon + CloudNativeCon + Open Source Summit多元化獎學金現正接受申請
KubeCon + CloudNativeCon和Open Source Summit即將首次合體落地中國
KubeCon + CloudNativeCon + Open Source Summit購票窗口,當即購票!
CNCF邀請你加入最終用戶社區