資深專家深度剖析Kubernetes API Server第3章(共3章)

在本系列的前兩部分中我們介紹了API Server的總體流程鸿吆,以及API對象如何存儲到etcd中。在本文中我們將探討如何擴(kuò)展API資源争涌。

在一開始的時候,擴(kuò)展API資源的唯一方法是擴(kuò)展相關(guān)API源代碼蛙奖,集成為你所需的資源×么叮或者外永,推動一個全新的類型為新的核心對象API合入社區(qū)代碼。但是拧咳,這樣就會導(dǎo)致核心API資源類型的不斷增加伯顶,直至API過載。為了避免這種API資源的無限制擴(kuò)展骆膝,在Kubernetes中提供兩種擴(kuò)展核心API的方法:

1.使用自定義資源定義(CRDs)祭衩,最開始的時候被稱為第三方資源(TPRs)。通過CRD你能夠簡單而靈活的方式定義自己的資源對象類型阅签,并讓API server處理整個生命周期掐暮。

2.使用與主API Servers?并行運行的用戶API?Servers(UAS)。這種方式政钟,可能更多的設(shè)計代碼開發(fā)路克,可能需要你投入較多的時間及精力。當(dāng)然养交,這種方式也能夠讓你對API資源有更細(xì)致精算,全面的了解。

在本文中碎连,我們主要對CRD相關(guān)定義以及使用進(jìn)行探討灰羽。

CRDs的聲明及創(chuàng)建

在本系列文章第一部分所提到過的,每個API資源根據(jù)Group群組分類鱼辙,每個對象都有一個對應(yīng)的版本號與HTTP路徑相關(guān)聯(lián)×溃現(xiàn)在如果想要實現(xiàn)一個CRD,首先需要的是就是命名一個新的API Group群組倒戏,這個API群組不能與已經(jīng)存在的群組重復(fù)怠噪。在你自己新建的API群組中,你可以擁有任意數(shù)量的資源杜跷,并且它們可以與其他群組中的資源具有相同的名稱舰绘。下面我們來列舉一個實際的例子:

在之前我們有介紹過,每個版本的由API群組管理的Kubernetes資源是跟HTTP路徑相關(guān)的葱椭。CRD類似于面向?qū)ο缶幊讨幸粋€類的定義,而實際使用的CR可以看做為它的一組實例口四。首先我們對例子中的一些字段作說明孵运,第一行中的CRD?apiVersion在kube-apiserver 1.7?之后都是這樣定義的。從第5行之后我們定義了spec?的相關(guān)字段蔓彩。在第6行spec.group是定義了你創(chuàng)建的CRD的API群組(在本例子中定義為了example.com)治笨。第7行定義了CRD對象的版本驳概。每個資源只有一個固定版本,但在API群組中還是能有多個不同版本的資源旷赖。第8行的spec.names有兩個必填項:kind顺又,按照慣例第一個字母大寫,plural等孵,按照慣例全為小寫稚照,這個字段與最終生成的HTTP路徑相關(guān),比如在本例子中俯萌,最終的HTTP路徑為https://

上面的kind主要是用來描述對象的類型果录,而resource?資源是與HTTP路徑相關(guān)的。大多數(shù)情況下這兩個是匹配的咐熙;但是在某些特定情況下在相同的API?HTTP路徑下可能返回不通的kind(比如Status?錯誤對象會返回另一種kind)弱恒。

值得注意的是resource?資源(在本例中是databases)和group群組(本例中是example.com)必須與metadata.name?字段匹配(本例為第四行databases.example.com)。

現(xiàn)在我們根據(jù)上面的YAML文件來創(chuàng)建一個CRD:

$ kubectl create -f databases-crd.yaml

customresourcedefinition "databases.example.com" created

由于這個創(chuàng)建過程是異步進(jìn)行的棋恼,所以你必須檢查一下你創(chuàng)建的CRD的狀態(tài)返弹,確認(rèn)你創(chuàng)建的CRD沒有與其它資源沖突,并且API Server已經(jīng)調(diào)用相關(guān)處理函數(shù)完成創(chuàng)建爪飘。你可以在腳本或代碼中通過輪詢完成這個過程义起。最后我們能得到以下狀態(tài):

