溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶(hù)服務(wù)條款》

結(jié)合Kubernetes解讀微服務(wù)的12要素

發(fā)布時(shí)間:2020-08-06 20:24:41 來(lái)源:ITPUB博客 閱讀:157 作者:EAWorld 欄目:云計(jì)算

結(jié)合Kubernetes解讀微服務(wù)的12要素

本文由公眾號(hào)EAWorld翻譯發(fā)表,轉(zhuǎn)載需注明出處。

作者:Michael D. Elder 

譯者:白小白 

原題:Kubernetes & 12-factor apps 

原文:http://t.cn/EoBns1o

關(guān)于12原則的更多內(nèi)容,可以進(jìn)一步閱讀《全網(wǎng)首發(fā):逐一解讀云原生應(yīng)用開(kāi)發(fā)“12-Factors”》

如果你在使用容器來(lái)構(gòu)建應(yīng)用的話,一定聽(tīng)過(guò)什么是“12要素原則”?!?2要素”為開(kāi)發(fā)微服務(wù)提供了一組明確的指引。人們相信只要遵循這些原則,就可以更容易的運(yùn)行、擴(kuò)展和部署應(yīng)用與服務(wù)。

在講述“12要素原則”的時(shí)候,筆者習(xí)慣于將這些原則按普遍的場(chǎng)景進(jìn)行分組。對(duì)我來(lái)說(shuō),12要素最終是關(guān)于如何編碼、部署和運(yùn)營(yíng)的原則。這些是軟件交付生命周期里最常見(jiàn)的場(chǎng)景,為多數(shù)開(kāi)發(fā)者和DevOps整合團(tuán)隊(duì)所熟知。

那么在使用Kubernetes的過(guò)程中,如何在構(gòu)建微服務(wù)的時(shí)候應(yīng)用12要素原則呢?事實(shí)上,12要素原則對(duì)Kubernetes的發(fā)展和演進(jìn)過(guò)程產(chǎn)生了深遠(yuǎn)的影響。接下來(lái)的內(nèi)容,我將逐一分析,Kubernetes的容器編排模型是如何對(duì)各組12要素原則進(jìn)行直接的支持的。


一、與編碼有關(guān)的要素


關(guān)于源碼管理,需要考慮的因素是基準(zhǔn)代碼、構(gòu)建和部署生命周期以及最終如何維持生產(chǎn)環(huán)境和開(kāi)發(fā)環(huán)境的一致性。

結(jié)合Kubernetes解讀微服務(wù)的12要素

一個(gè)基本的軟件交付周期圖

Source control all the things

源碼控制一切


要素一:一份基準(zhǔn)代碼,多份部署


Kubernetes中大量的使用聲明式結(jié)構(gòu)。應(yīng)用的全部信息都經(jīng)由YAML或者JSON實(shí)現(xiàn)基于文本的表達(dá)。容器本身則被描述為Dockerfile這樣的源碼格式,在構(gòu)建的過(guò)程中,可以反復(fù)的將文本格式的Dockerfile轉(zhuǎn)為容器鏡像。因?yàn)閺溺R像到容器部署環(huán)節(jié)都被封裝為文本形態(tài),可以很容易的實(shí)現(xiàn)對(duì)所有事物的源碼控制,而最常用的工具是Git。

在Kubernetes中,很多東西可以用聲明的方式來(lái)進(jìn)行描述?!禟ubernetes in the Enterprise》這本書(shū)中記錄了很多完整的示例,相關(guān)的代碼都在Github上。

如果應(yīng)用需要跨越開(kāi)發(fā)、用戶(hù)驗(yàn)收、生產(chǎn)等不同的環(huán)境來(lái)運(yùn)行的話,最常用的方法是使用GitOps交付模型來(lái)實(shí)現(xiàn)多分支的管理,來(lái)區(qū)分環(huán)境之間的差異。


要素五:嚴(yán)格分離構(gòu)建、發(fā)布和運(yùn)行


