你好呀,我是why。
是的,我又發現了一個寶藏,又迫不及待的想分享給大家。
這個寶藏是一個開源專案,或者叫做一本開源的書。
讓我意難平的是,這本寫的如此具有學習潛力和指導意義的開源書,目前才 887 個 Star。
趕得早不如趕得巧,我就是第 888 個點 Star 的人,聽起來就很有緣分的樣子:
https://icyfenix.cn/
先看一下我看了之後整理的思維導圖吧:
看不清沒關係,文末會給你領取連結的。
看完之後我個人的一個感受是:
關於分散式架構方向,寫的很多很全。而且都是筆者一路走過來的經驗之談,濃縮在了文章裡面。
對的起首頁的這一句口號:構建可靠的大型分散式系統。
誰寫的?
那麼這個開源書的作者是誰呢?
周志明。
是的,就是你想到的那個寫了 JVM 的書的男人。
其實你仔細看周佬寫的自我介紹,很有小細節。
程式設計師、研究員、作者、佈道師這四個職業,排在第一的是最沒有噱頭的“程式設計師”一職。
而在程式設計師裡面,給自己的描述是:
一名兼職一些管理與研究工作的程式設計師。
其實關於這個點,我看過周佬的一些公開場合的自我介紹,都是說自己是一個“兼職一些管理工作的程式設計師”,給自己這樣的人設標籤。
他在自己寫的《程式設計師之路》一文中解釋過這個標籤。
他想要透過這個標籤表達的是對於一枚程式設計師,以後是想要發展為一個架構師還是研發管理者,都不要輕易地離開技術領域的一線前沿,離開技術、放棄編碼的決定很可能會像你高考之後放下的數學、生物、地理等知識那樣,一旦放手,畢生就很難有機會再重新撿起來。
當你放下程式碼的時間越長,久而久之,你對程式碼、技術、產品狀態與團隊研發狀態的理解,漸漸的會和團隊成員產生了偏差錯位,喪失了細節上給予指導的能力,喪失了專業問題上提出接地氣解決方案的能力,只能在無法短期難以校驗對錯的大戰略方向提意見。
在會議、流程及團隊管理措施上下功夫,在職業經理人式的宣講與彙報上尋找存在感。
此刻,你便從團隊的導師變成了管理者,最終你與團隊的關係,從攜手並肩奮鬥的夥伴,完全演變成只能靠公司制度與管理職位的權力來維繫僱傭關係。
我能理解周佬說的現象,其實是一個非常普遍的現象。甚至有的朋友走上管理崗位的目標就是不再寫程式碼了,基於當前的市場和行業現狀,這樣的選擇是無可厚非的。
只是,有沒有那麼一點點可能,不要完全拋棄程式碼。這也需要是你和團隊之間的最行之有效的紐帶。
就像《程式碼整潔之道》一書中說的:
軟體架構師本身就是最好的程式設計師,他們會一直編寫程式碼,雖然可能不會像其他程式設計師輸出的程式碼量那樣多,但是隻有持續地程式設計,才能確保他們遇見其他程式設計師所面對的問題,體會其他程式設計師心中的感受,因此如果不程式設計,他們亦將無法勝任軟體架構這項工作。
這本《鳳凰架構》,周佬自己對它的定位是這樣的:
給開發人員整理的關於軟體架構方面的技能地圖,同時系統的梳理自己的知識,並配備了對應技術方案的演示程式。
真的是一件利人利己的事情。
我本來的想法是先帶著大家囫圇吞棗的走一圈這一本書,主要起到一個介紹的作用。
但是越寫越不得勁的感覺。因為即使我寫的這麼賣力認真,都沒有體現出這本書的價值的千分之一。
你得自己去讀,你才知道我沒有騙你:
這真的是個寶藏啊!
所以我決定換個思路,告訴大家這裡面有什麼就行了,其實就是書中的探索起步一小節。
探索起步
這是探索起步的更新日誌部分,可以看到周佬對於該專案一直在進行維護新內容:
而對於已有的內容,其中的錯別字、不通順的地方、含義不清的地方,他也在抽時間修改,最近的一次修改就是 6 月 6 日,昨天,上週日:
所以,相比於其他的大部分網上的文章來說,會更加實時、系統、優質一點。
全書分為五大部分和兩個篇外,而為了讓你快速定位到合適自己的部分,周佬也細心的介紹了每一部分對應的讀者型別。
引導篇 探索起步:這部分面向於準備對文件介紹的內容親身實踐的探索者。 第一部分 演進中的架構:這部分適合所有開發者,但尤其推薦剛剛從單體架構向微服務架構轉型的開發者去閱讀。 第二部分 架構師的視角:這部分討論與風格無關的架構知識,適合所有技術架構師、系統設計、開發人員。 第三部分 分散式的基石:這部分面向於使用分散式架構的開發人員。 第四部分 不可變基礎設施:這部分面向於基礎設施運維人員、技術平臺的開發者。 第五部分 技術方法論:這部分面向於在企業中能對重要技術決策進行拍板的決策者。 篇外 隨筆文章:這部分無特定讀者物件,內容是筆者日常文章的整理。 篇外 附錄:這部分面向剛開始接觸雲原生環境的設計者、開發者。
其中第一部分的我讀完之後做的思維導圖如下:
可以大家對於其中的後微服務時代和無服務時代稍微有點陌生,但是我換個英文名稱,大家就應該是非常熟悉了。
後微服務時代其實就是雲原生時代,Cloud Native。
而無服務其實就是 Serverless。
但是需要注意的是,周佬把 Serverless 排在了 Cloud Native 之後,其實它們兩者並沒有繼承替代關係。不要因為周老對於兩者的書寫順序產生了“無服務就會比微服務更加先進”的錯誤想法。
周佬對於這兩者之間的關係描述是這樣的:
如果說微服務架構是分散式系統這條路當前所能做到的極致,那無服務架構,也許就是“不分散式”的雲端系統這條路的起點。
第二部分的思維導圖如下:
這一部分主要聊了我們做分散式服務時,一定會涉及到的問題,比如:遠端服務呼叫(RPC)、分散式事務的處理、多級分流、架構安全。
我個人認為這一部分是乾貨滿滿的。
其中訪問遠端服務,對 RPC 和 REST 從各自的起源開始進行了一個詳盡的描述:
事務處理小節,大家可以看看“共享事務”的概念,其實我發現有一部分號稱是微服務架構的專案,走向了“共享事務”的路線。
我認為這是一種偽分散式。
透明多級分流系統從客戶端到網路在到服務端的拆析,這是一種上帝視角的描述,而這一部分的主題就是“架構師的視角”。
架構師就應該是從這樣的一個比較統籌規劃的角度去看待系統,不必進入到具體系統的細枝末節中去:
第三部分分散式的基石:
共識演算法、服務發現、流量治理、網路通訊、監控預警共同構成了分散式的基石。
可以說如果是一個分散式的服務,都能找到上面的這些關鍵詞的影子。
有些是應用系統自己做的。
有些是開源框架就幫你搞定了,你甚至不知道它們的存在。
但是上面的諸如流量治理和監控預警(可觀察性)不是一個分散式服務一開始搭建時所必須的。
大多數情況下,剛剛搭建好的分散式都處於一個蠻荒狀態。
隨著時間推進和業務的發展,會慢慢補充上流量治理和監控預警。
也就是說如果想要分散式服務發展的監控可控,那麼這些東西都是應該有的。
“基石”一詞,像是手術刀一樣精準。
來到了第四部分,不可變基礎設施:
到這裡我們就要從微服務走向雲原生了。
在這一章,周佬以容器、編排系統和服務網格的發展為主線,介紹虛擬化容器與服務網格是如何模糊掉軟體與硬體之間的界限,如何在基礎設施與通訊層面上幫助微服務隱藏複雜性,解決原本只能由程式設計師通過軟體程式設計來解決的分散式問題。
接下來的“技術方法論”屬於微服務避坑指南,從目的、前提、邊界、治理四個角度去闡述如何更好的使用微服務。
最後一部分是“隨筆文章”:
其中的《雲原生時代,Java 的危與機》和《程式設計師之路》這兩篇文章,建議大家反覆觀看。
前者是技術方向的,後者是軟技能方向的。
讀完《Java 的危與機》,我感受到的是一場關於 Java 的自我革命已經悄然開始了。
Java 並不是一個優秀的開發語言,這一點我是非常承認且確定的。但是 Java 有一個龐大的使用者群體和異常豐富的生態,這是它的護城河。所以短時間內還倒不下來。
但是大風起於青萍之末。風雨欲來,而包括我在內的很多人都渾然不知。
在文章裡面,周佬有這樣的一段話:
Java 支援提前編譯最大的困難在於它是一門動態連結的語言,它假設程式的程式碼空間是開放的(Open World),允許在程式的任何時候通過類載入器去載入新的類,作為程式的一部分執行。要進行提前編譯,就必須放棄這部分動態性,假設程式的程式碼空間是封閉的(Closed World),所有要執行的程式碼都必須在編譯期全部可知。這一點不僅僅影響到了類載入器的正常運作,除了無法再動態載入外,反射(通過反射可以呼叫在編譯期不可知的方法)、動態代理、位元組碼生成庫(如 CGLib)等一切會執行時產生新程式碼的功能都不再可用,如果將這些基礎能力直接抽離掉,Helloworld 還是能跑起來,但 Spring 肯定跑不起來,Hibernate 也跑不起來,大部分的生產力工具都跑不起來,整個 Java 生態中絕大多數上層建築都會轟然崩塌。
“整個 Java 生態中絕大多數上層建築都會轟然崩塌。”
所以,Java 的這次變革屬於要釜底抽薪。
讀完《Java 的危與機》之後,你再去看《Graal VM》一文,你就明白了:為什麼說 Graal VM 的成功與否,與 Java 的前途命運息息相關。
而這場變革已然悄悄開始,比如說一個小點:
大多數執行期對位元組碼的生成和修改操作,在 Graal VM 看來都是無法接受的。
但是比如 CGLIB 就是通過執行時產生位元組碼(生成代理類的子類)來做動態代理的。
這是目前的主流形式。
現在因為Graal VM 支援不了,所以必須由和框架一起來共同解決。
因此自 Spring Framework 5.2 起,@Configuration 註解中加入了一個新的 proxyBeanMethods 引數,設定為 false 則可避免 Spring 對與非介面型別的 Bean 進行代理。
同樣地,對應在 Spring Boot 2.2 中,@SpringBootApplication 註解也增加了 proxyBeanMethods 引數,通常採用 Graal VM 去構建的 Spring Boot 本地應用都需要設定該引數。
我最喜歡的還是技術演示工程部分,直接把專案 Demo 都給你準備好了,開箱即用:
而且周佬寫的這個開源專案有個特點,引用的部分會給出具體的官方的地址。嚴謹又權威,比如寫到專案中用到的技術元件的時候:
一個問答
在專案裡面,我還發現了一個問答。
問題和回答都非常的好,搬運過來給大家看看。
評論區:https://icyfenix.cn/methodology/forward-msa/prerequest.html
問題如下:
周大哥,看到了您說的馬太效應。再聯想到之前您講的軟體涅槃,而完善的微服務體系允許服務有涅槃的過程,有強大的容錯能力。微服務發展又如此迅猛,覺得馬太效應真的不遠。
我不禁對最需要掌握的技能進行了思考,併產生了更強的焦慮感。
我是一名有七年工作經驗的java開發工程師,28歲,目前在一家北京的傳統資訊軟體技術公司,工資相對計算機行業偏低。
侷限在java語言來說,jvm調優與併發程式設計等比較高階的能力,是不是就很不關鍵了?
jvm我讀了您寫的《深入理解Java虛擬機器:JVM高階特性與最佳實踐》的第二版與第三版,由於工作中鮮有機會實踐,只停留在一些理論理解,而缺失實踐,理論知識也會淡忘。
併發程式設計讀過《Java併發程式設計實戰》,對併發程式設計有些瞭解,也有一些實踐,一般水平。
微服務公司並沒有用起來,實踐經驗也缺少。遠端呼叫、分散式事務、註冊中心、配置中心、熔斷、限流等知識,通過看視訊跟您的這個文件有一些瞭解。
java基礎知識,經過這些年的磨練,是挺紮實了,spring能熟練使用。
常用設計模式有了解,也理解的比較到位。
我不想淪為螺絲釘。
我應該提升自己的哪些能力呢?
這些年只是做到了勝任分配給自己的工作。
現在發現自己缺少前瞻性思考,缺少對自己職業生涯的把控。
我現在想把握自己的職業生涯,請周大哥給一些指導。
我會通過招聘市場去挖掘市場需求,做整理,進行思考。
但是迫不及待的想跟您述說一下,請您不吝賜教,希望我的請求不是很唐突。
這個問題其實是很具有普遍性的:學了沒地方實踐,慢慢就忘記了。理論學了一大堆,聊起來可以談笑風生,但是就是沒有實際使用過。自己就是一顆螺絲釘。
周佬的回覆如下:
寫這文章不是為了販賣焦慮,我也沒有能力指導別人的職業生涯,但針對“應該提升自己的哪些能力”這類問題,我以前被問過很多次,這裡可以重複一下。
我的建議就兩個:
不要輕視不直接產生實踐價值的知識; 不要對陷入已經被你熟練掌握的技術中不能自拔。
為了便於你理解,我做一個很土的比喻,把程式設計師提升自己類比成武俠中的練功,軟體中的技能其實有很明顯的“內力”和“武功”之分,譬如你提到的Java虛擬機器,這類知識不僅是你在工作中鮮有機會實踐,我也是差不多的。
大學計算機課程中,以“原理”二字結尾的課程,譬如計算機原理、作業系統原理、編譯原理、資料庫原理,等等,對絕大多數人而言,都不太會去設計處理器邏輯電路、設計程式語言和編譯器,開發作業系統核心。
這些都有很經典的書:編譯原理的龍書,計算機體系結構和程式執行的CSAPP,分散式與資料庫原理的DDIA、作業系統原理的MOS,等等。這些書系統嚴謹全面,但可讀性並不優秀,在B站/Coursera刷這些書作者們的公開課翻譯視訊也許是更好的方法。
這些技能能夠輔助你去思考和分析問題,但是很難直接為你解決生產中的問題,以實踐價值,就是以工作中是否有機會用到來衡量它們的作用是不合適的。
但這些課程之所以會是必修,是因為學習它們,能夠為一名程式設計師的知識框架構築好基礎。
這話聽起來很教條,可是當你一旦建立了相對完備穩固的知識框架,發現遇到的新知識、新技術,能夠很自然地安放在已有知識體系的某個位置上,能夠清楚感知到語言、技術、框架的設計意圖和目標,甚至能共鳴到設計者當時所想,就會產生一種理所當然的感覺。
這樣你接受新知識的認知負荷就會比別人更低,掌握起來更快速,理解起來更深刻。
我在這文件開篇中所說的,寫這部文件是以整理自己的知識框架為目的,並非場面話,這點的確就是程式設計師如何學習新知識的關鍵,在知識快速迭代IT業界,這也是決定一名程式設計師能力上限有多高的根本因素。
相對的,那些具體的、用來解決生產中問題的技術和方法,譬如你提到的Spring、設計模式,我將其類比為“武功”。
這當然也是重要的,只有內力沒有武功無法行走江湖,空有一身理論,但寫不出程式碼來(包括那些只定大方向的架構師、設計者),我認為不肯定是合格的程式設計師,也很難指望能成為一名出色的技術領導(難以服眾)。
但是具體的“武功”應該是能夠快速撿起的,也能快速“忘掉”的,就是避免將一件事情做熟了,就一直陷在這件事情裡面,避免拿到一把好的錘子,就看著一切問題都像是釘子。
很多程式設計師都抱怨,自己是CRUD Boy,自己在業務邏輯中打滾,沒有機會接觸底層的或者前瞻性的技術,所以自己技術難以提升。
這裡當然有客觀原因的存在,但往往也是受到了主觀原因放大。
程式設計師其實與舊時代的手工技藝者差不多,骨子裡就有天生的技術崇拜,你寫的程式碼比別人的優雅健壯高效能,你殺BUG比別人快速乾淨利索,就會受到大家的認可。
很自然地,更多偏向技術偏向深層次的工作就會落到你這裡,至少你會有話語權,有選擇做哪些事情的權利,是否要一直在圍繞著你最熟悉的業務去打滾是由你決定的。
學習武藝成為“武林高手”,是成為大BOSS之後才不必長期面對蝦兵蟹將的糾纏。
學習一門具體的技術,也是為了用它解決好問題,然後把它忘掉,去掌握那些更深層次的、更前沿,而且自己還不會的技術。
最後還有個追問和回答如下:
不知道大家看到這個回答後的感受是怎麼樣的。
至少對我而言,振聾發聵。特別是這兩點:
不要輕視不直接產生實踐價值的知識; 不要對陷入已經被你熟練掌握的技術中不能自拔。
已經放入手機標籤中,時常提醒自己。
與君共勉。