$ kubectl get crd databases.example.com -o yaml

apiVersion: apiextensions.k8s.io/v1beta1

kind: CustomResourceDefinition

metadata:

??creationTimestamp: 2017-08-09T09:21:43Z

??name: databases.example.com

??resourceVersion: "792"

??selfLink: /apis/apiextensions.k8s.io/v1beta1/customresourcedefinitions/databases.example.com

??uid: 28c94a05-7ce4-11e7-888c-42010a9a0fd5

spec:

??group: example.com

??names:

????kind: Database

????listKind: DatabaseList

????plural: databases

????singular: database

??scope: Namespaced

??version: v1

status:

??acceptedNames:

????kind: Database

????listKind: DatabaseList

????plural: databases

????singular: database

??conditions:

??- lastTransitionTime: null

????message: no conflicts found

????reason: NoConflicts

????status: "True"

????type: NamesAccepted

??- lastTransitionTime: 2017-08-09T09:21:43Z

????message: the initial names have been accepted

????reason: InitialNamesAccepted

????status: "True"

????type: Established

以上,我們可以看到通過kubectl可以看到我們之前創(chuàng)建的CRD悦施,并且顯示出了CRD的一些狀態(tài)信息并扇。

CRDs的使用

在通過kubectl proxy將Kubernetes API開啟本地代理后,查看我們剛才創(chuàng)建的CRD:

$ http 127.0.0.1:8001/apis/example.com

HTTP/1.1 200 OK

Content-Length: 223

Content-Type: application/json

Date: Wed, 09 Aug 2017 09:25:44 GMT


{

????"apiVersion": "v1",

????"kind": "APIGroup",

????"name": "example.com",

????"preferredVersion": {

????????"groupVersion": "example.com/v1",

????????"version": "v1"

????},

????"serverAddressByClientCIDRs": null,

????"versions": [

????????{

????????????"groupVersion": "example.com/v1",

????????????"version": "v1"

????????}

????]

}

請注意抡诞,在默認(rèn)情況下十分鐘內(nèi)穷蛹,kubectl是查看存儲在~/.kube/cache/discovery目錄的緩存。所以昼汗,可能會需要10分鐘后你才能看到你新創(chuàng)建的CRD資源肴熏。但是,當(dāng)沒有緩存時顷窒,kubectl發(fā)現(xiàn)不了所需的資源時蛙吏,那么會重新緩存它。

接下來鞋吉,我們來看一個CRD實例:

$ cat wordpress-database.yaml

apiVersion: example.com/v1

kind: ??????Database

metadata:

??name: ????wordpress

spec:

??user: ????wp

??password: secret

??encoding: unicode


$ kubectl create -f wordpress-databases.yaml

database "wordpress" created


$ kubectl get databases.example.com

NAME ???????KIND

wordpress ??Database.v1.example.com

想要通過API來監(jiān)控資源的創(chuàng)建與更新鸦做,你可以通過對某個resourceVersion(我們通過curl來實例對指定版本的database做監(jiān)控)之后的修改做監(jiān)控watch。


$ http 127.0.0.1:8001/apis/example.com/v1/namespaces/default/databases

HTTP/1.1 200 OK

Content-Length: 593

Content-Type: application/json

Date: Wed, 09 Aug 2017 09:38:49 GMT


{

????"apiVersion": "example.com/v1",

????"items": [

????????{

????????????"apiVersion": "example.com/v1",

????????????"kind": "Database",

????????????"metadata": {

????????????????"clusterName": "",

????????????????"creationTimestamp": "2017-08-09T09:38:30Z",

????????????????"deletionGracePeriodSeconds": null,

????????????????"deletionTimestamp": null,

????????????????"name": "wordpress",

????????????????"namespace": "default",

????????????????"resourceVersion": "2154",

????????????????"selfLink": "/apis/example.com/v1/namespaces/default/databases/wordpress",

????????????????"uid": "8101a7af-7ce6-11e7-888c-42010a9a0fd5"

????????????},

????????????"spec": {

????????????????"encoding": "unicode",

????????????????"password": "secret",

????????????????"user": "wp"

????????????}

????????}

????],

????"kind": "DatabaseList",

????"metadata": {

????????"resourceVersion": "2179",

????????"selfLink": "/apis/example.com/v1/namespaces/default/databases"

????}

}