如標(biāo)題所述,為了遵循這一原則,構(gòu)建、發(fā)布和運(yùn)行環(huán)境要實(shí)現(xiàn)嚴(yán)格的分離。最典型的實(shí)現(xiàn)方式是工件管理:一旦代碼提交,構(gòu)建隨之開(kāi)始,而后生成容器鏡像并發(fā)布到鏡像庫(kù)。如果使用了Helm(Kubernetes的包管理器,類(lèi)似Ubuntu的apt-get),Kubernetes應(yīng)用會(huì)同時(shí)被打包和發(fā)布到Helm庫(kù)。通過(guò)對(duì)二進(jìn)制文件或者鏡像文件的重新構(gòu)建,所有這些發(fā)布物可以在不同的環(huán)境中進(jìn)行復(fù)用和部署,并且可以保證不會(huì)這個(gè)過(guò)程中引入任何未知的變更。


要素十:開(kāi)發(fā)環(huán)境與生產(chǎn)環(huán)境等價(jià)


遵循這一等價(jià)原則,可以避免下面這種惱人的對(duì)話,“在我那好好的,怎么在你那就不行了呢”。容器(或者莫不如說(shuō)是Kubernetes)讓?xiě)?yīng)用的交付和運(yùn)行依賴(lài)實(shí)現(xiàn)了標(biāo)準(zhǔn)化,這意味著可以將任何事物以相同的方式部署到任何地方。因此,如果在生產(chǎn)環(huán)境使用了高可用的MySQL配置,就可以在開(kāi)發(fā)集群中部署相同的架構(gòu)。通過(guò)在前期的開(kāi)發(fā)環(huán)境中建立生產(chǎn)環(huán)境的等價(jià)架構(gòu),通??梢员苊庖恍┎豢深A(yù)見(jiàn)的差異,而這些差異可能對(duì)于應(yīng)用的正常運(yùn)行(甚至是失?。┊a(chǎn)生至關(guān)重要的影響。


二、與部署有關(guān)的要素


構(gòu)建的價(jià)值僅在成功部署時(shí)才能得以體現(xiàn)。在12要素中,有很大比例的原則描述了相關(guān)的最佳實(shí)踐,包括微服務(wù)該如何部署,如何處理依賴(lài),以及如何解析其他微服務(wù)的細(xì)節(jié)。

微服務(wù)的可靠性取決于其最不可靠的依賴(lài)。

如何理解這句話呢,答案就在下面的這張Kubernetes架構(gòu)圖中:

結(jié)合Kubernetes解讀微服務(wù)的12要素

Pod以及相關(guān)的Kubernetes對(duì)象


要素二:顯式聲明依賴(lài)關(guān)系


對(duì)于上面那句話的理解,首先需要考慮依賴(lài)關(guān)系的構(gòu)建,12要素中關(guān)于依賴(lài)關(guān)系的闡述參照了構(gòu)建管理的原則。然而我仍舊傾向于將依賴(lài)要素放在與部署有關(guān)的分組中,因?yàn)閷?duì)于其他API或者數(shù)據(jù)存儲(chǔ)的依賴(lài)將對(duì)微服務(wù)的可靠性產(chǎn)生廣泛的影響。Kubernetes引入了readiness和liveness的探針機(jī)制,可以執(zhí)行運(yùn)行期的依賴(lài)檢查。readiness探針可以驗(yàn)證在某個(gè)時(shí)間點(diǎn)或者時(shí)間段,是否存在健康的后端service用以響應(yīng)請(qǐng)求。而liveness探針可以確認(rèn)service本身的健康性。在給定的時(shí)間窗口內(nèi),如果兩個(gè)指標(biāo)之一觸發(fā)了失敗的臨界值,Pod將被重啟。

譯注:

此處作者對(duì)于liveness和readiness的理解是有誤解的。liveness指標(biāo)實(shí)際上標(biāo)志了容器可以正常工作的底線,只有在超過(guò)這一底線時(shí),容器才會(huì)被重啟。而readiness指標(biāo)則標(biāo)志了容器可以正常工作的上線,不滿足readiness的要求,容器并不會(huì)被重啟,而僅會(huì)標(biāo)志為“非正常”狀態(tài)。舉例來(lái)說(shuō),Tomcat的應(yīng)用啟動(dòng)成功后就是liveness,但只有在spring容器初始化、數(shù)據(jù)庫(kù)連接等相關(guān)過(guò)程完成后,才是readiness。

更多內(nèi)容參見(jiàn)http://t.cn/EorvPAh

建議花時(shí)間閱讀《Release It!》這本書(shū),領(lǐng)略書(shū)中的智慧,以及使用書(shū)中描述的架構(gòu)模式(熔斷器,F(xiàn)ail Fast,Timeouts等)來(lái)改進(jìn)應(yīng)用程序的可靠性。

