如何解讀《微信技術總監談架構:微信之道——大道至簡》
[http://www.52im.net/thread-201-1-1.html]學習一下
一、前言
最近在朋友圈看到有人分享騰訊微信技術總監周顥的一個技術報告,題目是《微信技術總監談架構:微信之道——大道至簡》(演講全文整理、演講PPT講稿下載),我也轉發了一下。然後就被本司妹子看到了,非讓我解釋一下。
無奈微信的技術人員出來交流的太少了,只能寫下這篇淺顯的文章,通俗的解釋一下微信背後的技術力量。
二、敏捷
在微信的技術報告中,通篇演講所說的內容,其實都是為了兩個字服務:“敏捷”。首先,我們要先解釋一下敏捷。
在軟體領域,敏捷軟體開發實際上已經是一種術語,它又稱敏捷開發,是一種從1990年代開始逐漸引起廣泛關注的一些新型軟體開發方法,是一種應對快速變化的需求的一種軟體開發能力。敏捷 (Agile)也是一股思潮, 它包括了好幾種軟體開發的方法論 (methodology); 這些方法論又是建立在許多業界證明行之有效的最佳實踐方法 (best practices) 上面的,例如:Software Development Rhythms 、ASD/Adaptive Software Development、Scrum、XP Extreme Programming等等。敏捷開發最終的目的,都是使軟體能夠快速迭代和交付。
So,簡單來說就是為了軟體快速迭代和交付,微信的技術做了什麼事情,是如何做的。
在報告中,有一段話的意思是這樣的:微信的成功來源於產品決策的成功,為了給產品決策最大的自由度和能力,微信的技術允許釋出前十分鐘的需求變更。做到這個事情非常非常牛,我必須要解釋一下它的難度。
一個人的精力是有限的也是容易出錯的,所以,在傳統軟體開發流程中,規定了一系列的規範來保證軟體能夠不出錯。一個需求的完整開發流程大致是這樣的:需求提出,技術分析,開發,自測,模組測試,聯調測試,灰度測試,完整發布。
即使已經做了這麼多步的保證,所有故障的80%仍然是釋出導致的。為了保證服務的穩定性——微信的及格線是99.95%——開發中的變更一般是很昂貴的,因為需要把已經走過的步驟再重走一遍。所以大部分軟體開發對於開發中的需求變更都是非常忌諱的,對於開發人員來說也是如此,誰也不想辛苦完成的東西再重新來一遍,或者因為頻繁的需求變更導致測試不完全而出現故障。放張漫畫感受一下程式設計師的心情
對於微信來說,更是如此。我估計微信內部有上百個模組,幾千臺伺服器,任意一個模組、程式出現問題都可能會影響到微信的正常服務。尤其是在釋出前十分鐘還允許變更,需要一套強大的技術、測試和監控系統才能支援如此的任性。
對比一下前東家(不能說名字,也算個大廠),固定每週釋出兩次,釋出持續時間4個小時。例如,週二釋出一次,那週二釋出的所有需求在週一上午已經確定了;如果釋出失敗了,第二天繼續發這個。我曾經見過有一個需求一週都沒有發上去。
在如此困難的情況下,微信憑藉了幾個思路來做到如此敏捷,後面我來依次解釋一下。
三、努力減少人為的錯誤
既然人的問題如此突出,那麼,要想提高效率做到敏捷,一定要先從人的方面著手。
微信的這篇報告提出的思路是:大系統小做+基礎元件。應該說,這是一個工業界普遍的解決思路。
我們一般人看到的軟體,例如微信,就是在自己手機上執行的一個程式,無所謂大小系統,所有的功能都集中在一起,集中在一個軟體中,無需也不能拆分。但在這種服務類軟體例如微信、微博等,還有一個更加龐大在後端伺服器的程式。
第一,一般來說,後端服務的邏輯相對前端軟體來說更復雜:
後端程式要做各種計算、驗證和儲存的功能。如果前端軟體端的程式碼有幾萬行的話,後端服務的程式碼一般要有幾十萬或者上百萬行。例如,簡單的登入,在前端只不過發一個登入的請求到後端伺服器,而伺服器要做的事情呢,從資料庫中取得你的使用者名稱和密碼驗證資訊,把請求過來的使用者名稱加密密碼(密碼不能明文儲存,要經過一些複雜的計算過程取得一個加密的東西)和資料庫的進行驗證;判斷是否一個異常登入(還要從資料庫取的最近的登入資訊);判斷是否過頻繁登入(防止惡意伺服器攻擊);等這些都做完了,才能返回說登入成功了。
第二,伺服器端程式要比前端軟體層承載更多的請求和更大的壓力:
還是以上一點說的登入舉例,所有的那些操作,伺服器端要在100ms之內處理完成;同時,這種登入請求每一秒都有幾萬或者十幾萬。至少現在,一臺普通伺服器是無法同時處理這麼多請求的,這就表示後端程式要部署很多臺機器才行,這也造成了更多的複雜性。
如此複雜的系統,一個人是萬萬駕馭不了的。那麼,唯一的選擇就是把複雜變成簡單。
首先,針對邏輯複雜的特點,我們會把幾十萬行程式碼組成的系統進行拆分,拆分一般是依據功能性,例如:註冊登入、訊息邏輯、漂流瓶等等,然後把這些程式分別部署到不同的伺服器上。
放一頁報告的PPT:
這張圖應該是微信伺服器端的主要邏輯和部署結構,其中每一個機器的圖都是一組(很多臺)伺服器。這樣的好處很明顯,當拆分後,一個人只需要瞭解其中某一個模組的程式即可,不再需要詳細的瞭解其他東西是怎麼執行的。
但是,邏輯的複雜性解決了,又出現了另外一個問題,就是遠端呼叫的複雜度和穩定性問題。
定義一下遠端呼叫(RPC):
In computer science, a remote procedure call (RPC) is an inter-process communication that allows a computer program to cause a subroutine or procedure to execute in another address space (commonly on another computer on a shared network) without the programmer explicitly coding the details for this remote interaction.
簡單來說,要呼叫的程式在另外一臺物理伺服器上。
而有網路參與的情況下,可靠性要比單機呼叫低一個等級,為了彌補這個可靠性的降低,需要做很多異常情況處理,例如:網路斷了、有一次呼叫非常慢,有一臺伺服器沒有響應了等等。
我們前面又提到,微信只有幾十上百個模組在同時執行,不能要求每一個模組都把這些複雜的東西都做一次,並且受限於經驗的問題,每個人做的都會不一樣會有遺漏,這個時候,遠端服務框架這個基礎元件就應運而生了。
在報告中的一頁PPT,提到了兩個基礎元件:
就是屬於遠端服務框架中的一部分,它能夠讓開發人員很簡單的使用,10分鐘即可寫一個遠端呼叫,並且各種錯誤都由框架處理了,只要很開心的關心我們的業務是如何執行的即可。Yes,開發快了好多倍。
當然,遠端服務框架是一個很複雜和系統的工程,他至少應該關心4個方面:
- 開發的簡易型
- 服務的分散式呼叫鏈及服務狀態的跟蹤統計
- 服務的配置管理,包括服務發現、負載均衡和依賴管理
- 服務之間的排程和生命週期管理
阿里巴巴公司曾經開源過一套遠端服務框架:dubbo,摘一張它的程式整體設計圖:
在報告中還提到一個很重要的基礎元件,儲存元件,它遮蔽了容災擴容等複雜問題。
儲存是如此重要,所有的內容最終都要落到儲存上;儲存是如此重要,大部分的操作最終都要從儲存讀資料。正因為儲存的重要,所以它又顯的非常脆弱,任何一點小的問題,一定會影響一大批使用者。
在這種情況下,務必要進行減少儲存的出錯機率,並且讓上層遮蔽這些處理,讓開發人員專注於自己的模組,這種思想和前面說的遠端呼叫框架思路是一致的。
在報告中,提到了4中容災模型,前面兩種分別是主備、雙寫,這個就不多說了,主要說下另外兩種。
Set模型+雙寫:
這裡,報告裡說的不慎明確,他說能夠實現完全一致的備份副本,但是隻能支援追加寫以及需要外部索引,類似簡化版的GoogleFS,主要儲存圖片和音訊。這裡我腦補一下,希望能猜中。
讀到這些關鍵字,除了GoogleFS,我還想起了一個東西:bitcask模型。
bitcask模型有一個外部索引,一般是放到記憶體中,儲存了每一個key所在的檔案位置和value長度及位置;在寫入的時候,追加寫入檔案中,並更新索引內容,把位置指向新的磁碟位置。bitcask模型的好處是對於機械磁碟友好,寫吞吐量大,資料持久化好不用擔心crash後的資料丟失問題。這種模型就和報告所說的特點很像了,只不過把記憶體索引放到了外部一個單獨的服務裡面。當一個Set寫入失敗的時候,只需要寫入另外一個,並把索引寫入索引服務即可;讀的時候,先讀索引服務,然後去某一個Set中讀取資料。因為每一個Set都做了主備模型,並不特別擔心不可讀。
四、及時發現錯誤
說了這麼多,我們做了好多事情來儘量避免問題的產生,提高生產效率,但是遺憾的是,錯誤永遠不可避免,這個時候,能夠及時發現錯誤並解決它,影響儘量少的人就成了關鍵。微信給出的答案是:一套簡單易用的監控系統+自動報警+灰度上線
對於這個,我其實沒有啥好說的,都應該能很好的理解,任何軟體服務的監控工作都是必不可少的。不過聽視訊上說的,微信5分鐘即可部署好一個監控點並設定好報警閾值,完成監控和自動報警的工作,這個還是很牛的。
還有一項技術是灰度上線。顧名思義,灰度介於黑與白之間。在這裡的意義就是,上線時只上線一部分,目的是用一部分使用者檢測程式碼的正確性,如果出現異常可以迅速的回到之前正確的程式碼上,實現影響儘量少的使用者。
從報告給出的截圖看,微信可以實現上線時任意選擇要上線的伺服器。如果上線有問題,也只會影響到訪問到問題伺服器的使用者。當一臺伺服器上線驗證沒有問題,可以選擇多幾臺上線,最後再上線全部伺服器。這樣就減少了很多的風險,有更大的容錯性。
相關文章
- 讀《大道至簡》有感
- 大道至簡讀後感
- 《大道至簡》讀後感
- 微信域名防封技術,微信域名總是被封如何解決
- 大道至簡的架構設計思想之:封裝(C系架構設計法,sishuok)架構封裝
- 大道至簡觀後感
- CTO、技術總監、首席架構師的區別架構
- 微信活碼技術如何解決微信群二維碼失效問題
- 讀大道至簡之我見3——團隊建設
- 讀書筆記 之《軟體架構設計: 大型網站技術架構與業務架構融合之道》筆記架構網站
- nginx大道至簡之反向代理Nginx
- 大道至簡的養生方法
- 讀《大道至簡:軟體工程實踐者的思想》有感軟體工程
- 談談 Android MVP 架構 | 掘金技術徵文AndroidMVP架構
- 大道至簡之redux原始碼分析Redux原始碼
- 微信域名防封技術分享,微信中主流的微信域名防封技術都在這裡!
- 《大道至簡--軟體工程實踐者的思想》讀後感軟體工程
- 《大道至簡——軟體工程實踐者的思想》讀後感軟體工程
- 微信域名防封技術,微信域名總是被遮蔽要怎麼解決
- Redux技術架構簡介(一)Redux架構
- 微信小程式錯誤監控方法談微信小程式
- 微信域名防封技術-微信域名封禁檢測
- 大道至簡–API設計的美學API
- Golang 受歡迎的原因:大道至簡Golang
- Steve Jobs-06-大道至簡(simplicity)
- 大道至簡--API設計的美學API
- 程式設計師要懂得“大道至簡”程式設計師
- 大道至簡第一章--java虛擬碼讀後感Java
- 技術總監
- Dubbo Mesh 總體技術架構方案架構
- 微信域名防封技術、微信域名檢測技術的常見問題解答
- 微信團隊原創分享:iOS版微信的記憶體監控系統技術實踐iOS記憶體
- 簡陋至極:微信小程式日曆元件(思路)微信小程式元件
- 微信支付技術解決方案
- Laikelib淺談區塊鏈技術架構AI區塊鏈架構
- 《大道至簡》創作參考筆記連結彙總(持續更新)筆記
- 豆瓣的架構—專訪豆瓣網站的技術總監洪強寧架構網站
- 談談微信小程式微信小程式