2011-04-15 55 views
1

我目前正在將大型古老的Oracle Forms應用程序移植到JSF &我需要對領域模型做出決定。Java/JSF/Spring/WebFlow DDD體系結構設計問題

我被鎖定在使用Spring JDBC模板(無ORM),並利用DAO層來處理令人困惑的遺留數據庫模式,這一模式一定是第一年合作社設計的。對於領域模型,我真的想把事情做得很高OO,例如:假設有一個域對象計劃。目標將太OO-如果它能夠執行PlanInstance.load(byId(「12345」)),PlanInstance.save(),.delete(),.create()等等。但是隨後出現這種情況;因爲這些域對象包含對有狀態bean的引用(比如Repositories),所以它們不能被序列化。如何克服這一點?

最初我開始分裂的東西,如:PlanData(Stateless,Singleton)使用的PlanData(Statefull,SessionScoped)。通過這種方式,公共控制器代碼被提取並且被阻止在每個會話作用域bean中被複制,並且最重要的是允許會話作用域bean被序列化。在這一點上,我真的需要構造它OO風格以最大限度地減少複雜性,但是我只是不知道如何在會話範圍中引用狀態對象(由於序列化錯誤)時如何獲得對象。

我能想到的唯一可能性是使狀態引用暫態&設計了某種機制,以便在bean未序列化時重新注入依賴關係。任何人都可以向我提供解決這一難題的任何見解嗎?必須有某種模式/實踐來解決我可能只是失蹤的問題。

回答

0

我會保持該狀態的狀態和管理是分開的(即Plan與PlanManager)。通過使用數據訪問模式(PlanManager),您可以保持開放以便稍後使用ORM(比方說)如果db模式是將來重做。將國家和國家管理層放在同一個班級(PlanInstance)是違背OO單一責任原則的。

有狀態會話有作用域的bean本身沒有被序列化(至少不會存儲在持久性存儲中 - 但可能會序列化它們以支持會話故障切換)。控制器和會話bean維護對數據bean的引用。

有狀態bean決定何時加載,調用邏輯,更改狀態並保存數據對象。它們爲您的域對象提供上下文。在一些設計中(通常被稱爲「貧血域模型」),域對象沒有行爲,並且所有邏輯都存在於無狀態服務中。如果我理解正確,你想在你的域對象中封裝狀態和行爲,並且域對象需要使用有狀態會話bean來執行他們的工作。在可能的情況下,嘗試將域對象中的功能分解爲不依賴於會話狀態(將使測試更簡單)或將該功能推送到使用適當的會話狀態調用的服務bean中。如果您別無選擇,只能使用對來自域模型行爲的有狀態bean的引用,那麼有狀態bean可以將必要的狀態/存儲庫引用作爲參數提供給域對象上的方法調用。這樣,域對象仍然是無狀態的,但可以使用有狀態bean來實現域邏輯。

一直以來,都考慮域對象的單一職責。在某些時候,域邏輯可能會分裂成多層(比如低層和更高層的邏輯),這可能會導致對域對象中有狀態bean的需求變得不必要。