在環(huán)境中存儲(chǔ)配置

按照這一要素的要求,開(kāi)發(fā)者需要將配置源碼存儲(chǔ)在進(jìn)程的環(huán)境變量表中,如ENV VARs。通過(guò)配置與代碼的分離,微服務(wù)將徹底的獨(dú)立于環(huán)境,可以不進(jìn)行任何源碼級(jí)的變更就移植到另一環(huán)境。Kubernetes提供了ConfigMaps和Secrets對(duì)象用于配置源碼的管理(事實(shí)上Secrets在未經(jīng)額外的加密的情況下不應(yīng)納入源碼管理)。容器可以在運(yùn)行時(shí)獲取配置的細(xì)節(jié)。將配置信息存儲(chǔ)為環(huán)境變量有利于系統(tǒng)的擴(kuò)展以及處理日漸增長(zhǎng)的服務(wù)需求。


要素六:以無(wú)狀態(tài)的進(jìn)程運(yùn)行應(yīng)用


在Kubernetes中,容器鏡像作為Pod中的進(jìn)程運(yùn)行。來(lái)自12要素的觀察發(fā)現(xiàn),Linux內(nèi)核已經(jīng)通過(guò)圍繞進(jìn)程模型的資源共享實(shí)現(xiàn)了大量的優(yōu)化。Kubernetes或者說(shuō)容器只是提供了一個(gè)界面來(lái)實(shí)現(xiàn)更好的隔離,讓處于同一主機(jī)的容器進(jìn)程可以并行不悖。進(jìn)程模型的應(yīng)用使得系統(tǒng)擴(kuò)展和故障恢復(fù)的管理變得更加容易。一般來(lái)說(shuō),進(jìn)程應(yīng)該是無(wú)狀態(tài)的,這樣才能以副本的方式實(shí)現(xiàn)工作負(fù)載的橫向擴(kuò)展。但在Kubernetes中,也有諸如數(shù)據(jù)庫(kù)/緩存這類(lèi)有狀態(tài)的工作負(fù)載。

應(yīng)該使用持久的數(shù)據(jù)存儲(chǔ)來(lái)按需保存應(yīng)用的狀態(tài),應(yīng)用進(jìn)程的所有實(shí)例都可以通過(guò)配置文件來(lái)發(fā)現(xiàn)這些存儲(chǔ)。在基于Kubernetes的應(yīng)用中,Pod的多個(gè)副本同時(shí)運(yùn)行,請(qǐng)求可能被路由到任何一個(gè)副本,因此,微服務(wù)不可能期待粘滯會(huì)話(即讓用戶(hù)在一次會(huì)話周期內(nèi)的所有請(qǐng)求始終轉(zhuǎn)發(fā)到同一個(gè)特定的對(duì)象)。

得益于進(jìn)程模型的機(jī)制,所有的service都可以很容易的通過(guò)創(chuàng)建更多的進(jìn)程實(shí)例來(lái)實(shí)現(xiàn)擴(kuò)展,Kubernetes提供了很多控制器來(lái)完成這項(xiàng)工作,如ReplicaSets, Deployments, StatefulSet, ReplicationController等等。

參見(jiàn)如下代碼片段的第2行至第7行,關(guān)于副本的部分。

結(jié)合Kubernetes解讀微服務(wù)的12要素

watson-conversation.yaml hosted with ? by GitHub

Kubernetes的部署文件列示了所需的副本數(shù)量的聲明(如第7行所示)


要素四:把后端服務(wù)當(dāng)作附加資源


我們通常把網(wǎng)絡(luò)環(huán)境這類(lèi)依賴(lài)定義為“后端服務(wù)”。正確的做法是把這些 上游服務(wù)的生命周期獨(dú)立于微服務(wù)本身的生命周期來(lái)考慮。無(wú)論是后端服務(wù)的附加或者剝離,都不應(yīng)該影響微服務(wù)本身正常響應(yīng)的能力。

