在具有豐富域模型(應用程序邏輯位於模型中,而不是服務中)的Web服務器項目中,如何處理將依賴關係注入模型對象?你有什麼經驗?如何處理注入到富域模型的依賴關係?
你使用某種形式的AOP?像Springs @Configurable註釋一樣?加載時間或建立時間weawing?遇到的問題?
您是否使用手動注射?那麼你如何處理不同的實例化場景(通過庫創建對象[如Hibernate],創建具有「新」的對象...)?
或者你使用其他方式注入依賴關係嗎?
在具有豐富域模型(應用程序邏輯位於模型中,而不是服務中)的Web服務器項目中,如何處理將依賴關係注入模型對象?你有什麼經驗?如何處理注入到富域模型的依賴關係?
你使用某種形式的AOP?像Springs @Configurable註釋一樣?加載時間或建立時間weawing?遇到的問題?
您是否使用手動注射?那麼你如何處理不同的實例化場景(通過庫創建對象[如Hibernate],創建具有「新」的對象...)?
或者你使用其他方式注入依賴關係嗎?
爲了保持我的域對象清潔,我避免在實體/聚合/值對象上使用注入,而是在需要時將這些注入到服務或存儲庫中。
爲此,我們使用普通的Spring構造函數注入來簡化測試。
如果您需要向實體中注入某些東西,建議可以編寫一個構建器或工廠,然後在其中注入您需要的東西。
我們使用Spring的@Configurable(和普通的new運算符一樣),它的作用就像一個魅力。沒有更多anemic domain models。最後,這是更加面向對象的設計,是不是:
Person person = new Person(firstname, lastname);
// weird
peopleService.save(person);
// good (save is @Transactional)
person.save();
Mail mail = new Mail(to, subject, body);
// weird
mailService.send(mail);
// good (send is @Transactional)
mail.send();
雖然我們沒有做任何性能比較。到目前爲止,我們根本沒有覺得有必要這樣做。
編輯:這是人類會是什麼樣子:
@Configurable("person")
public class Person {
private IPersonDAO _personDAO;
private String _firstname;
private String _lastname;
// SNIP: some constructors, getters and setters
@Transactional(rollbackFor = DataAccessException.class)
public void save() {
_personDAO.save(this);
}
@Transactional(readOnly = true)
public List<Role> searchRoles(Company company) void{
return _personDAO.searchRoles(this, company);
}
// it's getting more interesting for more complex methods
@Transactional(rollbackFor = DataAccessException.class)
public void resignAllRoles(Company company) {
for (Role role : searchRoles(company)) {
role.resign();
}
}
}
// the implementation now looks like this
personService.getPerson(id).resignAllRoles(company);
// instead of this
roleService.resignAll(personService.searchRoles(personService.getPerson(id), company));
這就是Spring配置:
<context:spring-configured />
<bean id="person" class="org.example.model.Person" lazy-init="true">
<property name="personDAO" ref="personDAO" />
</bean>
注:正如你看到的,還有服務周圍,如以搜索對象(personService.getPerson(id)),但是對所有傳遞對象(例如人)進行操作的所有方法都被移至該類本身(即person.save()而不是personService.save(person))。該方法本身保持不變,並與任何基礎數據訪問層(純JDBC,Hibernate,JPA等)一起工作。它只是移動到它所屬的地方。
你如何持續集成測試你的實體?普通的JDBC?因爲如果你使用hibernate,這個策略是行不通的! – Arne 2010-05-19 10:15:40
@當然它會。看到我的編輯爲例。這個想法是,你只需將DAO注入到域對象中即可。然後將方法從服務移至類(通常是將此類的對象作爲參數的所有方法)。其他一切都保持不變。 – sfussenegger 2010-05-19 13:27:25
但是,如果您已經擁有personId(例如,您正在編輯某人)呢?然後你可以做一些像'personService.getPerson(personId).resignAllRoles(company);'或'roleService.resignAll(personService.searchRoles(personId,company));'第一個可能會做額外的不必要的查詢來獲得人物。 – 2014-01-09 17:55:10
您還可以查看下面的鏈接,這可以幫助很多。
軟件體系結構和豐富域模型的實用觀點描述了豐富域模型和軟件體系結構在哪裏見面。
此外,它介紹瞭如何配置,具有以下技術,框架和API的實現和JUnit這樣的觀點:
http://www.ruimtefotografie.org/forum/viewtopic.php?f=32&t=193
http://stackoverflow.com/questions/2091749/domain-driven-design-and-transactions-in-spring-environment – Bozho 2010-01-20 11:21:08