dmitriylanets
@dmitriylanets
веб-разработчик

Как организовать фабрику для создания объектов?

В процессе изучения DDD, сразу скажу не использую ORM. Есть следующие сущности:
UserService, User(Entity),Group(Entity),Address(ValueObject)
Для получения пользователя со связями делаю что то подобное:
class UserService{

function findByid($id){
     $User = $this->UserRepository->find($id);
     $Group = $this->GroupRepository->find($User->getGroupId());
     $User->setGroup( $Group ) ;
     $User->setAddress(new Address( $User->getCity(), $User->getStreet()  ));

return $User;
}

}

Вопрос такой, где производить сборку готовой сущности для дальнейшего использования, может в фабрике, что то вроде $UserFactory->build( $User, $Group ); но тогда вопрос с сохранением сущности в бд, где то нужно объект переводить в формат пригодный для сохранения, возможно нужен UserMapper который это и будет делать, или же всю работу с сохранением делать через UserService?
  • Вопрос задан
  • 274 просмотра
Пригласить эксперта
Ответы на вопрос 2
Fesor
@Fesor
Full-stack developer (Symfony, Angular)
сразу скажу не использую ORM

Сразу скажу - используйте ORM.

class UserService{

И где тут DDD? Где единый язык?

Вопрос такой, где производить сборку готовой сущности для дальнейшего использования,

В репозитории или в одной из его зависимостей. В частности в Doctrine2 репозиторий запрашивает сущность в entity manager-а, который загружает их сначала в unit of work, который хранит все в identity map для того что бы не допускать дублей сущностей (если мы будем каким либо образом запрашивать одну и ту же сущность, ORM вернет вам один и тот же объект, что делает использование ORM собственно и удобным). Внутренний мэппер мэпит данные из базы на сущности с использованием гидраторов.

При сохранении происходит flush Unit-of-Work, при котором вычисляются изменения во всех сущностях и генерится SQL.

то есть вам в любом случае нужно реализовать мэппер объектов либо взять готовый, затем вам нужно реализовать Unit-of-work, затем лоадер данных из базы ну и т.д. Я обдумывал вариант легкой замены Doctrine2 и понял что это в принципе практически не возможно. Именно по этой причине существует не так много реализаций data-mapper, для PHP это только доктрина, для Java это Hibernate, для Python - SQLAlchemy... и как бы больше реализаций и нет.

Дядя Боб в одном из своих докладов на тему архитектуры приложенй (запамятовал название, поищу) рассказывал на эту тему много чего, мол и про загоны "не использовать ORM" которые были в 90-х, и почему реализация дата мэппера это весьма сложная задача....

p.s. вывод - берите Doctrine2 ORM и не засоряйте себе голову попытками реализовать дата мэппер самостоятельно - это очень сложная задача. Именно поэтому не так много реализаций этого подхода.
Ответ написан
@Alew
Репозиторий(DDD) должен отдавать ГОТОВЫЕ объекты(в DDD агрегаты). Как он их собирает, сам или делегирует десятку мелко нашинкованных фабрик, использует он ОРМ или нет, это дело десятое. Вообще, рекомендую перепроверить свое понимание основных идей DDD.
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы