Action On DDD

Action On DDD

常見的開發方式

MVC貧血模型

最多見的開發模式傳統EJB開發時提倡的開發模式,是經過算法調用數據對象的getter/setter方法修改數據,再將數據存儲起來的過程。算法

在MVC下,常見的模式是controller層中經過一部分算法判斷數據對象的數據是否符合業務須要,在service中經過另外一部分算法按照規則業務規則修改數據分別調用不一樣dao將數據更新或存儲起來。數據庫

優勢:架構

簡單邏輯場景開發快,實現簡單。併發

服務化後通訊時傳送的對象簡潔高效框架

缺點:微服務

複雜邏輯場景下,代碼冗長難懂,維護困難。優化

代碼邏輯和業務邏輯的直接關聯度低,在沒有註釋的狀況下其它人很難經過代碼瞭解業務場景。搜索引擎

代碼耦合度很高,難以免出現「上帝類」的狀況。spa

 

評價:設計

數據喂機器的開發方式,特別適合有大量表單錄入的系統,對業務邏輯的表現能力差,複雜業務場景維護困難。

 

關於領域驅動實現的方式

核心點:領域驅動是將業務功能限制在特定領域進行劃分後,專一於某些特定領域的開發方式,它的最佳實現是領域自治,即領域內的對象(聚合根)自身僅能管理本身的數據和狀態,這樣避免了領域對象相互污染的狀況。領域驅動關心的是領域對象是什麼,而不是對象作什麼。

例如:轉帳行爲中,領域關注的核心概念是 「帳戶(Account)」,而不是日誌,可是根據業務需求須要在轉帳進行的過程當中寫入日誌。爲了完成業務須要,咱們在帳戶金額變更的過程當中不得不加入日誌寫入的行爲邏輯:

class Account{

AccountLog accountLog;

// 方法內不得不集成了日誌寫入操做

void reduce(BigDecimal amount){

//...

accountLog.writeReduceLog(accountId,amount);

//...

}

}

咱們發現,爲了執行一個與領域內無關的操做,不得爲了業務須要引入一個領域外的對象,致使Account對象領域被污染。

 

DCI

DCI是數據Data 場景Context 交互Interactions的簡稱,DCI是一種特別關注行爲的模式(能夠對應GoF行爲模式),由MVC模式提出者Trygve Reenskaug提出。

Trygve Reenskaug認爲數據Data應當是靜態的,即數據自己不能有動做(你見過表格本身填寫本身的嗎?),可是數據反應了一個對象的狀態。

若是要想讓數據可以執行各類行爲則須要將數據放入角色模型(Role Model)中,由角色模型驅動完成數據變動 (假設PersonData反應了一我的的基本信息,則若是想讓這我的去工做,則必須將PersonData 放入Worker角色中)。

協做交互模型(Collaboration Model)則是驅動角色模型如何動做的關鍵,若是咱們須要角色們協調起來去完成某個業務場景,則必須經過協做交互模型來進行(上個例子提到的Worker,若是須要執行放款操做,則還須要與對應的Account角色進行交互)。

對於DCI實現的領域驅動設計,Role和Collaboration(即Interactions)纔是真正的領域模型,Context和Data則更面向於程序,由Context準備好足夠的程序組件和Data,讓數據經過協做模型和角色模型完成一系列動做,再將獲得的Data進行存儲的。

 

評價:

與傳統Evans提倡的DDD模型略有不一樣,Evans提倡領域自治,即模型的數據由本身更新,DCI則是將數據分離更新。在實踐過程當中,DCI架構更像是一個完整的場景劇的表演過程,由Context爲角色Role準備表演的「舞臺」,舞臺中包括了各類各樣的必要設施,角色們只要根據劇本Collaboration進行表演便可,最後獲得的數據是角色自己的完結狀態。

 

CQRS

命令查詢的責任分離Command Query Responsibility Segregation (簡稱CQRS)模式是一種架構體系模式,可以使改變模型的狀態的命令和模型狀態的查詢實現分離。

當一個Command進來時,從倉儲Repository加載一個聚合aggregate對象羣,而後執行其方法和行爲。這樣,會激發聚合對象羣產生一個事件,這個事件能夠分發給倉儲Repository,或者分發給Event Bus事件總線,好比JavaEE的消息總線等等。事件總線將再次激活全部監聽本事件的處理者。固然一些處理者會執行其餘聚合對象羣的操做,包括數據庫的更新。

查詢時,則經過查詢優化的數據庫直接進行查詢(典型的有將數據冗餘在搜索引擎中查詢或直接生成報表在數據庫查詢)

 

評價:

該架構的較爲複雜,在實現起來也較爲困難(特別在Spring框架下),因爲數據的存儲和更新都是經過事件進行,在整個系統中會出現大量不一樣類型的事件,在實現過程服務化的狀況下,要保證遊離在領域對象中的數據與數據庫中的數據一致,不得不進行鎖處理,不太適合傳統的服務化和微服務化架構 。適合該模式開發的典型框架是Akka Actor,這是因爲在Akka集羣中,領域對象(Actor)由且僅有一個,不會由於併發出現多個相同的Actor。

相關文章
相關標籤/搜索