說(shuō)起CAT契邀,需要先簡(jiǎn)單介紹一下分布式服務(wù)鏈路監(jiān)控摆寄。
隨著微服務(wù)技術(shù)的普及,現(xiàn)在的系統(tǒng)體積變得越來(lái)愈龐大坯门,功能變得越來(lái)越復(fù)雜微饥。
一個(gè)簡(jiǎn)單的接口,如查詢操作古戴,其背后可能涉及到幾十甚至上百的服務(wù)調(diào)用欠橘,不同的服務(wù)又由不同的團(tuán)隊(duì)開(kāi)發(fā)維護(hù)。
如果沒(méi)有一套好的調(diào)用鏈監(jiān)控现恼,當(dāng)系統(tǒng)出現(xiàn)故障肃续、服務(wù)之間依賴出現(xiàn)問(wèn)題的時(shí)候,就會(huì)非常難以定位問(wèn)題叉袍。
另一方面始锚,還需要對(duì)這些數(shù)量龐大的服務(wù)進(jìn)行各種指標(biāo)的監(jiān)控,如相應(yīng)時(shí)間喳逛、請(qǐng)求量(QPS瞧捌、PV)、錯(cuò)誤率等润文,以確保整個(gè)系統(tǒng)的高效察郁、健康運(yùn)行。
所以转唉,分布式服務(wù)鏈路監(jiān)控對(duì)于微服務(wù)來(lái)說(shuō)是不可或缺的,相應(yīng)的稳捆,各種服務(wù)監(jiān)系統(tǒng)也應(yīng)運(yùn)而生赠法。
2002年,eBay乔夯,CAL砖织。
2010年,Google發(fā)表論文 末荐,"Dapper, a Large-Scale Distributed System Tracing Infrastructure"
2011年侧纯,大眾點(diǎn)評(píng),CAT
Twitter甲脏,Zipkin
阿里巴巴眶熬,鷹眼
接下來(lái)進(jìn)入本文的主題
CAT(Central Application Tracking)是原大眾點(diǎn)評(píng)基于eBay的CAL改進(jìn)而來(lái)的分布式服務(wù)鏈路監(jiān)控平臺(tái)妹笆。
CAT自2004年開(kāi)源以來(lái),在攜程娜氏、陸金所拳缠、平安銀行、拼多多贸弥、OPPO窟坐、獵聘網(wǎng)、找鋼網(wǎng)等100多家公司绵疲、企業(yè)的生產(chǎn)環(huán)境中落地應(yīng)用哲鸳。以2016年的一組數(shù)據(jù)為例:
美團(tuán)點(diǎn)評(píng),2016年盔憨,3000+應(yīng)用服務(wù)徙菠,7000+服務(wù)器,100+TB/天般渡,單機(jī)峰值QPS 16w
攜程懒豹,2016年,4500+應(yīng)用服務(wù)驯用,10000+服務(wù)器脸秽,140TB/天,單機(jī)峰值QPS 10w
目前蝴乔,CAT(作為服務(wù)端項(xiàng)目基礎(chǔ)組件记餐,提供了 Java, C/C++, Node.js, Python, Go 等多語(yǔ)言客戶端,已經(jīng)在美團(tuán)點(diǎn)評(píng)的基礎(chǔ)架構(gòu)中間件框架(MVC框架薇正,RPC框架片酝,數(shù)據(jù)庫(kù)框架,緩存框架等挖腰,消息隊(duì)列雕沿,配置系統(tǒng)等)深度集成,為美團(tuán)點(diǎn)評(píng)各業(yè)務(wù)線提供系統(tǒng)豐富的性能指標(biāo)猴仑、健康狀況审轮、實(shí)時(shí)告警等。
整體設(shè)計(jì)
監(jiān)控整體要求就是快速發(fā)現(xiàn)故障辽俗、快速定位故障以及輔助進(jìn)行程序性能優(yōu)化疾渣。為了做到這些,CAT對(duì)監(jiān)控系統(tǒng)的一些非功能做了如下的要求:
- 實(shí)時(shí)處理:信息的價(jià)值會(huì)隨時(shí)間銳減崖飘,尤其是事故處理過(guò)程中榴捡。
- 全量數(shù)據(jù):最開(kāi)始的設(shè)計(jì)目標(biāo)就是全量采集,全量的好處有很多朱浴。
- 高可用:所有應(yīng)用都倒下了吊圾,需要監(jiān)控還站著达椰,并告訴工程師發(fā)生了什么,做到故障還原和問(wèn)題定位街夭。
- 故障容忍:CAT本身故障不應(yīng)該影響業(yè)務(wù)正常運(yùn)轉(zhuǎn)砰碴,CAT掛了,應(yīng)用不該受影響板丽,只是監(jiān)控能力暫時(shí)減弱呈枉。
- 高吞吐:要想還原真相,需要全方位地監(jiān)控和度量埃碱,必須要有超強(qiáng)的處理吞吐能力猖辫。
- 可擴(kuò)展:支持分布式、跨IDC部署砚殿,橫向擴(kuò)展的監(jiān)控系統(tǒng)啃憎。
- 不保證可靠:允許消息丟失,這是一個(gè)很重要的trade-off似炎,目前CAT服務(wù)端可以做到4個(gè)9的可靠性辛萍,可靠系統(tǒng)和不可靠性系統(tǒng)的設(shè)計(jì)差別非常大。
CAT從開(kāi)發(fā)至今羡藐,一直秉承著簡(jiǎn)單的架構(gòu)就是最好的架構(gòu)原則贩毕,主要分為三個(gè)模塊:CAT-client、CAT-consumer仆嗦、CAT-home辉阶。
- Cat-client 提供給業(yè)務(wù)以及中間層埋點(diǎn)的底層SDK。
- Cat-consumer 用于實(shí)時(shí)分析從客戶端提供的數(shù)據(jù)瘩扼。
- Cat-home 作為用戶給用戶提供展示的控制端谆甜。
在實(shí)際開(kāi)發(fā)和部署中,Cat-consumer和Cat-home是部署在一個(gè)JVM內(nèi)部集绰,每個(gè)CAT服務(wù)端都可以作為consumer也可以作為home规辱,這樣既能減少整個(gè)層級(jí)結(jié)構(gòu),也可以增加系統(tǒng)穩(wěn)定性栽燕。
上圖是CAT目前多機(jī)房的整體結(jié)構(gòu)圖:
- 路由中心是根據(jù)應(yīng)用所在機(jī)房信息來(lái)決定客戶端上報(bào)的CAT服務(wù)端地址
- 每個(gè)機(jī)房?jī)?nèi)部都有的獨(dú)立的原始信息存儲(chǔ)集群HDFS
- cat-home可以部署在一個(gè)機(jī)房也可以部署在多個(gè)機(jī)房按摘,在做報(bào)表展示的時(shí)候,cat-home會(huì)從cat-consumer中進(jìn)行跨機(jī)房的調(diào)用纫谅,將所有的數(shù)據(jù)合并展示給用戶
- 實(shí)際過(guò)程中,cat-consumer溅固、cat-home以及路由中心都是部署在一起付秕,每個(gè)服務(wù)端節(jié)點(diǎn)都可以充當(dāng)任何一個(gè)角色
客戶端架構(gòu)設(shè)計(jì)
CAT客戶端是java,客戶端在收集端數(shù)據(jù)方面使用ThreadLocal侍郭,是線程本地變量询吴,也可以稱之為線程本地存儲(chǔ)掠河。線程局部變量(ThreadLocal)其實(shí)的功用非常簡(jiǎn)單,就是為每一個(gè)使用該變量的線程都提供一個(gè)變量值的副本猛计,是Java中一種較為特殊的線程綁定機(jī)制唠摹,是每一個(gè)線程都可以獨(dú)立地改變自己的副本,而不會(huì)和其它線程的副本沖突奉瘤。
在監(jiān)控場(chǎng)景下勾拉,為用戶提供服務(wù)都是web容器,web容器比如Tomcat或者Jetty盗温,后端的rpc服務(wù)端比如dubbo或者點(diǎn)評(píng)自研的服務(wù)框架pigeon藕赞,也都是基于線程池來(lái)實(shí)現(xiàn)的。業(yè)務(wù)方在處理業(yè)務(wù)邏輯時(shí)基本都是在一個(gè)線程內(nèi)部調(diào)用后端服務(wù)卖局,數(shù)據(jù)庫(kù)斧蜕,緩存等,將這些數(shù)據(jù)拿回來(lái)在進(jìn)行業(yè)務(wù)邏輯邏輯封裝砚偶,最后將結(jié)果展示給用戶批销。所以將所有的監(jiān)控請(qǐng)求作為一個(gè)監(jiān)控上下文存入于線程變量就非常合適。如上圖業(yè)務(wù)執(zhí)行業(yè)務(wù)邏輯的時(shí)候染坯,就會(huì)把此次請(qǐng)求對(duì)應(yīng)的監(jiān)控存放于線程上下文中均芽,存于上下文的其實(shí)是一個(gè)監(jiān)控樹(shù)的結(jié)構(gòu)。在最后業(yè)務(wù)線程執(zhí)行結(jié)束時(shí)酒请,將監(jiān)控對(duì)象存入一個(gè)異步內(nèi)存隊(duì)列中骡技,CAT有個(gè)消費(fèi)線程將隊(duì)列內(nèi)的數(shù)據(jù)異步發(fā)送到CAT服務(wù)端。
服務(wù)端架構(gòu)設(shè)計(jì)
服務(wù)端單機(jī)cat-consumer的整體架構(gòu)如下:如上圖羞反,CAT服務(wù)端在整個(gè)實(shí)時(shí)處理中布朦,基本上實(shí)現(xiàn)了全異步化處理。
- 消息接收是基于Netty的NIO實(shí)現(xiàn)
- 消息接收到服務(wù)端就存放內(nèi)存隊(duì)列昼窗,然后程序開(kāi)啟一個(gè)線程會(huì)消費(fèi)這個(gè)消息做消息分發(fā)
- 每個(gè)消息都會(huì)有一批線程并發(fā)消費(fèi)各自隊(duì)列的數(shù)據(jù)是趴,以做到消息處理的隔離
- 消息存儲(chǔ)是先存入本地磁盤(pán),然后異步上傳到hdfs文件澄惊,這也避免了強(qiáng)依賴hdfs
當(dāng)某個(gè)報(bào)表處理器處理來(lái)不及時(shí)候唆途,比如Transaction報(bào)表處理比較慢,可以通過(guò)配置支持開(kāi)啟多個(gè)Transaction處理線程掸驱,并發(fā)消費(fèi)消息肛搬。
監(jiān)控模型
CAT主要支持以下四種監(jiān)控模型:
- Transaction 適合記錄跨越系統(tǒng)邊界的程序訪問(wèn)行為,比如遠(yuǎn)程調(diào)用,數(shù)據(jù)庫(kù)調(diào)用毕贼,也適合執(zhí)行時(shí)間較長(zhǎng)的業(yè)務(wù)邏輯監(jiān)控温赔,Transaction用來(lái)記錄一段代碼的執(zhí)行時(shí)間和次數(shù)
- Event 用來(lái)記錄一件事發(fā)生的次數(shù),比如記錄系統(tǒng)異常鬼癣,它和transaction相比缺少了時(shí)間的統(tǒng)計(jì)陶贼,開(kāi)銷比transaction要小
- Heartbeat 表示程序內(nèi)定期產(chǎn)生的統(tǒng)計(jì)信息, 如CPU利用率, 內(nèi)存利用率, 連接池狀態(tài), 系統(tǒng)負(fù)載等
- Metric 用于記錄業(yè)務(wù)指標(biāo)啤贩、指標(biāo)可能包含對(duì)一個(gè)指標(biāo)記錄次數(shù)、記錄平均值拜秧、記錄總和痹屹,業(yè)務(wù)指標(biāo)最低統(tǒng)計(jì)粒度為1分鐘
CAT報(bào)表
Transaction報(bào)表 :
一段代碼的運(yùn)行情況,如運(yùn)行次數(shù)枉氮、QPS志衍、錯(cuò)誤次數(shù)、失敗率嘲恍、響應(yīng)時(shí)間統(tǒng)計(jì)(平均影響時(shí)間足画、Tp分位值)等等。Event報(bào)表 :
監(jiān)控一段代碼運(yùn)行次數(shù)佃牛,例如記錄程序中一個(gè)事件記錄了多少次淹辞,錯(cuò)誤了多少次。
Problem報(bào)表 :
記錄整個(gè)項(xiàng)目在運(yùn)行過(guò)程中出現(xiàn)的問(wèn)題,包括一些異常爷速、錯(cuò)誤央星、訪問(wèn)較長(zhǎng)的行為。Problem報(bào)表是由logview存在的特征整合而成惫东,方便用戶定位問(wèn)題莉给。
- Long-url,表示Transaction打點(diǎn)URL的慢請(qǐng)
- Long-sql廉沮,表示Transaction打點(diǎn)SQL的慢請(qǐng)求
- Long-service颓遏,表示Transaction打點(diǎn)Service或者PigeonService的慢請(qǐng)求
- Long-cache,表示Transaction打點(diǎn)Cache.開(kāi)頭的慢請(qǐng)求
- Long-call滞时,表示Transaction打點(diǎn)Call或者PigeonCall的慢請(qǐng)求
Heartbeat報(bào)表 (JVM相關(guān)的狀態(tài)信息)
- LoadAverage
- FreePhysicalMemory
- FreeSwapSpaceSize
- PS ScavengeCount
- PS ScavengeTime
- PS MarkSweepCount
- PS MarkSweepTime
Storage報(bào)表 (數(shù)據(jù)庫(kù)相關(guān))
Cache報(bào)表 (緩存相關(guān))
參考鏈接:
https://tech.meituan.com/2018/11/01/cat-in-depth-java-application-monitoring.html
https://github.com/dianping/cat