2013年6月29日 星期六

OO的"沉重",DDD (1)

Domain Driven Design提示了我許多以前沒看過的議題,如何讓設計者更加專心地在OO上面

Domain model是一種Ubiquitous lanuage

  • 現實以及模型做綁定,這是很簡單的規則,但是往往愈到專案後期,分析的模型愈是和實際的程式碼相差愈大
  • Domain Model不是單純的圖形,他是一種語言,也就是包含了上下文(context)
  • Domain Model因為有語言的特色,大家需要看得懂,聽得懂
  • Domain Model必須不斷的精練,也就是隨著專案成長以及精簡

為何不如XP之類的agile process採用user story之類的技巧呢?主要的問題在於各個user story以及design存在於設計師的心中,是一種隱性的資料(implicit data),其次agile process,往往產出的主要成果是code,code是一種完美的實現(implemetation)的呈現,然則是太細節,如果將專案的整個class diagram畫在黑板上鐵定很壯觀,但是恐怕解釋要花上很久

而如同agile process一樣,必須發展適當的、共通的語言,將設計精簡的呈現出來,且DDD和agile process一樣相信,feedback是很重要的,設計過程必須和使用者溝通,也就是"語言"主要的用途

如何從問題/需求過渡到設計,DDD的方式採用了類似DB Table design(這是一個很不好的比喻,但是退化/極簡的domain model幾乎就是這種模式),跟著利用design pattern作為指引,可以簡單地使用下面的圖形作為依據


設計工作主要圍繞著serviceentityvalue object之間的設計

  • entity含有唯一ID,且生命週期間狀態的轉換是有意義的,如身分證
  • value object則是臨時的狀態,通常是依附於entity上面
  • service則是一種類似於基礎建設的存在,往往處於領域的邊界,如DNS service

而entity以及value object中間往往有關係,在設計上,希望關係(關係在設計圖上用連線表示)愈簡單愈好,避免太過複雜的關係,簡化關係的方式有三

  • 限定travel方向
  • 限定關聯方式
  • 減少關聯


另外一種"打包"關係的方式就是使用aggregation,將物件打包成一個entity,所有內部資料必須透過root處理,且參考到的物件,往往只是value object,也就是並不會影響到實際物件內部物件的狀態

同樣的,如果需要生成狀態的抽象畫,可以使用factory pattern。而repository pattern則適用於查詢相似物件的應用或者封裝travel/filter的行為,比方說,從persistence裝置找到所有大於65歲的老年人口,如果要從某個根物件訪問到所有符合條件的物件太過費時、複雜且沒效率。

DDD有兩個特色,全都形而上,幾乎不涉及persistence,也不涉及class定義等等的部分(GoF多少有class定義)。DDD提示我們如何專注在OOAD上面,而非過去的設計模式(procedure or others)

這裡有些anti-pattern,可供參考,是否是使用舊的方式在設計
  • 每個entity就是對應一個table或者一個record
  • 關係非常複雜,很多關係是雙向的
  • 所有物件的persistence是由一個巨大的facade對應到DB或者檔案
從DDD我也體悟到了J2EE為何會被批評為太過heavy,J2EE每每需要綁訂多個責任,因為J2EE這個architecture管理了persistence以及object的life-time,造成了物件往往有過多的責任,這是一種負擔

經過這些基本考量之後,跟著在每個iteration,如何繼續改善domain model,是一個重要的工作,而且沒有固定的方法

沒有留言:

張貼留言