舉例來(lái)說(shuō),如果應(yīng)用需要與數(shù)據(jù)庫(kù)進(jìn)行交互,就需要設(shè)定一些連接細(xì)節(jié),來(lái)隔離應(yīng)用與數(shù)據(jù)庫(kù)的交互行為,可以使用動(dòng)態(tài)的服務(wù)發(fā)現(xiàn),或者是使用Kubernetes Secret的Config配置來(lái)實(shí)現(xiàn)。接下來(lái),需要考慮的是網(wǎng)絡(luò)請(qǐng)求是否實(shí)現(xiàn)了容錯(cuò)機(jī)制,以保證即使后端服務(wù)發(fā)生了運(yùn)行時(shí)失敗,也不會(huì)觸發(fā)微服務(wù)的級(jí)聯(lián)失敗(《Release It!》書(shū)中有更詳盡的闡述)。相關(guān)的后端服務(wù)應(yīng)該運(yùn)行在獨(dú)立的容器中,或者集群以外的什么地方。微服務(wù)不應(yīng)該關(guān)注交互的細(xì)節(jié),所有與數(shù)據(jù)庫(kù)的交互行為都通過(guò)API來(lái)完成。


要素七:通過(guò)端口綁定提供服務(wù)


在生產(chǎn)環(huán)境中,多個(gè)微服務(wù)提供了不同的功能,服務(wù)間的通信需要經(jīng)由良好定義的協(xié)議來(lái)達(dá)成。可以使用Kubernetes Service對(duì)象來(lái)聲明和解析集群內(nèi)外相關(guān)服務(wù)的網(wǎng)絡(luò)端點(diǎn)。

在容器出現(xiàn)以前,任何時(shí)候,如果需要部署一個(gè)新的服務(wù)或者更新現(xiàn)有服務(wù)的版本的話,就需要花大量的時(shí)間解決主機(jī)上的端口沖突問(wèn)題。容器的隔離機(jī)制以及Linux內(nèi)核的網(wǎng)絡(luò)命名空間機(jī)制,使得在單一主機(jī)的相同端口上運(yùn)行多個(gè)進(jìn)程或者同一個(gè)微服務(wù)的多個(gè)版本成為可能。從而,Kubernetes的Service對(duì)象就可以向所有主機(jī)暴露微服務(wù)池,并且對(duì)入站請(qǐng)求實(shí)現(xiàn)基本的負(fù)載均衡。

在Kubernetes中,Service對(duì)象是聲明式的,并且會(huì)自動(dòng)完成路由到Pod的相關(guān)請(qǐng)求的負(fù)載均衡工作。

處理對(duì)Pod的相關(guān)請(qǐng)求的負(fù)載均衡的Service聲明示例:

結(jié)合Kubernetes解讀微服務(wù)的12要素

watson-conversation-service.yaml hosted with ? by GitHub


三、與運(yùn)營(yíng)有關(guān)的要素


要素八(并發(fā)),要素九(可處置性),要素十一(日志)和要素十二(任務(wù)管理)與如何簡(jiǎn)化微服務(wù)的運(yùn)營(yíng)相關(guān)。

Kubernetes聚焦于多個(gè)Pod的簡(jiǎn)單部署單元如何按需創(chuàng)建和銷(xiāo)毀,單獨(dú)的Pod本身毫無(wú)價(jià)值。


要素八:通過(guò)進(jìn)程模型進(jìn)行擴(kuò)展


要素六所提到的進(jìn)程模型在并發(fā)機(jī)制的實(shí)現(xiàn)上大放異彩。前文說(shuō)過(guò),Kubernetes可以通過(guò)不同種類(lèi)的生命周期控制器來(lái)實(shí)現(xiàn)無(wú)狀態(tài)應(yīng)用的運(yùn)行時(shí)擴(kuò)展。所需要的副本數(shù)量以聲明式模型定義并可以在運(yùn)行時(shí)變更。同樣,Kubernetes也定義了很多用于管理并發(fā)的生命周期控制器,如ReplicationControllers, ReplicaSets, Deployments, StatefulSets, Jobs和DaemonSets。

下面的動(dòng)畫(huà)展示了副本添加的過(guò)程:

結(jié)合Kubernetes解讀微服務(wù)的12要素


ReplicaSet可以用來(lái)添加更多的Pod。新創(chuàng)建的Pod會(huì)自動(dòng)響應(yīng)來(lái)自Service對(duì)象的入站請(qǐng)求。

基于對(duì)CPU、內(nèi)存等相關(guān)計(jì)算資源以及其他外部指標(biāo)的閾值監(jiān)測(cè),Kubernetes引入了自動(dòng)擴(kuò)展的機(jī)制。Horizontal Pod Autoscaler (HPA) 可以實(shí)現(xiàn)在一個(gè)Deployment或者ReplicaSet中自動(dòng)的擴(kuò)展Pod的數(shù)量。

