基于微服务成熟度模型的高可用优化实践
前言
? ?? 隨著微服務(wù)的流行,每個(gè)互聯(lián)網(wǎng)公司后臺(tái)都有無數(shù)大大小小的服務(wù),服務(wù)與服務(wù)之間又有著千絲萬縷的調(diào)用關(guān)系。要保證整個(gè)微服務(wù)系統(tǒng)的成熟穩(wěn)定,就必須保證每個(gè)微服務(wù)的成熟度。但如何來定義服務(wù)的成熟度?應(yīng)該從哪些緯度來考量?各個(gè)緯度里又有哪些普遍的問題?如何來優(yōu)化?
? ? ?本文介紹了愛奇藝技術(shù)產(chǎn)品團(tuán)隊(duì)用來衡量服務(wù)成熟度的模型,并基于此模型對(duì)多個(gè)后臺(tái)服務(wù)進(jìn)行評(píng)估,總結(jié)出了一些常見的低分項(xiàng),并對(duì)低分項(xiàng)整理了相關(guān)優(yōu)化方案。希望對(duì)大家有所幫助。
01
?服務(wù)成熟度模型
? ? ? ?為了能夠?qū)Ψ?wù)的成熟度進(jìn)行量化,我們需要從多個(gè)維度對(duì)服務(wù)進(jìn)行評(píng)估。
? ? ? ?每個(gè)服務(wù)隨著需求不斷迭代,每個(gè)迭代周期都需要經(jīng)歷如下三個(gè)階段:開發(fā)測(cè)試,運(yùn)維上線,線上運(yùn)行。每一個(gè)階段,都需要一系列的措施來保證服務(wù)最終的成熟可靠。我們針對(duì)每一個(gè)階段,梳理出來需要關(guān)注的指標(biāo),來衡量該階段的整體質(zhì)量。
? ? ? ?我們對(duì)上面3個(gè)階段進(jìn)行綜合評(píng)分,并根據(jù)評(píng)分對(duì)服務(wù)成熟度進(jìn)行了等級(jí)劃分。(1-5分為準(zhǔn)入級(jí),6-7分為服務(wù)級(jí),8-10分為成熟級(jí)。)
? ? ? ?通過這樣的服務(wù)成熟度模型,我們就可以以量化的指標(biāo)直觀的評(píng)價(jià)一個(gè)服務(wù)的成熟度,并發(fā)現(xiàn)服務(wù)有哪些可改進(jìn)項(xiàng)。
02
?低分項(xiàng)梳理
? ? ? 基于服務(wù)成熟度模型,我們對(duì)多個(gè)后臺(tái)服務(wù)進(jìn)行了評(píng)估,發(fā)現(xiàn)了一些指標(biāo)項(xiàng)在各個(gè)服務(wù)中普遍得分較低。這些指標(biāo)項(xiàng)包括:
開發(fā)測(cè)試方面:代碼規(guī)范,單元測(cè)試,壓力測(cè)試,接口撥測(cè);
運(yùn)維上線方面:灰度上線,上線回滾;
線上可用性方面:系統(tǒng)保護(hù),數(shù)據(jù)備份,報(bào)警處理,應(yīng)急預(yù)案。
? ? ?? 于是我們優(yōu)先對(duì)這些低分項(xiàng)的優(yōu)化方案進(jìn)行了梳理,期望通過對(duì)低分項(xiàng)的優(yōu)化,提升服務(wù)的成熟度,使我們的服務(wù)提升至成熟級(jí)別。
03
?低分項(xiàng)優(yōu)化方案
? ? ? 我們的服務(wù)主要基于Java語言開發(fā),主要是虛機(jī)部署的部署方式,并少量采用容器部署。所以下面的優(yōu)化方案主要圍繞我們的服務(wù)現(xiàn)狀展開。
3.1
開發(fā)測(cè)試
? ? ? ?線上bug往往都是開發(fā)新需求引入的,如果在開發(fā)測(cè)試階段盡可能的發(fā)現(xiàn)問題,提高代碼質(zhì)量,能夠?qū)栴}的影響范圍控制在最小。下面是開發(fā)測(cè)試階段一些常見的措施和手段:
3.1.1 代碼規(guī)范
? ? ? ?代碼風(fēng)格:采用統(tǒng)一的代碼風(fēng)格,一方面可以使得代碼的可讀性提升,另一方面會(huì)減少代碼合并時(shí)的沖突,并與開發(fā)工具集成,支持自動(dòng)提示不規(guī)范代碼,有的不規(guī)范代碼甚至可以一鍵修正。配合GitLab CI和Sonar檢查,可以對(duì)每次的提交進(jìn)行代碼規(guī)范的檢查,并以報(bào)告的形式直觀的展現(xiàn)。
3.1.2 單元測(cè)試
? ? ? 單元測(cè)試位于測(cè)試金字塔的最底層。運(yùn)行效率快,一般完成的測(cè)試case跑下來不會(huì)超過10分鐘,可以集成在CI流程中,快速反饋問題。維護(hù)成本低,單元測(cè)試在開發(fā)階段就能發(fā)現(xiàn)問題,修復(fù)成本低。測(cè)試金字塔越向上反饋的時(shí)間越長,實(shí)現(xiàn)的成本也越高。因此推薦大家提升單元測(cè)試的覆蓋率。
? ? ? Java最常用的測(cè)試框架是Junit。另外配合Mock測(cè)試庫Mockito和測(cè)試覆蓋率工具Jacoco形成完整的單元測(cè)試工具集。在IDEA和SonarQube中都可以配置Jacoco的插件來直觀的展示單元測(cè)試的覆蓋率。
? ? ? 在推進(jìn)單元測(cè)試的過程中,我們經(jīng)常遇見的問題是:項(xiàng)目補(bǔ)充單元測(cè)試費(fèi)時(shí)費(fèi)力,新增代碼的測(cè)試覆蓋率如何把關(guān)?
我們的解決思路是:
已有代碼優(yōu)先對(duì)重要代碼(如公共庫,工具類)補(bǔ)充單元測(cè)試。
新增代碼增加代碼覆蓋率的指標(biāo)(如:設(shè)定新增代碼測(cè)試覆蓋率不得低于90%)
隨著新增代碼和對(duì)老代碼修改,項(xiàng)目整體的測(cè)試覆蓋率會(huì)逐步提升。
新增代碼測(cè)試覆蓋率統(tǒng)計(jì):使用diff-cover工具可以通過分析分支代碼差異和Jacoco測(cè)試報(bào)告,計(jì)算出當(dāng)前分支修改代碼的測(cè)試覆蓋率。
3.1.3 單元測(cè)試
(1)為什么要做壓力測(cè)試?通過壓力測(cè)試,我們能夠:
·? 發(fā)現(xiàn)性能瓶頸
·? 預(yù)估資源使用情況
·? 為限流配置提供參考
·? 發(fā)現(xiàn)新需求引入的問題
(2)壓力測(cè)試工具應(yīng)具備什么功能?
常見的壓力測(cè)試工具有JMeter等。我們使用愛奇藝云平臺(tái)提供的LoadMaker云壓測(cè)系統(tǒng),它具備如下特點(diǎn):
·? 多個(gè)施壓集群,壓力可以達(dá)到很高
·? 創(chuàng)建和保存壓測(cè)場(chǎng)景,重復(fù)執(zhí)行
·? 提供壓測(cè)報(bào)告:QPS,響應(yīng)時(shí)間,錯(cuò)誤率等數(shù)據(jù)
? ? ?? 同時(shí),為了壓測(cè)不影響線上用戶的真實(shí)流量,我們構(gòu)建了單獨(dú)的壓測(cè)資源池。在需要壓測(cè)時(shí),選擇資源池中的機(jī)器和帶壓測(cè)模塊,可自動(dòng)構(gòu)建壓測(cè)環(huán)境。
(3)什么情況下需要壓測(cè)?
·? 例行壓測(cè):版本灰度期間對(duì)重點(diǎn)項(xiàng)目進(jìn)行例行壓測(cè)。
·? 新項(xiàng)目/接口上線前壓測(cè):新項(xiàng)目上線前壓測(cè),指導(dǎo)容量預(yù)估和限流配置。
3.1.4 接口撥測(cè)
? ? ? ?對(duì)于后臺(tái)接口服務(wù),我們比較關(guān)心線上接口返回的數(shù)據(jù)是否正確以及新代碼上線是否影響了已有邏輯?接口撥測(cè)可以很好的覆蓋上面兩個(gè)問題。一方面可以用于線上接口返回?cái)?shù)據(jù)的校驗(yàn),實(shí)時(shí)發(fā)現(xiàn)接口異常。另一方面可以用于自動(dòng)化接口測(cè)試,配合上線流程,發(fā)現(xiàn)新增代碼是否有引入的問題,及時(shí)終止上線操作。一個(gè)接口撥測(cè)系統(tǒng)應(yīng)具備如下特性:
(1)支持對(duì)接口返回結(jié)果做校驗(yàn)。
(2)復(fù)雜校驗(yàn)支持編寫腳本。
(3)可設(shè)置多個(gè)撥測(cè)點(diǎn),模擬正式用戶請(qǐng)求場(chǎng)景。
(4)支持報(bào)警。
(5)詳細(xì)的測(cè)試報(bào)告。
(6)和上線流程打通,支持灰度后的自動(dòng)化接口測(cè)試。
3.2
運(yùn)維上線
3.2.1 灰度上線機(jī)制
? ? ? ?代碼在測(cè)試環(huán)境測(cè)試通過并不能保證代碼完全沒有問題,仍然有可能因?yàn)闇y(cè)試疏漏或環(huán)境差異等原因?qū)е挛窗l(fā)現(xiàn)的問題。如果沒有灰度上線的機(jī)制,這些潛在問題直接上線,可能對(duì)線上系統(tǒng)帶來災(zāi)難性的后果。
? ? ? ?灰度上線需要配合灰度檢查來確保本次上線的安全性。我們采用的檢查方式有:
(1)灰度上線后針對(duì)灰度機(jī)器進(jìn)行自動(dòng)化接口檢測(cè)。
(2)對(duì)比灰度機(jī)監(jiān)控指標(biāo)和線上機(jī)器的監(jiān)控指標(biāo)。
(3)灰度環(huán)境測(cè)試功能驗(yàn)收。
3.2.2 上線回滾
? ? ? ?如果發(fā)生因?yàn)樯暇€新代碼導(dǎo)致的線上問題,首先要做的應(yīng)該是回滾操作,而不是去分析問題和修復(fù)代碼上線。回滾操作需要盡量做到以下幾點(diǎn):
(1)回滾速度快,如果需要revert代碼,重新編譯打包,上傳至服務(wù)器,整個(gè)流程會(huì)比較漫長,故障恢復(fù)的時(shí)間也會(huì)比較長。
(2)回滾完整,有些代碼和配置文件是有依賴的,如果只回滾了代碼,可能導(dǎo)致啟動(dòng)后的異常。
(3)可回滾性,這需要架構(gòu)層面的思考,不要出現(xiàn)無法回滾的情況,如上線后數(shù)據(jù)寫入,對(duì)回滾后的代碼不兼容。
? ? ???我們采用的是RPM打包的方式進(jìn)行上線和回滾。通過RPM的形式把一次部署的所有內(nèi)容(代碼和配置)打包,部署時(shí)服務(wù)器保留歷史版本的RPM包,當(dāng)需要回滾時(shí),直接執(zhí)行Job安裝歷史版本的RPM包即可。如果服務(wù)采用的是容器部署,則回滾起來會(huì)更簡(jiǎn)單,只需啟動(dòng)歷史版本的鏡像即可。
3.3
線上可用性
3.3.1 系統(tǒng)保護(hù)
? ? ? ?線上運(yùn)行時(shí)可能面對(duì)各種各樣的問題,機(jī)器故障,網(wǎng)絡(luò)問題,依賴的服務(wù)方掛掉,流量劇增等等。如何在如此險(xiǎn)惡的環(huán)境下生存?不能相信別人,只能提升服務(wù)自身的可靠性。一般采取方式有:熔斷,限流,降級(jí),重試等。
熔斷
? ? ? 當(dāng)我們依賴的服務(wù)方有問題時(shí),不能把我們的服務(wù)拖垮,常用的方式是熔斷。當(dāng)依賴方成功率低于我們?cè)O(shè)置的閾值時(shí),暫停對(duì)其調(diào)用,過一定間隔再去重試。
? ? ? 常用的熔斷組件有:Hystrix,Sentinel等。下表是Hystrix和Sentinel的對(duì)比。
? ? ? 鑒于Netflix對(duì)Hystrix不再維護(hù),以及Sentinel更加豐富的功能,我們選擇了Sentinel作為我們的熔斷組件。
降級(jí)
? ? ? ?當(dāng)發(fā)生突發(fā)事故,服務(wù)整體超負(fù)載時(shí),為了避免服務(wù)整體不可用,一般會(huì)啟用服務(wù)降級(jí),以保證重要或基本服務(wù)正常運(yùn)行,非重要服務(wù)延遲使用或暫停使用。
? ? ? ?為此,我們實(shí)現(xiàn)了一個(gè)頁面降級(jí)服務(wù)。該服務(wù)會(huì)定時(shí)請(qǐng)求頁面接口,并對(duì)其進(jìn)行校驗(yàn),校驗(yàn)通過后將結(jié)果保存起來;當(dāng)服務(wù)出現(xiàn)異常或超負(fù)載時(shí),打開降級(jí)開關(guān),頁面服務(wù)會(huì)直接讀取之前保存的靜態(tài)頁面數(shù)據(jù)返回。犧牲個(gè)性化,從千人千面降級(jí)為千人一面。由于去除了頁面構(gòu)造的流程,處理能力會(huì)大幅提升,保證服務(wù)的正常運(yùn)行。
限流
? ? ? ?限流非常重要,它是保護(hù)服務(wù)正常運(yùn)行的重要關(guān)卡。尤其是在出現(xiàn)流量突增時(shí),合理的限流可以保護(hù)你的服務(wù)不被打垮。如果沒有配置限流,不但流量突增時(shí)服務(wù)會(huì)被打垮,服務(wù)也難以恢復(fù),因?yàn)榉?wù)重啟后會(huì)被再次打垮。
? ? ? ?我們一般會(huì)在網(wǎng)關(guān)層和服務(wù)層分別配置限流。
? ? ? ?網(wǎng)關(guān)層使用nginx的限流插件可以配置單機(jī)的限流。
? ? ? ?服務(wù)層使用Sentinel限流。Sentinel可以基于QPS,并發(fā)數(shù),調(diào)用關(guān)系來限流,并且支持集群整體限流。下圖是Sentinel集群限流的實(shí)現(xiàn)。
重試
? ? ?從客戶端到后端服務(wù),中間各個(gè)環(huán)節(jié)都有可能出現(xiàn)異常,如DNS故障,運(yùn)營商節(jié)點(diǎn)故障,后臺(tái)服務(wù)器故障等等,導(dǎo)致請(qǐng)求失敗。
? ? ? 針對(duì)不同的情形,適當(dāng)?shù)闹卦嚳梢栽黾诱?qǐng)求成功率。愛奇藝APP端的重試分為如下幾種:
1. IP直連重試,通過配置直連IP數(shù)來控制重試次數(shù)。
2. 超級(jí)管道重試,公司自研基于HTTP的網(wǎng)關(guān)代理服務(wù),可做到異地重試。
3. HTTP重試。
4.原url重試。
? ? ? 詳細(xì)信息可以參考公眾號(hào)文章《愛奇藝移動(dòng)端網(wǎng)絡(luò)優(yōu)化實(shí)踐分享:網(wǎng)絡(luò)請(qǐng)求成功率優(yōu)化篇》。
? ? ? ?重試可以提高成功率,但是過度重試可能會(huì)導(dǎo)致后端服務(wù)壓力過大,出現(xiàn)雪崩效應(yīng)。所以重試策略上應(yīng)該注意如下幾點(diǎn):
1. ?重試策略可云控,極端情況下可后臺(tái)配置關(guān)閉重試。
2. ?區(qū)分錯(cuò)誤碼重試,不是所有錯(cuò)誤碼都需要重試,如后臺(tái)觸發(fā)限流返回的錯(cuò)誤碼就不需要重試。
3.3.2 數(shù)據(jù)備份
? ? ? ?在數(shù)據(jù)庫的使用上,我們需要考慮數(shù)據(jù)庫的高可用。在這方面,公司的服務(wù)云團(tuán)隊(duì)做了很多方面的優(yōu)化,大家可以在公眾號(hào)文章里查詢到,本文就不詳細(xì)展開了。作為業(yè)務(wù)方,我們需要注意的是數(shù)據(jù)庫的使用要嚴(yán)格按照兩地三中心的架構(gòu)申請(qǐng)和使用。
3.3.3 監(jiān)控報(bào)警
? ? ? ?完善的監(jiān)控報(bào)警可以讓我們?cè)诜?wù)出現(xiàn)問題的第一時(shí)間感知到,及時(shí)處理,避免問題的擴(kuò)散。從不同的緯度,我們需要不同的監(jiān)控,主要包括:
指標(biāo)監(jiān)控
? ? ?監(jiān)控服務(wù)的關(guān)鍵指標(biāo),這里包括3部分:機(jī)器指標(biāo)(CPU,內(nèi)存,網(wǎng)絡(luò)流量等),服務(wù)指標(biāo)(QPS,成功率,響應(yīng)時(shí)間等),第三方接口指標(biāo)(QPS,成功率,響應(yīng)時(shí)間等)。
? ? ? 具體的實(shí)現(xiàn)方案是:通過Collectd和自研Meerkat組件進(jìn)行指標(biāo)上報(bào),上報(bào)給Graphint進(jìn)行匯總存儲(chǔ),并通過Grafana進(jìn)行展示。
應(yīng)用日志監(jiān)控
? ? ? 基于應(yīng)用日志的監(jiān)控可以讓我們發(fā)現(xiàn)更加細(xì)粒度的異常,如應(yīng)用內(nèi)拋出的異常,內(nèi)部業(yè)務(wù)邏輯錯(cuò)誤等。
? ? ? ?首先我們定義了一套日志打印的格式規(guī)范,所有需要監(jiān)控的日志都按統(tǒng)一的格式進(jìn)行日志輸出。然后通過日志收集組件Venus將機(jī)器上的日志投遞到Kafka隊(duì)列,最終入到Druid時(shí)序數(shù)據(jù)庫內(nèi),進(jìn)行多維度的分析存儲(chǔ)。前端報(bào)表使用Graphna進(jìn)行展示。
全鏈路監(jiān)控
? ? ? ?如果要監(jiān)控上下文的鏈路關(guān)系、跨系統(tǒng)的故障定位等相關(guān)問題,需要進(jìn)行全鏈路監(jiān)控。詳細(xì)信息可以參考公眾號(hào)文章《愛奇藝全鏈路自動(dòng)化監(jiān)控平臺(tái)的探索與實(shí)踐》。
3.3.4 應(yīng)急預(yù)案
? ? ? ?盡管我們上面列舉了一系列的可用性優(yōu)化措施,但在真實(shí)的線上環(huán)境里,仍然會(huì)出現(xiàn)各種各樣的異常,故障,需要我們進(jìn)行手動(dòng)處理。當(dāng)問題真正出現(xiàn)時(shí),如果現(xiàn)場(chǎng)去想應(yīng)該如何處理,可能由于慌亂而沒有做到最優(yōu)的處理方案。因此,我們需要提前想好可能出現(xiàn)的問題,以及出現(xiàn)這些問題時(shí)應(yīng)該如何處理,并形成書面的文檔。在問題出現(xiàn)時(shí),我們只需要對(duì)著文檔一步一步處理即可。
04
# 服務(wù)質(zhì)量檢查
? ? ? ?有了優(yōu)化方案,如何判斷服務(wù)有沒有按照優(yōu)化方案實(shí)施?如何保證服務(wù)長期保持較高的可用性?我們不希望做完一輪優(yōu)化,服務(wù)成熟度提升之后,長期沒有跟進(jìn)的話,服務(wù)成熟度又慢慢的開始下降。
? ? ? ?因此對(duì)這些常見的服務(wù)成熟度指標(biāo)進(jìn)行了自動(dòng)化的檢查,并形成每日的健康度報(bào)告,把服務(wù)的成熟度監(jiān)控起來。一旦有某項(xiàng)指標(biāo)出現(xiàn)異常,我們能夠及時(shí)處理。這樣使我們的服務(wù)成熟度保持長期的穩(wěn)定狀態(tài)。
總結(jié)與展望
? ? ? ?在本文介紹了愛奇藝提出的服務(wù)成熟度模型的定義,以可量化的指標(biāo)來評(píng)估服務(wù)的成熟度。然后以該模型為標(biāo)準(zhǔn),對(duì)后臺(tái)服務(wù)進(jìn)行了評(píng)估,并總結(jié)了各個(gè)后臺(tái)服務(wù)普遍得分較低的指標(biāo)項(xiàng)。針對(duì)這些低分項(xiàng),梳理了優(yōu)化方案。并建立了自動(dòng)化的服務(wù)質(zhì)量檢測(cè)機(jī)制,以保證服務(wù)成熟度的長期穩(wěn)定。
? ? ? ?通過可用性優(yōu)化,多個(gè)重要服務(wù)的成熟度模型評(píng)分都已經(jīng)提升到了8分以上,并通過自動(dòng)化的服務(wù)質(zhì)量檢測(cè)機(jī)制,長期監(jiān)測(cè)成熟度的各個(gè)指標(biāo),一旦發(fā)現(xiàn)某些指標(biāo)異常,及時(shí)進(jìn)行修復(fù)改進(jìn)。
? ? ? 未來,會(huì)在下面兩點(diǎn)進(jìn)行持續(xù)的改進(jìn)和增強(qiáng):
1. ??成熟度模型評(píng)分的自動(dòng)化。避免人工評(píng)分的主觀因素,同時(shí)提升效率。
2. ??自動(dòng)化的服務(wù)質(zhì)量檢測(cè)機(jī)制增加更多的指標(biāo)。
? ? ? ?希望通過基于服務(wù)成熟度模型的優(yōu)化,使我們的服務(wù)可用性得到持續(xù)的提升。
也許你還想看
愛奇藝號(hào)基于Prometheus的微服務(wù)應(yīng)用監(jiān)控實(shí)踐
愛奇藝微服務(wù)監(jiān)控的探索與實(shí)踐
掃一掃下方二維碼,更多精彩內(nèi)容陪伴你!
總結(jié)
以上是生活随笔為你收集整理的基于微服务成熟度模型的高可用优化实践的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: mysql 存储过程 队列_mysql使
- 下一篇: EBS发票AP常用表