DDD 四層微服務架構

大家好,我是 Jensen。一個想和大家一起打怪升級的程序員朋友。

許久未提筆,這段時間,筆者除了奔忙於公司的一大堆項目交付,還在寫業務代碼的過程中,沉澱出了一套 DDD 風格的微服務基礎框架。

作爲一位時不時就斷更的技術自媒體,光打嘴炮是不夠的,總要產出點什麼,所以斷更並不是我本意,再次向大家致歉,爭取個寬大處理。

…… 我錯了,下次還敢……

《趕緊進入正題吧》

0x1

微服務搭建思路

大家看到的這張架構圖並不是空穴來潮,它是通過不斷演變出來的,我們要從 DDD 四層架構、微服務架構兩個維度去融合理解。

這裏的 DDD 四層架構適用於單個服務的工程架構(如圖中的左下部分),就是單體應用的 DDD 四層架構的包劃分方式。

而微服務架構,則是從整體去看,整合多個單體應用,它們之間通過應用 SDK 工程進行 RPC 通訊。

0x2

微服務架構下的應用 SDK

這個工程比較好理解,類似於我們傳統的理解的 RPC 包,或者叫 API 包,在 Maven 工程裏,一般定義爲一個子 Module,裏面主要定義的是 Feign 接口(如 service.XxxFeignService),DTO 對象(contract.dto.XxxRequest/XxxResponse)等等,此外還可以對 FeignService 返回的數據進行清洗與簡單通用的封裝(如 util.XxxUtil),也就是說它還能封裝簡單的業務邏輯。

但需要特別注意:應用 SDK 要往一個大尺度獨立的聚合工程的方向去搭建,它裏面的頂層包要按內部業務系統的維度去隔離,並且它和業務系統不是一對一的關係。

爲什麼要這樣設計?我講個例子你就明白了。

我們公司的業務系統在頂層劃分爲 SaaS 應用和 PaaS 應用,那麼 PaaS 應用對應的應用 SDK 可以命名爲 PaaSSdk,在 PaaSSdk 工程裏,包括了消息中心、ChatAI、應用市場等 PaaS 應用的外部接口封裝與簡單業務邏輯封裝。

這樣做的好處顯而易見——SaaS 應用需要用到 PaaS 應用的接口時,只需要引入 PaaSSdk 即可,原則上這個內部 Sdk 與我們平時引入的外部 Jar 包沒什麼區別,可能只是網關和鑑權體系不一樣罷了。

而且,簡單的業務系統就用一個 module 就好了,沒必要再拆分多個 module,要知道,每引入多一個東西就有更多的不確定性。

所以你也就能理解,爲什麼這裏的應用 Sdk 與業務系統不是一對一的關係,如果是一對一,業務系統勢必要引入大量的 Jar 包,這在維護成本上是個災難。試想一下,如果要用到阿里雲 OSS 的 Jar 包時,你會引入大量 POM 嗎?

0x3

DDD 四層架構下的業務工程

DDD 建模與落地的這幾年,收穫了不少好評,也着實爲業務成功做出了貢獻,優化了大半年,如今終於可以跟大家正式見面了。

先談架構思想:

DDD 四層架構說明:

0x4

集成 D3boot 基礎框架

領導讓你搭個業務系統,如果什麼都從零開始的話,項目週期就太長了。我們在搭建系統的過程中,如果有這麼一個框架,能夠快速解決 CRUD、工程結構劃分等等問題就好了。

D3boot 基礎框架的出現,正是爲了解決這個問題。一般 SpringBoot 只能集成 Spring 體系內的技術棧,但作爲心態更開放的我們,不應把目光聚焦在 Spring 體系內,每家企業都應該有自己的基礎框架。

D3boot,意爲 DDD 工程快速啓動,其中融入了 DDD 領域驅動的架構思想,並且能處處體現充血模型帶來的 CRUD 上的便利,還支持 SaaS 應用的搭建(租戶隔離)。D3boot 框架旨在快速搭建 SaaS 業務系統,減少繁瑣的 CRUD 定義,減少不必要的 xml 代碼書寫。

充血模型的思想體現在對 Model 的繼承,即可實現你想要的 CRUD;而通過領域工廠(Factory 的 build、convert、fill 等方式),又可以利用貧血模型思想的優勢,對複雜的對象進行構建、轉換、填充,彌補了充血模型的不足。

