ZStack中的標籤不只幫助用戶彙集資源,也幫助控制軟件行爲。ZStack有一套完整的規範,用以定義標籤的類別、形式和用法。除了用戶外,插件也能夠建立本身的標籤,以記錄元數據和拓展示有的資源屬性;經過這些手段,標籤能夠幫助插件引入新的特性,而不改變ZStack的數據庫結構,消除了在軟件升級對數據庫遷移的需求。web
動機算法
隨着雲中資源的不斷增加,用戶可能會想要有一種方式,使用人類可讀的標籤,去分組類似的資源。舉個例子,全部Web服務器的虛擬機均可以有一個標籤'web-tier-vm',這樣能夠從UI和CLI把它們做爲一個組來獲取。對於IaaS自己,預先定義的業務邏輯也許歷來都不能知足用戶的需求。以建立虛擬機爲例,默認的選擇目標主機的算法是,從主機池中隨機選擇一個,但用戶可能須要各類各樣的算法來知足它們的使用情景。好比說選擇內存超過8G的主機,選擇擁有SR-IOV硬件的主機,或選擇一個有當前用戶的運行中虛擬機的主機。IaaS軟件幾乎不能爲全部無止境的、不可預知的需求提供單獨的API,必須有一種機制容許基礎API(如APICreateVmInstanceMsg)攜帶額外信息。數據庫
根據各自的業務邏輯,插件能夠選擇是否建立數據庫表。好比,Open vSwitch L2 Network插件,因爲須要建立一種新的類型的資源,可能須要添加一張新表;然而,一個容許主機保留內存的插件可能不須要添加一張新表,而僅需在主機上附加一點數據。若是IaaS軟件沒有爲插件提供一種附加數據,它們將開始創造新的、瑣碎的模式或添加現有模式的列從而修改現有的模式,致使軟件升級時數據庫遷移的難處理的狀況。apache
最後,對於創建在ZStack上的第三方軟件,容許它們將信息存儲到ZStack的數據庫能夠避免數據完整性問題,並使得它們可使用ZStack的所有查詢API(詳見「查詢API」)。編程
問題後端
大多數IaaS軟件都有着標籤的概念。然而,它們並非都爲不一樣場景定義了一個詳盡的標籤規範。例如,一些IaaS使用標籤是爲了用戶聚合資源,一些IaaS是爲了內部業務邏輯。ZStack則爲不一樣場景的標籤的每個層面都精心設計了標籤規範。服務器
標籤系統架構
在ZStack中,標籤本質上是攜帶了少許資源相關信息的字符串。一個標籤一般由如下幾個字段組成:工具
FIELDui |
DESCRIPTION |
uuid |
標籤的UUID |
resourceUuid |
標籤所關聯的資源的UUID |
resourceType |
標籤所關聯的資源的類型 |
Tag |
一個包含了有意義信息的字符串 |
Type |
標籤類型:System 或者 User |
在標籤方面,ZStack和其餘IaaS軟件的本質區別是ZStack將標籤分爲兩類:用戶(User)和系統(System)。
1.用戶標籤
用戶標籤,顧名思義,是用戶爲資源分組而建立的標籤。例如,經過標籤'apache2-http'將安裝了Apache2 HTTP服務器的虛擬機分組,這樣用戶就能夠經過查詢API獲取這些虛擬機,使用標籤'apache2-http'做爲查詢條件便可:
QueryVmInstance __userTag__=apache2-http
備註:詳見「查詢API」
這是最多見的標籤使用方法,一個資源能夠和多個標籤相關聯,而且被不一樣的邏輯組劃分。
用戶標籤也能夠經過和系統的標籤一塊兒使用來控制ZStack的行爲。例如,若是一個用戶標籤SSD
已經在主存儲系統上建立好,那麼一個系統標籤能夠指導ZStack在有用戶標籤SSD的主存儲上去建立VM的根目錄。在這種狀況下,用戶標籤更像是用戶輸入的資源元數據。咱們很快就會看到,插件也可使用系統標籤建立資源元數據。
2.系統標籤
不像用戶標籤能夠被用戶在任意時間、以任意值建立,系統標籤有固定的格式,而且是被ZStack的業務服務和插件提早定義好的,能夠在如下場景被使用:
2.1元數據
插件可使用系統標籤來記錄資源的元數據。例如,主機的數據庫表中沒有列去記錄如hypervisor版本,hypervisor SDK版本這樣的元數據;然而,衍生的主機插件,例如,KVM主機插件,可能須要這些元數據來肯定當前虛擬機管理程序是否有某些特徵;例如,是否能對KVM在線快照是由libvirt和QEMU版本決定的。在ZStack中,當鏈接到後端主機時,KVM主機插件將OS的版本,libvirt版本,QEMU的版本和qemu-img工具的版本做爲系統標籤保存。
QuerySystemTag fields=tag resourceUuid=d07066c4de02404a948772e131139eb4
{
"inventories": [
{
"tag": "capability:liveSnapshot"
},
{
"tag": "qemu-img::version::2.0.0"
},
{
"tag": "os::version::14.04"
},
{
"tag": "libvirt::version::1.2.2"
},
{
"tag": "os::release::trusty"
},
{
"tag": "os::distribution::Ubuntu"
}
],
"success": true
}
2.2資源屬性
插件也可使用系統標籤將新屬性添加到資源中。例如,虛擬機的數據庫模式中沒有列來記錄該使用什麼IP分配算法,何時分配虛擬機網卡。這種額外的屬性能夠用系統標籤實現。插件能夠建立的系統標籤的數量沒有限制,附加的插件能夠利用這點,並避免干擾數據庫模式。
數據庫表和系統標籤:由於數據庫表和系統標籤均可以定義資源屬性,有時會難以決定屬性是應該爲數據庫模式中的一列,仍是應該爲一個單獨的表中的系統標籤。添加新列來修改一個現有的數據庫模式,一般須要進行數據庫遷移,這是IaaS軟件升級的一個主要痛點。因此開發者可能更傾向使用系統標籤來表明新屬性。然而,濫用系統標籤是一種錯誤的編程方式。按照ZStack的約定,只應該使用系統標籤形式引入非固有的資源屬性;系統的標籤並不能拯救設計的很爛的數據庫表。例如,若是VM的數據庫表缺失集羣UUID(雖然不會),即便須要進行數據庫遷移也必須補充回來;但爲了私人使用而被用戶建立的插件引入的部門ID應該做爲一個系統標籤實現。這種權衡有時候並不容易,咱們會嚴格控制任何數據庫結構的變化。
2.3元編程
系統標籤也能夠標註資源以影響ZStack的執行流,它在某種程度上相似於Metaprogramming(https://en.wikipedia.org/wiki/Metaprogramming)。
例如,管理員能夠在KVM主機上建立一個系統標籤reservedMemory::1G,提示ZStack主機分配器從主機的可用內存保留1G內存;若是管理員改變心意,他能夠經過刪除標籤來回收這1G內存。有不少相似的系統標籤。
例如,在用戶標籤這一節中,咱們提到了同時使用用戶標籤SSD和系統標籤來爲VM的根雲盤指定主存儲。系統標籤叫primaryStorage::allocator::userTag::{tag}::required,若是一個虛擬機實例規格上有primaryStorage::allocator::userTag::SSD::required,從該虛擬機實例規格上建立的虛擬機根雲盤的任務,將只被分配到擁有用戶標籤爲SSD的主存儲上。有許多稱之爲解釋點interpreting points的代碼,將在執行過程當中尋找特定的系統標籤,能夠改變代碼的默認行爲。
2.4第三方軟件集成
創建在ZStack上的第三方軟件可使用系統標籤在ZStack的數據庫中存儲和資源關聯的信息,這能有效避免第三方軟件數據庫和ZStack數據庫的數據不一致性。
例如,一個私有軟件可能須要記錄虛擬機的部門ID來審計每一個部門IT資源的使用狀況,這個功能一般由一個私有的數據庫完成,並迫使私有軟件跟蹤虛擬機的生命週期,由於它須要在數據庫建立或銷燬時,去更新本身的數據庫。不然,數據將不會正確反映真實狀況。
有了系統標籤的幫助,私有軟件可使用系統標籤,例如audit::departmentId::{id}將信息存儲在ZStack的數據庫,將管理部門ID生命週期的責任轉移給ZStack。當一個虛擬機被銷燬,它的部門ID(例如audit::departmentId::1)將在刪除該虛擬機記錄的數據庫事務中被自動刪除。此外,私有軟件能夠用它們的部門ID調用常規查詢API檢索虛擬機:
QueryVmInstance fields=uuid __sysTag__=audit::departmentId::1
注:在ZStack版本(0.6)中,咱們還沒開放容許定義任意系統標籤的接口,全部的系統標籤都是預先定義的。咱們計劃在下一個版本中開放這個接口,用戶定義的系統標籤能夠在建立的時候添加一些系統容許的前綴,例如,3rd::
。
和其餘組件的關係
標籤系統是ZStack核心組件之一;它不只具備單獨的API和服務,並且還和其餘核心組件無縫集成。用戶能夠在資源建立時或在資源建立後建立標籤。ZStack全部創造型的API支持兩個固有參數:userTags
和systemTags,經過它們傳遞的標籤將隨着資源一塊兒建立。例如:
CreateVmInstance name=testTag systemTags=hostname::web-server-1 l3NetworkUuids=6572ce44c3f6422d8063b0fb262cbc62
instanceOfferingUuid=04b5419ca3134885be90a48e372d3895 imageUuid=f1205825ec405cd3f2d259730d47d1d8
若是資源已經存在,用戶可使用標籤API來建立或刪除標籤:
CreateUserTag resourceType=VmInstanceVO resourceUuid=613af3fe005914c1643a15c36fd578c6 tag=web
DeleteTag uuid=596070a6276746edbf0f54ef721f654e
資源被刪除時,與資源相關聯的標籤將被自動刪除。
資源能夠經過使用兩個特殊的查詢條件進行查詢:__userTag__
and__systemTag__標籤:
QueryVmInstance __userTag__=web zoneUuid=04b5419ca3134885be90a48e372d3895
QueryHost __systemTag__=capability:liveSnapshot
也有查詢API專門用於分類:
QueryUserTag resourceUuid=0cd1ef8c9b9e0ba82e0cc9cc17226a26 tag~=web-server-%
QuerySystemTag resourceUuid=50fcc61947f7494db69436ebbbefda34
總結
在這篇文章中,咱們展現了ZStack的標籤系統。經過這個系統,用戶、插件和第三方軟件能夠經過各類各樣的方式使用標籤,而不用改變代碼和數據庫表結構。這是又一個基本點,激發了一種潛力,使得ZStack在快速進化爲一個成熟的、完整的雲計算解決方案的同時,又能保持核心架構強壯穩定。