我們可以對/apis/example.com/v1/namespaces/default/databases/wordpressCRD的HTTP路徑通過curl命令對的"resourceVersion": "2154"進(jìn)行監(jiān)控watch:

$ curl -f 127.0.0.1:8001/apis/example.com/v1/namespaces/default/databases?watch=true&resourceVersion=2154

現(xiàn)在我們新開一個shell對話窗口谓着,刪除wordpress?CRD資源泼诱,我們可以查看剛才的監(jiān)控watch窗口是否接收到了這個消息:

$ kubectl delete databases.example.com/wordpress

請注意:我們能夠使用kubectl delete database wordpress刪除CRD資源,是因為之前在Kubernetes沒有定義有database?資源赊锚。此外治筒,database是我們CRD中的spec.name.singular字段屉栓,從英語語法派生而來。

我們可以看到之前監(jiān)控watch CRD databases從API Server處返回的更新狀態(tài):

{"type":"DELETED","object":{"apiVersion":"example.com/v1","kind":"Database","metadata":{"clusterName":"","creationTimestamp":"2017-0[0/515]

:38:30Z","deletionGracePeriodSeconds":null,"deletionTimestamp":null,"name":"wordpress","namespace":"default","resourceVersion":"2154","selfLink":"/apis/example.com/v1/namespaces/

default/databases/wordpress","uid":"8101a7af-7ce6-11e7-888c-42010a9a0fd5"},"spec":{"encoding":"unicode","password":"secret","user":"wp"}}}

上述shell會話的運行及輸出結(jié)果如下圖所示:

最后耸袜,讓我們看一下CRD database?的各個數(shù)據(jù)是如何存儲在etcd中的友多。下面是我們直接通過HTTP API進(jìn)入etcd訪問得到的數(shù)據(jù):

$ curl -s localhost:2379/v2/keys/registry/example.com/databases/default | jq .

{

??"action": "get",

??"node": {

????"key": "/registry/example.com/databases/default",

????"dir": true,

????"nodes": [

??????{

????????"key": "/registry/example.com/databases/default/wordpress",

????????"value": "{\"apiVersion\":\"example.com/v1\",\"kind\":\"Database\",\"metadata\":{\"clusterName\":\"\",\"creationTimestamp\":\"2017-08-09T14:53:40Z\",\"deletionGracePeriodSeconds\":null,\"deletionTimestamp\":null,\"name\":\"wordpress\",\"namespace\":\"default\",\"selfLink\":\"\",\"uid\":\"8837f788-7d12-11e7-9d28-080027390640\"},\"spec\":{\"encoding\":\"unicode\",\"password\":\"secret\",\"user\":\"wp\"}}\n",

????????"modifiedIndex": 670,

????????"createdIndex": 670

??????}

????],

????"modifiedIndex": 670,

????"createdIndex": 670

??}

}

從上面可以看到,CRD數(shù)據(jù)在etcd中最終以一個未解析的的狀態(tài)存在〉炭颍現(xiàn)在將CRD刪除域滥,所有的CRD實例也會跟著刪除,這是一個級聯(lián)刪除操作胰锌。

目前CRDs的使用現(xiàn)狀骗绕,局限及將來的展望

CRDs的發(fā)展現(xiàn)狀如下所示:

1.在Kubernetes 1.7版本中CRDs開始取代ThirdPartyResources?(TPRs)?,并且TPRs?將會在Kubernetes 1.8被刪除资昧。

2.將TPRs遷移到CRDs實例可以參考文檔migration酬土。

3.支持一個CRD中只有單個version版本,當(dāng)然格带,一個群組中可能有多個version版本撤缴。

4.CRDs提供一個API方案,在用戶角度看它與Kubernetes原生的API資源基本沒有區(qū)別

5.CRDs是多版本多分支穩(wěn)定的基礎(chǔ)叽唱。關(guān)于CRD資源的JSON-Schema的格式有效性校驗可以參考文檔CRD validation proposal屈呕。相關(guān)資源回收可以參考文檔Garbage collection。

接下去我們來看一下一些CRDs的局限:

1.CRD不提供版本轉(zhuǎn)換功能棺亭,也就是說虎眨,每個CRD只能有一個版本(預(yù)計不會在近期或中期內(nèi)看到支持CRD版本轉(zhuǎn)換)。

2.在Kubernetes1.7當(dāng)中镶摘,目前并沒有對于CRD的相關(guān)校驗validation嗽桩。

3.沒有快速,實時的準(zhǔn)入(admission)機制(但是可以支持webhooks?形式的初始化及準(zhǔn)入)凄敢。

4.在Kubernetes1.7中你不能定義子資源(sub-resources)碌冶,比如scale或者status,不過目前有在這方面proposal的討論涝缝。

5.CRD目前不支持默認(rèn)值配置扑庞,即不支持為特定的字段配默認(rèn)值(在Kubernetes1.7后續(xù)的版本中可能會支持)。

為了解決上述的問題拒逮,并且靈活的擴(kuò)展Kubernetes罐氨,你可以運行一個與主API Server并行的用戶API Servers。我們將在本博文的以后部分中詳細(xì)介紹如何編寫UAS滩援,并編寫一個custom controller完整使用CRD?栅隐。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子约啊,更是在濱河造成了極大的恐慌,老刑警劉巖佣赖,帶你破解...
    沈念sama閱讀 217,277評論 6 503
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件恰矩,死亡現(xiàn)場離奇詭異,居然都是意外死亡憎蛤,警方通過查閱死者的電腦和手機外傅,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,689評論 3 393
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來俩檬,“玉大人萎胰,你說我怎么就攤上這事∨锪桑” “怎么了技竟?”我有些...
    開封第一講書人閱讀 163,624評論 0 353
  • 文/不壞的土叔 我叫張陵,是天一觀的道長屈藐。 經(jīng)常有香客問我榔组,道長,這世上最難降的妖魔是什么联逻? 我笑而不...
    開封第一講書人閱讀 58,356評論 1 293
  • 正文 為了忘掉前任搓扯,我火速辦了婚禮,結(jié)果婚禮上包归,老公的妹妹穿的比我還像新娘锨推。我一直安慰自己,他們只是感情好公壤,可當(dāng)我...
    茶點故事閱讀 67,402評論 6 392
  • 文/花漫 我一把揭開白布换可。 她就那樣靜靜地躺著,像睡著了一般境钟。 火紅的嫁衣襯著肌膚如雪锦担。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,292評論 1 301
  • 那天慨削,我揣著相機與錄音洞渔,去河邊找鬼。 笑死缚态,一個胖子當(dāng)著我的面吹牛磁椒,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播玫芦,決...
    沈念sama閱讀 40,135評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼浆熔,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了桥帆?” 一聲冷哼從身側(cè)響起医增,我...
    開封第一講書人閱讀 38,992評論 0 275
  • 序言:老撾萬榮一對情侶失蹤慎皱,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后叶骨,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體茫多,經(jīng)...
    沈念sama閱讀 45,429評論 1 314
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,636評論 3 334
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片颂碧。...
    茶點故事閱讀 39,785評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡璧函,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 35,492評論 5 345
  • 正文 年R本政府宣布斑唬,位于F島的核電站,受9級特大地震影響纸泄,放射性物質(zhì)發(fā)生泄漏赖钞。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,092評論 3 328
  • 文/蒙蒙 一聘裁、第九天 我趴在偏房一處隱蔽的房頂上張望雪营。 院中可真熱鬧,春花似錦衡便、人聲如沸献起。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,723評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽谴餐。三九已至,卻和暖如春呆抑,著一層夾襖步出監(jiān)牢的瞬間岂嗓,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,858評論 1 269
  • 我被黑心中介騙來泰國打工鹊碍, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留厌殉,地道東北人。 一個月前我還...
    沈念sama閱讀 47,891評論 2 370
  • 正文 我出身青樓侈咕,卻偏偏與公主長得像公罕,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子耀销,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 44,713評論 2 354

推薦閱讀更多精彩內(nèi)容