目前我已使用這套輕量級微服務基礎框架,在公司裏的健康管理平臺、消息中臺、工單中臺、社交中臺、ChatAI 等業務系統應用了起來,使用感受一個字:舒服。

而作爲基礎框架,考慮的更多是不同框架集成的問題、功能邊界問題,接下來我給大家一一介紹。

以下是 D3boot 的結構:

一、base:基礎組件

可擴展的基礎組件,下面包括多個子模塊,包括:

  1. base-core:基礎核心組件

定義了基礎核心上下文(如 SpringContext、ThreadContext、BaseContext)、核心契約(如 R 對象、Page 對象、抽象領域事件、業務異常、統一狀態碼等)、核心工具類(如 Bean 轉換工具、Json 轉換工具、業務斷言工具等)。

  1. base-data:基礎數據組件

定義了基礎模型(支持 CRUD 的充血模型)、基礎倉庫及 MybatisPlus 的倉庫實現、數據類型處理器等,支持通過 @TenantId 註解 PO 類租戶字段來隔離租戶數據等。用到數據庫的工程需要依賴此包。

  1. base-mq:基礎 MQ 組件

目前集成了 Kafka 消息隊列,可快速通過註解方式實現 MQ 消費。

  1. base-kit:基礎工具箱

工具類,底下按不同的能力又細分爲緩存類、事件類、語言類、線程類、WEB 類工具。

  1. base-monitor:基礎監控組件

集成 HealthCheck 接口、啓動打印代碼版本功能、日誌告警功能(能把 log.error 的日誌告警到企微機器人 / 釘釘機器人)。

  1. base-web:基礎 WEB 組件

定義了 CRUD 控制器基類 CRUDController、按端劃分的模型控制器接口 ModelController、全局異常增強、全局 R 對象包裝、全局 Feign 異常降級、各類 WEB 攔截器、基礎接口認證功能等。WEB 工程需要依賴此包。

二、base-bom:基礎依賴組件

Maven 的 BOM(Bill of Materials)機制是 Maven 項目中的一個重要概念,它用於管理項目的依賴關係和版本控制。BOM 機制可以幫助開發人員快速構建和維護項目,並且可以確保項目的穩定性和可靠性。

Spring 有自己的 bom 文件,如 spring-boot-dependencies,裏面定義了構建 SpringBoot 工程所需要的依賴。

參考 Spring 的方式,我們把第三方的依賴統一在 base-bom 組件裏進行管理,這樣一來,業務工程只需要引入對應的 dependency 即可(包括定義 D3boot 框架裏的組件版本),不需要再在業務系統過多地指定用哪個版本,達到版本統一的效果。

三、base-contract-parent:業務 Contract 父工程組件

作爲應用 SDK 工程的父 POM,快速搭建應用 SDK。

四、base-parent:業務父工程組件

作爲業務工程的父 POM,快速搭建業務系統。

五、ddd-demo:DDDDemo 工程

基於 D3boot 框架搭建的 DDD 四層架構風格的業務工程,寫得比較粗糙,具體參考架構圖的實現爲準。

0x5

寫在最後

我一直認爲,基礎框架不能寫得太重,公司的公共組件不應放在基礎框架工程內實現,而是另外定製。在基礎框架的開發過程中,我不斷汲取前輩的優秀代碼經驗,並融入自己的代碼特色,提煉高複用性代碼,並對中間件進行淺封裝。

此外,本着技術開放的心態,這套基礎框架決定走開源路線,大家可以下載 Deploy 到自己的私倉使用,基於自己公司的業務進一步定製自己的基礎組件。

Gitee 源碼地址:https://gitee.com/jensvn/d3boot(例行賒 Star)

D3boot 基礎框架具體的使用方式見源碼的 README.md 文件,這裏不再贅述。

最後,非常感謝大家能夠看到這裏,有任何技術上的問題,可以向我的 AI 助理諮詢(https://www.doubao.com/bot/eYivWxHr),當然也可以私 V 我:Jensvn,獲得框架使用上的支持,也歡迎大家能給這個框架提出寶貴的優化建議。

作者:Jensen

專注分享程序員日常 / 架構技術 / 職場乾貨

本文由 Readfog 進行 AMP 轉碼,版權歸原作者所有。
來源https://mp.weixin.qq.com/s/mcNC9mSoEOzKv-MD2LwtcQ?poc_token=HLGAYGWjxeHrtkR4fiDfC9lqFaPLAxuWQnlu38Mx