Комментарии 18
Изолированная модель предметной области — это модель, операции над которой закрыты в рамках ее сущностей и объектов значений
Дальше в эту изолированную доменную область неизбежно пролезет диспетчер событий, а логика домена, которую мы пытались изолировать и сконцентрировать, растечется по сервисам и слоям.
Рекомендую обращать внимание на то, как адепты DDD реализуют обработку событий домена: там вылезут все фатальные недостатки подхода.
Пока вы не дорастёте до DSL/кодогенерации (никогда), полная изоляция предметной области недостижима. В рамках DDD на трейд-оффы этой изоляции принято не обращать внимания.
Ответ, как всегда, заключается в том, чтобы бороться со сложностью
Сниженная сложность интерфейсов домена компенсируется сложностью в управлении огромным количеством абстракций, сложностью связывания домена с другими слоями приложения. Всё это помножится на велосипедостроительство: у каждой команды свой взгляд на DDD, что приводит к удивительным образцам оверинженеринга.
"Чистота семантики" обойдётся очень дорого: сложность при DDD не снижается, а размазывается.
Продаваемая адептами DDD "простота" достигается не тем, что сложное становится проще, а тем, что всё становится примерно одинаково сложно. Не сложные задачи решаются быстрее, а легкие дольше.
"Вау-эффект", который обычно показывают на графиках (где x — время, y — сложность, и сложность в какой-то момент перестаёт расти) заключается именно в этом: уменьшается волатильность "сложности", из-за чего возникает иллюзия, что DDD делает сложное проще, хотя всё ровно наоборот.
DDD — это когда стабильно сложно для разработчика, и стабильно дорого для бизнеса, в этом весь трюк.
Процесс разработки не стабилен, и это не нравится бизнесу: трудно управлять, трудно строить прогнозы и планы. DDD создаёт иллюзию стабильности на графиках (и это даже может где-то сработать), но скорее всего, просто сделает дороже для бизнеса и сложнее для разработчика. На дистанции проект неизбежно станет более хрупким (фактор автобуса+сложность кодовой базы) и менее управляемым (из-за масштаба проекта).
Я пришёл к тому, что у домена не должно быть логики, не должно быть интерфейсов, домен - это только сущности, любые действия над сущностями выполняются на уровне сервисов и бизнес логики. Исключение стандартные методы и интерфейсы, ToString, GetHashCode, IComparable и т. п. Любые попытки запихнуть логику в домен непременно вызывали проблемы, что на каком то этапе требовалось прокинуть сервис в домен, а это не правильно
Статья интересная. Сам постоянно задумываюсь над тем, что зависимость от интерфейса не даёт настоящей инверсии зависимостей.
Но примеров не хватает, как изолировать модель? Как в модели Address правильно избавиться от location API? Сразу принимать zip code в конструктор, насколько я понимаю?
всегда невозможно
А может возможно?
Мне видится это разница в дизайне - в какой момент сделать нужный запрос. Если в рамках транзакции (бизнес-метода агрегата) вы знаете что вам понадобятся данные, то значит метод агрегата должен принять эти данные до операции. Готов попробовать помочь с конкретными примерами.
Мне кажется, что один лишь факт использования репозитория доменом не указывает на нарушение изоляции доменного слоя, т.к. паттерн репозиторий по задумке представляет инверсию зависимостей между слоем домена и слоем доступа к данным. Главное - чтобы все методы репозитория и их сигнатуры определялись исходя исключительно из потребностей домена и выражались через его (домена) терминологию.
Я не понял, как это будет материализоваться из базы и сохраняться? Мне кажется появится тонна водопроводного кода, чтобы поддерживать эту изоляцию.
В исходной статье есть пример работающего приложения с базой?
В общем случае - вручную. Т.е. в реализации get-метода репозитория необходимо забрать данные из какого-то хранилища (например, из БД) и затем на основании этих данных последовательно воссоздать агрегат через вызов соответствующих конструкторов/фабрик/методов. Аналогично - при сохранении.
В частных случаях это можно переложить на ORM, описав правила через fluent API. При этом ORM может либо уметь использовать конструкторы с параметрами, либо устанавливать значения свойств в обход бизнес-правил через рефлексию.
Изоляция модели предметной области