Как Принцип Единой Ответственности относится к модели анемичного / богатого домена? - PullRequest
10 голосов
/ 10 января 2012

В настоящее время выполняется некоторый анализ кода, взятый у другой команды, и есть одно сомнение в применении SRP и его связи с моделью анемичной или богатой области (как определено Мартином Фаулером). Концепция богатой доменной модели заключается в том, чтобы иметь интеллектуальный объект, который может не только устанавливать / получать свои свойства, но и выполнять более сложную бизнес-логику. Интересно, как это вписывается в SRP?

Скажем, у меня есть класс модели, обладающий некоторыми свойствами, которые могут выставлять эти реквизиты и обеспечивать некоторые простые вычисления их свойств. Следующее требование - иметь возможность хранить данные этого объекта в каком-то объекте хранения, который не находится под моим контролем, например:

class MyObject {
    // get set
    // parse sth

}

Способ хранения в хранилище

   storage.store(key, object);

Не нарушает ли SRP, если MyObject имеет такой метод хранения

public void store(Storage storage) {
    storage.store('keyOne', fieldOne);
    storage.store('keyTwo', fieldTwo);
}

Из pov этого объекта хорошо бы иметь возможность сохранить его состояние. Другой способ может заключаться в том, чтобы ввести вид сервиса здесь и сделать это так:

public StorageService {
    private Storage;
    // constructor here
    ....
    public void store(MyObject myobj);
}

Можете ли вы указать мне какие-либо ссылки, которые я могу прочитать об этой проблеме? Я нашел одну тему по SO здесь, но она не отвечает на мой вопрос полностью.

Как это разрешается в DDD? Модели в DDD по определению богаты и могут рассматриваться как имеющие слишком много обязанностей.

Ответы [ 3 ]

7 голосов
/ 10 января 2012

Модель расширенного домена ( RDM ) означает, что логика , управляющая поведением модели , принадлежит модели, а не обрабатывает модель как геттеры / сеттеры. Это не означает, что все, включая постоянство, безопасность, способ отображения модели в графическом интерфейсе и т. Д., Должно быть внутри модели.

RDM и SRP идут рука об руку, они не конфликтуют друг с другом.

Нарушение SRP / RDM:

Car {
   // possibly violates SRP
   storeInDatabase();  
   // smells like anemic domain model
   getEngineState();   
}

После SRP / RDM:

// usings aspects to remove cross-cutting concerns from the model and follow SRP
@DatabaseSerializable 
Car {
   // rich domain model encapsulates engine state and exposes behavior
   drive();            
}
4 голосов
/ 10 января 2012

«Модели в DDD по определению богаты и могут рассматриваться как имеющие слишком много обязанностей» - упрощенное толкование DDD.Всегда зависит от того, насколько хороши ваши модели.Вы можете создавать плохие модели, используя DDD (например, создавая объекты со слишком большим количеством ответственности или создавая анемичные модели).DDD и SRP также являются двумя хорошими практиками, такими как рефакторинг, TDD и многие другие, но вы должны дополнить их использование своим опытом и суждениями (или чьим-либо еще).У всего есть свои плюсы и минусы, не будьте догматичными в применении какой-либо практики.

3 голосов
/ 11 января 2012

@ Garrett Hall

Я несколько не согласен с вашим утверждением "RDM и SRP идут рука об руку, они не конфликтуют друг с другом".По моему опыту, когда SRP переоценен, это приводит к модели анемичной области.«Нет, мы не можем сделать или даже помочь поддержать какое-либо упорство, нет, мы не можем сделать 21-CFR11, нет, мы даже не можем знать, что такое графический интерфейс ...», и ваш класс в конечном итоге делает ничего и просто есть модель анемичного домена.

И если RDM переоценен (это направление / ошибка, к которой я склонен), то SRP полностью отходит на второй план, и вы в конечном итоге замечаете, что у вашего класса есть сотни методов и явно слишком много.

Вам нужно найти баланс, счастливую среду, где происходят как RDM, так и SRP.А найти такой баланс сложно, и часто в вашей команде больше интуиции и политики, чем технических знаний или правил.

«Познай себя».Если вы похожи на меня и склонны к чрезмерно сложным занятиям, знайте.И когда вы видите чей-то класс, который выглядит слишком сложным даже для вас, это большой красный флаг.Точно так же, если вы знаете, что вы достаточно хардкор в отношении SRP, и вы видите класс, который выглядит анемичным даже по вашим стандартам, это серьезный запах кода.

Теперь, немного отвечая на вопрос ОП о Storage, я думаюмногое зависит от того, насколько стабильным, стандартным и абстрактным является Storage.Если бы Storage был какой-то стандартной абстракцией XML, CSV или RDB, у меня не было бы абсолютно никаких проблем с объектами, знающими, как хранить себя.

...