掃二維碼與項(xiàng)目經(jīng)理溝通
我們?cè)谖⑿派?4小時(shí)期待你的聲音
解答本文疑問(wèn)/技術(shù)咨詢/運(yùn)營(yíng)咨詢/技術(shù)建議/互聯(lián)網(wǎng)交流
????軟件工程領(lǐng)域存在一個(gè)共識(shí):維護(hù)代碼所花費(fèi)的時(shí)間要遠(yuǎn)多于寫代碼。而整個(gè)代碼維護(hù)過(guò)程中,最驚心動(dòng)魄與扣人心弦的部分,莫過(guò)于問(wèn)題排查(Trouble-shooting)了。特別是那些需要 7x24 小時(shí)不間斷維護(hù)在線業(yè)務(wù)的一線服務(wù)端程序員們,大大小小的問(wèn)題排查線上救火早已成為家常便飯,一不小心可能就吃成了自助餐 —— 豎著進(jìn)躺著出,吃不了也兜不住。本文分享作者在服務(wù)端問(wèn)題排查方面的一些經(jīng)驗(yàn),包括常見問(wèn)題、排查流程、排查工具,結(jié)合實(shí)際項(xiàng)目中發(fā)生過(guò)的慘痛案例進(jìn)行現(xiàn)身說(shuō)法。