結(jié)合Kubernetes解讀微服務(wù)的12要素

HPA基于指標(biāo)的觀測(cè)來(lái)添加Pod

談及自動(dòng)擴(kuò)展,關(guān)于Pod縱向擴(kuò)展以及集群擴(kuò)展的話題值得關(guān)注??v向的Pod擴(kuò)展適用于有狀態(tài)的應(yīng)用。Kubernetes把CPU和內(nèi)存作為觸發(fā)器,來(lái)向Pod中添加更多的計(jì)算資源。也可以使用自定義的指標(biāo)代替HPA來(lái)觸發(fā)自動(dòng)擴(kuò)展。

結(jié)合Kubernetes解讀微服務(wù)的12要素

Vertical Pod Autoscaler擴(kuò)展了容器的可用內(nèi)存


要素九:快速啟動(dòng)和優(yōu)雅終止


12要素原則中的可處置性,考慮的是如何使用Linux內(nèi)核的信號(hào)機(jī)制來(lái)與運(yùn)行的進(jìn)程交互。遵循可處置性的原則,微服務(wù)可以快速啟動(dòng)并且可以隨時(shí)消亡而不影響用戶(hù)體驗(yàn)。對(duì)于無(wú)狀態(tài)的微服務(wù)來(lái)說(shuō),實(shí)現(xiàn)與部署相關(guān)的原則有助于達(dá)成可處置性。事實(shí)上,藉由前文提到的livenessProbes和readinessProbes探針機(jī)制,Kubernetes會(huì)銷(xiāo)毀在給定的時(shí)間窗口內(nèi)處于不健康的Pod。


要素十一:把日志當(dāng)作事件流


對(duì)于容器來(lái)說(shuō),所有的日志通常會(huì)記入到stdout或者stderr文件描述符。此處很重要的設(shè)計(jì)原則是,容器不應(yīng)該管理用于日志輸出的內(nèi)部文件,而應(yīng)交由容器編排系統(tǒng)來(lái)收集日志并進(jìn)行分析和歸檔。在Kubernetes中,日志收集一般作為公共服務(wù)存在。以我本人的工作經(jīng)歷來(lái)說(shuō),可以使用Elasticsearch-Logstash-Kibana組合來(lái)平滑的實(shí)現(xiàn)這一點(diǎn)。


要素十二:把后臺(tái)管理任務(wù)當(dāng)作一次性進(jìn)程運(yùn)行


像是數(shù)據(jù)庫(kù)遷移/備份/恢復(fù)/日常維護(hù)這類(lèi)管理任務(wù),應(yīng)該與微服務(wù)的基本運(yùn)行時(shí)邏輯隔離并解耦。在Kubernetes中,Job控制器可以創(chuàng)建一次性運(yùn)行的Pod,或者是按照日程規(guī)劃執(zhí)行不同活動(dòng)的Pod。Job控制器可以用來(lái)實(shí)現(xiàn)業(yè)務(wù)邏輯,因?yàn)镵ubernetes會(huì)將API令牌加載到Pod中,所以也可以使用Job控制器來(lái)與Kubernetes編排系統(tǒng)進(jìn)行交互。

通過(guò)對(duì)此類(lèi)管理任務(wù)的隔離,可以在未來(lái)簡(jiǎn)化微服務(wù)的行為,進(jìn)而減少可能出現(xiàn)的潛在失敗。


四、結(jié)語(yǔ)


如果讀者對(duì)這個(gè)話題很感興趣,建議點(diǎn)贊轉(zhuǎn)發(fā)與朋友分享本文的觀點(diǎn)。如果你有幸參加KubeCon Europe,歡迎來(lái)與我和Brad Topol面基,并且就此話題深入探討,我們會(huì)分享Kubernetes相關(guān)能力的更多演示。

除了架構(gòu)微服務(wù)的12原則以外,我和另一位作者,Shikha Srivastava,也識(shí)別了生產(chǎn)環(huán)境中遺漏的7條原則,Shikha很快會(huì)就此成文。敬請(qǐng)期待。

關(guān)于EAWorld微服務(wù),DevOps,數(shù)據(jù)治理,移動(dòng)架構(gòu)原創(chuàng)技術(shù)分享

向AI問(wèn)一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI