1. 程式人生 > >微服務踩坑之邊界

微服務踩坑之邊界

依賴關系 核心 不知道 為我 美好 正是 我們 article ade

近年來微服務/SOA很是流行,我們團隊趕時髦,也玩了玩。雖然用的時間還不長,但也已經踩過不少坑。今天想記錄下自己對邊界問題的一些思考。

很多人在談起微服務時,總是會很自豪的說,微服務為我們提供了高內聚低耦合的明顯好處,因為微服務強化了模塊化的概念。但是, 如何模塊化,如何明確的定義模塊的邊界,卻很少有人提及,而這正是微服務架構的難點,也恰恰是開發人員技術能力的體現。如何正確的定義模塊的邊界,似乎還沒人總結出一套理論原則。

當我們將一個單體服務進行模塊化拆分時,我們總是能夠很輕易地找到模塊邊界。那些不知道該放到哪個模塊裏的代碼,便是我們模塊邊界的所在。在整理這些棘手的代碼時,就是一個劃分邊界的過程。如果實在挪不開,這說明他們本就該屬於同一個模塊中或者他們上層應該還有一個服務。

在實際開發過程中,對單體服務進行重構的時候並不多。更多的時候,我們一開始做服務架構時便在使用微服務的架構模式。隨著系統需求的漸漸復雜化,我們會發現,服務間的耦合越來越嚴重,甚至出現了循環依賴。這種時候我們不得不質疑自己,當初的模塊是否劃分的足夠清晰。

我們做了一個借貸系統。系統中有兩個核心服務,借款與還款。

借款的核心需求:

A。用戶可以借款;

B。用戶可以查看自己的借款明細。包括借款時間/金額等。

還款的核心需求:

A。用戶可以對借款進行還款;

B。用戶可以查看還款明細。

一開始,一切都顯得很美好。我們遵循kiss原則,讓各個模塊盡量簡單;同時為了項目組開發的便利,我們盡量將模塊細化。於是劃分了一個借款模塊,一個還款模塊。此時,我們服務的依賴關系很清晰。還款模塊會單向依賴借款模塊。還款成功後,通過消息進行解耦,對借款余額進行更新。

但隨著系統需求的變化,借款詳情中需要展示用戶當前的還款情況,並計算未來的還款計劃,這些都需要依賴還款模塊。這種情況下,我們便形成了雙向依賴的循環。借款模塊會依賴還款模塊,還款模塊也依賴了借款模塊。

這種情況下,出於項目進度,我們並沒有進行任何的處理,而是任由雙向依賴的發生,甚至,在還款模塊直接依賴了借款的數據庫來達到快速開發的目的。但這也為日後欠了技術債。

A。循環依賴日後可能會帶來循環調用,這種結構上允許的閉環調用,很有可能在將來造成無意識的遞歸,讓系統崩潰。

B。項目構建時,A/B模塊的循環依賴,造成無法構建甚至循環構建。對我們系統的持續集成造成了障礙。

C。兩個模塊通過數據庫進行共享來達到代碼解耦,以後數據表結構若發生變化,代碼維護將極其困難。

這種事情,相信很多人都遇到過,解決方法或許也與我們當前的類似。但是,其實這裏有很好的辦法來解決這個問題。我們只需要在借款模塊與還款模塊的上層,抽象出一個借還款核心模塊,其負責將兩個模塊的耦合嚴重的業務進行整合,比如由他來發現借款訂單,通過調用還款模塊來計算還款計劃,便可以消除整個循環依賴了。但是,這樣會造成這種中間模塊越來越多,對以後的系統維護又造成了一定難度。但這也不失為一種方法。

所以很多時候在想,這兩個模塊一開始是否劃分的太細,是否一開始就應該在一起呢?我們劃分模塊邊界的依據又是什麽呢?歡迎大家一起探討。

微服務踩坑之邊界