創(chuàng)新互聯(lián)公司主營(yíng)即墨網(wǎng)站建設(shè)的網(wǎng)絡(luò)公司,主營(yíng)網(wǎng)站建設(shè)方案,成都app軟件開發(fā),即墨h5微信平臺(tái)小程序開發(fā)搭建,即墨網(wǎng)站營(yíng)銷推廣歡迎即墨等地區(qū)企業(yè)咨詢
一 問(wèn)題排查
1 常見問(wèn)題
Know Your Enemy:知己知彼,百戰(zhàn)不殆。
日常遇到的大部分問(wèn)題,大致可以歸到如下幾類:
上述分類可能不太完備和嚴(yán)謹(jǐn),想傳達(dá)的點(diǎn)是:你也可以積累一個(gè)這樣的 checklist,當(dāng)遇到問(wèn)題百思不得其解時(shí),耐心過(guò)一遍,也許很快就能對(duì)號(hào)入座。
2 排查流程
醫(yī)生:小王你看,這個(gè)傷口的形狀,像不像一朵漂浮的白云?
病人:...再不給我包扎止血,就要變成火燒云了。
??
??
快速止血
問(wèn)題排查的第一步,一定是先把血止住,及時(shí)止損。如何快速止血?常見方式包括:
保留現(xiàn)場(chǎng)
血止住了?那么恭喜你,至少故障影響不會(huì)再擴(kuò)大了。卸下鍋,先喘口氣再說(shuō)。下一步,就是要根據(jù)線索找出問(wèn)題元兇了。作為一名排查老手,你需要有盡量保留現(xiàn)場(chǎng)的意識(shí),例如:
定位原因
OK,排查線索也有了,接下來(lái)該怎么定位具體原因?這個(gè)環(huán)節(jié)會(huì)綜合考驗(yàn)?zāi)愕募夹g(shù)深度、業(yè)務(wù)熟悉度和實(shí)操經(jīng)驗(yàn),因?yàn)樵蛲记姘俟郑枰?case by case 的追蹤與分析。這里給出幾個(gè)排查方向上的建議:
解決問(wèn)題
最后,問(wèn)題根因已經(jīng)找到,如何完美解決收尾?幾個(gè)基本原則:
3 排查工具
手里只有錘子,那看什么都像釘子。作為工程師,你需要的是一整套工具箱。
??
??
??
??
問(wèn)題排查其實(shí)就是一次持續(xù)觀測(cè)應(yīng)用行為的過(guò)程。為了確保不遺漏關(guān)鍵細(xì)節(jié),你需要讓自己的應(yīng)用變得更“可觀測(cè)(Observable)。
提升應(yīng)用可觀測(cè)性有三大利器:日志(Logging)、監(jiān)控(Metrics)、追蹤(Tracing)。在我之前所做的項(xiàng)目中,這三塊能力分別是由 SLS、Alimonitor / AliMetrics / Tsar、EagleEye 提供的,這里就不再展開描述了。
另外也很推薦 Arthas 這個(gè)工具,非常實(shí)用和順手,相信很多同學(xué)都已經(jīng)用過(guò)。
二 系統(tǒng)優(yōu)化
只學(xué)會(huì)了問(wèn)題排查還遠(yuǎn)遠(yuǎn)不夠(當(dāng)然技能必須點(diǎn)滿,shit always happen),再熟練也只是治標(biāo)不治本。如果想從根源上規(guī)避問(wèn)題,必須從系統(tǒng)本身出發(fā):按照性能、穩(wěn)定性和可維護(hù)性三個(gè)方向,持續(xù)優(yōu)化你的系統(tǒng)實(shí)現(xiàn),扼殺問(wèn)題于搖籃之中,讓自己每天都能睡個(gè)安穩(wěn)覺。
老板:既要快,又要穩(wěn),還要好。哦,工資的事你別擔(dān)心,下個(gè)月一定能發(fā)出來(lái)。
??
??
系統(tǒng)優(yōu)化的三個(gè)基本方向:性能(Performance)、穩(wěn)定性(Stability)、可維護(hù)性(Maintainability)。三者之間并不是完全獨(dú)立的,而是存在著復(fù)雜的相互作用關(guān)系,有時(shí)甚至?xí)讼碎L(zhǎng)。
最優(yōu)秀的軟件系統(tǒng),并非要把這三個(gè)方向都做到極致,而是會(huì)根據(jù)自己實(shí)際的業(yè)務(wù)需求和場(chǎng)景合理取舍,在這三者之間達(dá)到一個(gè)綜合最優(yōu)的動(dòng)態(tài)平衡狀態(tài),讓各方面都能做到足夠好即可。
所以,優(yōu)化不只是一門科學(xué),也是一門藝術(shù)。
1 性能優(yōu)化
問(wèn):要跑出最快的圈速,是車手重要,還是賽車重要?答:全都重要。
沒有哪個(gè)男人會(huì)不喜歡高性能跑車,也沒有哪個(gè)女人會(huì)希望在看李佳琦直播時(shí)突然卡頓。
性能,是各行各業(yè)工程師們共同追求的終極浪漫。
性能指標(biāo)
指標(biāo)(Indicators)是衡量一件事物好壞的科學(xué)量化手段。對(duì)于性能而言,一般會(huì)使用如下指標(biāo)評(píng)估:
此外,同一個(gè)系統(tǒng)的吞吐率與響應(yīng)時(shí)間,一般還會(huì)存在如下關(guān)聯(lián)關(guān)系:吞吐率小于某個(gè)臨界值時(shí),響應(yīng)時(shí)間幾乎不變;一旦超出這個(gè)臨界值,系統(tǒng)將進(jìn)入超載狀態(tài)(overloaded),響應(yīng)時(shí)間開始線性增長(zhǎng)。對(duì)于一個(gè)有穩(wěn)定性要求的系統(tǒng),需要在做性能壓測(cè)和容量規(guī)劃時(shí)充分考慮這個(gè)臨界值的大小。
注:其實(shí)按更嚴(yán)謹(jǐn)?shù)恼f(shuō)法,性能就是單指一個(gè)系統(tǒng)有多“快”;上述部分指標(biāo)并不純粹只代表系統(tǒng)快慢,但也都與快慢息息相關(guān)。
性能分析
古人有句老話,If you can't measure it, you can't improve It.
要優(yōu)化一個(gè)系統(tǒng)的性能(例如Web請(qǐng)求響應(yīng)時(shí)間),你必須首先準(zhǔn)確地測(cè)量和分析出,當(dāng)前系統(tǒng)的性能究竟差在哪:是請(qǐng)求解析不夠快,還是查詢 DB 太慢?如果是后者,那又是掃描數(shù)據(jù)條目階段太慢,還是返回結(jié)果集太慢?或者會(huì)不會(huì)只是應(yīng)用與 DB 之間的網(wǎng)絡(luò)延遲太大?
任何復(fù)雜請(qǐng)求的處理過(guò)程,最終都可以拆解出一系列并行/串行的原子操作。如果只是逮住哪個(gè)就去優(yōu)化哪個(gè),顯然效率不會(huì)太高(除非你運(yùn)氣爆棚)。更合理的做法,應(yīng)該是堅(jiān)持 2/8 原則:優(yōu)先分析和優(yōu)化系統(tǒng)瓶頸,即當(dāng)前對(duì)系統(tǒng)性能影響最大的原子操作;他們很可能就是 ROI 最高的優(yōu)化點(diǎn)。
具體該如何去量化分析性能?這里列出了一些工具參考:
其中很多工具也是問(wèn)題排查時(shí)常用的診斷工具;畢竟,無(wú)論是性能分析還是診斷分析,目的都是去理解一個(gè)系統(tǒng)和他所處的環(huán)境,所需要做的事情都是相似的。
優(yōu)化原則
你應(yīng)該做的:上面已經(jīng)提了很多,這里再補(bǔ)充一點(diǎn):性能優(yōu)化與做功能需求一樣,都是為業(yè)務(wù)服務(wù)的,因此優(yōu)化時(shí)千萬(wàn)不要忙著自嗨,一定要結(jié)合目標(biāo)需求和應(yīng)用場(chǎng)景 —— 也許這塊你想做的優(yōu)化,壓根線上就碰不到;也許那塊很難做的優(yōu)化,可以根據(jù)流量特征做非通用的定制優(yōu)化。
你不應(yīng)該做的:即老生常談的提前優(yōu)化(Premature-optimization)與過(guò)度優(yōu)化(Over-optimization) —— 通常而言(并不絕對(duì)),性能優(yōu)化都不是免費(fèi)的午餐,優(yōu)化做的越多,往往可維護(hù)性也會(huì)越差。
優(yōu)化手段
常用的性能優(yōu)化手段有哪些?我這里總結(jié)了 8 個(gè)套路(最后 1 個(gè)是小霸王多合一匯總套路)。
1)簡(jiǎn)化
有些事,你可以選擇不做。
2)并行
有些事,你可以找人一起做。
方式:?jiǎn)螜C(jī)并行(多線程)、多機(jī)并行(分布式)。
優(yōu)點(diǎn):充分利用機(jī)器資源(多核、集群)。
缺點(diǎn):同步開銷、線程開銷、數(shù)據(jù)傾斜。
3)異步
有些事,你可以放手,不用死等。
方式:消息隊(duì)列 + 任務(wù)線程 + 通知機(jī)制。
優(yōu)點(diǎn):提升吞吐率、組件解耦、削峰填谷。
缺點(diǎn):排隊(duì)延遲(隊(duì)列積壓)。
4)批量
有些事,你可以合起來(lái)一起做。
方式:多次單一操作 → 合并為單次批量操作。
案例:TCP Nagel 算法;DB 的批量讀寫接口。
優(yōu)點(diǎn):避免單次操作的固有開銷,均攤后總開銷更低。
缺點(diǎn):等待延遲 + 聚合延遲。
5)時(shí)間空間互換
游戲的本質(zhì):要么有閑,要么有錢。
空間換時(shí)間:避免重復(fù)計(jì)算、拉近傳輸距離、分流減少壓力。
時(shí)間換空間:有時(shí)候也能達(dá)到“更快”的效果(數(shù)據(jù)量減少 → 傳輸時(shí)間減少)。
6)數(shù)據(jù)結(jié)構(gòu)與算法優(yōu)化
程序 = 數(shù)據(jù)結(jié)構(gòu) + 算法
7)池化 & 局部化
共享經(jīng)濟(jì) & 小區(qū)超市
池化(Pooling):減少資源創(chuàng)建和銷毀開銷。
局部化(Localization):避免共享資源競(jìng)爭(zhēng)開銷。
8)更多優(yōu)化手段
2 穩(wěn)定性優(yōu)化
穩(wěn)住,我們能贏?!?by [0 殺 10 死] 正在等待復(fù)活的魯班七號(hào)
維持穩(wěn)定性是我們程序員每天都要思考和討論的大事。
什么樣的系統(tǒng)才算穩(wěn)定?我自己寫了個(gè)小工具,本地跑跑從來(lái)沒出過(guò)問(wèn)題,算穩(wěn)定嗎?淘寶網(wǎng)站幾千人維護(hù),但雙十一零點(diǎn)還是經(jīng)常下單失敗,所以它不穩(wěn)定嘍?
穩(wěn)定是相對(duì)的,業(yè)務(wù)規(guī)模越大、場(chǎng)景越復(fù)雜,系統(tǒng)越容易出現(xiàn)不穩(wěn)定,且?guī)?lái)的影響也越嚴(yán)重。
??
??
衡量指標(biāo)
不同業(yè)務(wù)所提供的服務(wù)類型千差萬(wàn)別,如何用一致的指標(biāo)去衡量系統(tǒng)穩(wěn)定性?標(biāo)準(zhǔn)做法是定義服務(wù)的可用性(Availability):只要對(duì)用戶而言服務(wù)“可用”,那就認(rèn)為系統(tǒng)當(dāng)前是穩(wěn)定的;否則就是不穩(wěn)定。用這樣的方式,采集和匯總后就能得到服務(wù)總的可用/不可用比例(服務(wù)時(shí)長(zhǎng) or 服務(wù)次數(shù)),以此來(lái)監(jiān)測(cè)和量化一個(gè)系統(tǒng)的穩(wěn)定性。
可是,通過(guò)什么來(lái)定義某個(gè)服務(wù)當(dāng)前是否可用呢?這一點(diǎn)確實(shí)跟業(yè)務(wù)相關(guān),但大部分同類業(yè)務(wù)都可以用類似的方式去定義。例如,對(duì)于一般的 Web 網(wǎng)站,我們可以按如下方式去定義服務(wù)是否可用:API 請(qǐng)求都返回成功,且頁(yè)面總加載時(shí)間 < 3 秒。
對(duì)于阿里云對(duì)外提供的云產(chǎn)品而言,服務(wù)可用性是一個(gè)更加需要格外重視并持續(xù)提升的指標(biāo):阿里云上的很多用戶會(huì)同時(shí)使用多款云產(chǎn)品,其中任何一款產(chǎn)品出現(xiàn)可用性問(wèn)題,都會(huì)直接被用戶的用戶感知和放大。所以,越是底層的基礎(chǔ)設(shè)施,可用性要求就越高。關(guān)于可用性的更多細(xì)節(jié)指標(biāo)和概念(SLI / SLO / SLA),可進(jìn)一步參考云智能 SLA 了解。
可用性測(cè)量
有了上述可用性指標(biāo)定義后,接下來(lái)該如何去準(zhǔn)確測(cè)量系統(tǒng)的可用性表現(xiàn)?一般有如下兩種方式。
1)探針模擬
從客戶端側(cè),模擬用戶的調(diào)用行為。
2)服務(wù)端采集
從服務(wù)端側(cè),直接分析日志和數(shù)據(jù)。
優(yōu)點(diǎn):覆蓋所有調(diào)用數(shù)據(jù)。
缺點(diǎn):缺失客戶端鏈路數(shù)據(jù)。
對(duì)可用性數(shù)據(jù)要求較高的系統(tǒng),也可以同時(shí)運(yùn)用上述兩種方式,建議結(jié)合你的業(yè)務(wù)場(chǎng)景綜合評(píng)估選擇。
優(yōu)化原則
你應(yīng)該做的:關(guān)注 RT 的數(shù)據(jù)分布(如:p50/p99/p999 分位點(diǎn)),而不是平均值(mean) —— 平均值并沒有太大意義,更應(yīng)該去關(guān)注你那 1%、0.1% 用戶的準(zhǔn)確感受。
你不應(yīng)該做的:不要嘗試承諾和優(yōu)化可用性到 100% —— 一方面是無(wú)法實(shí)現(xiàn),存在太多客觀不可控因素;另一方面也沒有意義,客戶幾乎關(guān)注不到 0.001% 的可用性差別。
優(yōu)化手段
常用的穩(wěn)定性優(yōu)化手段有哪些?這里也總結(jié)了 8 個(gè)套路:
1)避免單點(diǎn)
父母:一個(gè)人在外漂了這么多年,也該找個(gè)人穩(wěn)定下來(lái)了。
如何避免?
只堆量不夠,還需要具備故障轉(zhuǎn)移能力(Failover)。
2)流控/限流
計(jì)劃生育、上學(xué)調(diào)劑、車牌限號(hào)、景區(qū)限行... 人生處處被流控。
3)熔斷
上午買的股票熔斷,晚上家里保險(xiǎn)絲熔斷... 淡定,及時(shí)止損而已。
4)降級(jí)
沒時(shí)間做飯了,今天就吃外賣吧... 對(duì)于健康問(wèn)題,還是得少一點(diǎn)降級(jí)。
觸發(fā)原因:流控、熔斷、負(fù)載過(guò)高。
常見降級(jí)方式:
5)超時(shí)/重試
釘釘不回怎么辦?每 10 分鐘 ping 一次,超過(guò) 1 小時(shí)打電話。
Timeout vs. Deadline:使用絕對(duì)時(shí)間會(huì)更好
重試:確??芍卦嚥僮鞯膬绲刃?。
6)資源設(shè)限
雙 11 如何避免女友敗家?提前把自己信用卡額度調(diào)低。
7)資源隔離
雙 12 女友還是要敗家?得嘞刷你自個(gè)的卡吧,別動(dòng)我的。
8 )安全生產(chǎn)
女友哭著說(shuō)再讓我最后剁一次手吧?安全第一,寧愿心疼也不要肉疼。
程序動(dòng)態(tài)性:開關(guān)、配置、熱升級(jí)。
審核機(jī)制:代碼 Review、發(fā)布審批。
灰度發(fā)布;分批部署;回滾預(yù)案。
3 可維護(hù)性優(yōu)化
前人栽樹,后人乘涼。
前人挖坑,后人涼涼。
維護(hù)的英文是 maintain,也能翻譯成:維持、供給。所以軟件維護(hù)能有多重要?它就是軟件系統(tǒng)的呼吸機(jī)和食物管道,維持軟件生命的必要供給。
系統(tǒng)開發(fā)完成上線,不過(guò)只是把它“生”下來(lái)而已。軟件真正能發(fā)揮多大價(jià)值,看的是交付后持續(xù)的價(jià)值兌現(xiàn)過(guò)程 —— 是不斷茁壯成長(zhǎng),為用戶發(fā)光發(fā)熱?還是慢慢墮落,逐漸被用戶所遺忘?這并不是取決于它當(dāng)下瞬時(shí)是否足夠優(yōu)秀(性能)和靠譜(穩(wěn)定),而是取決于未來(lái) —— 能否在不斷變化的市場(chǎng)環(huán)境、客戶需求和人為因素中,始終保持足夠優(yōu)秀和靠譜,并且能越來(lái)越好。
相比性能和穩(wěn)定性而言,可維護(hù)性所體現(xiàn)的價(jià)值往往是最長(zhǎng)遠(yuǎn)、但也最難在短期內(nèi)可兌現(xiàn)的,因此很多軟件項(xiàng)目都選擇了在前期犧牲可維護(hù)性。這樣決策帶來(lái)的后果,就跟架構(gòu)設(shè)計(jì)一樣,是幾乎無(wú)法(或者需要非常高的成本)去彌補(bǔ)和挽回的。太多的軟件項(xiàng)目,就是因?yàn)樵絹?lái)越不可維護(hù)(代碼改不動(dòng)、bug 修不完、feature 加不上),最后只能慢慢淪落為一個(gè)誰(shuí)都不想碰的遺留項(xiàng)目。
衡量指標(biāo)
相比性能和穩(wěn)定性而言,可維護(hù)性確實(shí)不太好量化(藝術(shù)成分 > 科學(xué)成分)。這里我選取了幾個(gè)偏定性分析的指標(biāo):
1)復(fù)雜度(Complexity):是否復(fù)雜度可控?
2)可擴(kuò)展性(Extensibility):是否易于變更?
3)可運(yùn)維性(Operability):是否方便運(yùn)維?
重要性
這里給了幾個(gè)觀點(diǎn),進(jìn)一步強(qiáng)調(diào)可維護(hù)性的重要性。
優(yōu)化原則
你應(yīng)該做的:遵循 KISS 原則、DRY 原則、各種代碼可讀性和架構(gòu)設(shè)計(jì)原則等。
你不應(yīng)該做的:引入過(guò)多臨時(shí)性、Hack 代碼;功能 Work 就 OK,欠一堆技術(shù)債(出來(lái)混總是要還的)。
優(yōu)化手段
常用的可維護(hù)性優(yōu)化手段有哪些?這里我總結(jié)了 4 個(gè)套路:
1)編碼規(guī)范
無(wú)規(guī)矩,不成方圓。
2)代碼重構(gòu)
別灰心,代碼還有救。
何時(shí)重構(gòu):任何時(shí)候代碼中嗅到壞味道(bad smell)。
重構(gòu)節(jié)奏:小步迭代、回歸驗(yàn)證。
重構(gòu) vs. 重寫:需要綜合考慮成本、風(fēng)險(xiǎn)、并行版本維護(hù)等因素。
推薦閱讀:Refactoring: Improving the Design of Existing Code。
3)數(shù)據(jù)驅(qū)動(dòng)
相信數(shù)據(jù)的力量。
4)技術(shù)演進(jìn)
技術(shù)是第一生產(chǎn)力。
三 結(jié)語(yǔ)
Truth lies underneath the skin - 真理永遠(yuǎn)暗藏在表象底下。
對(duì),就在這句話底下。
歡迎各位技術(shù)同路人加入阿里云云原生應(yīng)用研發(fā)平臺(tái) EMAS 團(tuán)隊(duì),我們專注于廣泛的云原生技術(shù)(Backend as a Service、Serverless、DevOps、低代碼平臺(tái)等),致力于為企業(yè)、開發(fā)者提供一站式的應(yīng)用研發(fā)管理服務(wù),內(nèi)推直達(dá):pengqun.pq # alibaba-inc.com,有信必回。

我們?cè)谖⑿派?4小時(shí)期待你的聲音
解答本文疑問(wèn)/技術(shù)咨詢/運(yùn)營(yíng)咨詢/技術(shù)建議/互聯(lián)網(wǎng)交流