Ответы пользователя по тегу Проектирование программного обеспечения
  • Недостати при комбинации нескольких команд во время одного запроса/процесса в CQRS подходе?

    @ddd329
    1. Допустим, в моей системе имеется 2 команды (command) и их обработчики (command handlers): 1 - создает пользователя, 2 - активирует его аккаунт. Но тут приходит бизнес и говорит: "Для пользователей, у которых почтовый адрес от gmail, аккаунты должны активироваться сразу же, в момент создания". Как в этом случае должен выглядеть контроллер, который обрабатывает запрос на создание пользователя? Должен ли он после вызова обработчика создания пользователя, сразу же вызвать обработчик активации аккаунта если почтовый адрес от gmail? Вопрос можно сформулировать так: имеет ли какие-то недостатки, подход, комбинирования обработчиков команд при обработке единого запроса?

    После выполнения команды на создание пользователя необходимо опубликовать событие об этом, а дальше некий обработчик в своем коде будет проверять email и если он от gmail, то формирует команду на активацию и дальше в шину её, или куда там у вас...
    Ответ написан
    Комментировать
  • По какому пути вы бы пошли при рефакторинге?

    @ddd329
    Менеджер проекта решил возвращать с округлением.

    Обычно округление и форматирование значений с плавающей запятой требуется для отображений в графическом интерфейсе пользователя.
    Если вашему менеджеру необходимо именно это, то никакие изменения в класс Balanceвносить не нужно, т.к. этот класс является бизнес-сущностью и соответственно реализован в бизнес-слое, а логику отображения необходимо править в слое отображения.
    Например, вы используете паттерн Model-ViewModel-View, то эту задачу должен решать класс ViewModel. Если используете паттерн Model-View-Presenter или Model-View-Controller, то соответственно задачу решает Presenter и Controller.
    Если речь об этом, то в принципе разговор здесь можно закончить, но если это необходимо для решения бизнес-задач, то давайте разберемся по порядку.

    1) Добавить округление в с существующий метод getBalance, запустить тесты на getBalance и через 5 мин пойти пить кофе.

    На вашем месте я бы сделал именно это, если речь идет не об отображении данных.

    2) Добавить в Класс Balance новый метод getAdvancedBalance c округлением а текущий метод не трогать тк у нас банки если что то сломается будет не приятно

    Вот здесь очень большую неразбериху в код внесете, у клиента получается два вида баланса что ли? Так какой из них вызывать чтобы узнать баланс? Если вы хотите первый метод оставить, значит он вам нужен... Вообщем нет..

    3) Сделать новый класс AdvancedBalance унаследовать от Balance и переопределить метод getBalance, отрефакторить весь проект на использование AdvancedBalance:getBalance вместо Balance:getBalance и молится что ничего не сломалось хоть тесты и есть, но банк и если у когото олигарха что то не то отобразится вам мало не покажется

    Можно так делать, но не нужно в вашем случае. Особенно не очень хорошо, как вы сказали чтобы отрефакторить весь проект и произвести замену класса Balance на AdvancedBalance. Вам необходим выполнить маленькую простую задачу, а изменений в этом случае придется сделать очень много, а это большой риск для внесения ошибок.
    Вообще для таких решений код проектируют таким образом: класс Balance объявляют абстрактным и у него определяют статический фабричный метод var balance = Balance.Create(/* агрументы */). Ну и соответственно в зависимости от значений входящих аргументов, вам вернется правильный наследник. Если вы захотите добавить нового наследника, например AdvancedBalance, то внесете изменения только в метод Create. Вот здесь наверное будет соблюден принцип открытости/закрытости.

    4) Сделать новый класс AdvancedBalance унаследовать от Balance и создать новый метод getAdvancedBalance, отрефакторить
    и снова молится.

    Если вы так сделаете, то нарушите принцип Барбары Лисков.
    Ответ написан
  • Как проектировать приложение с нуля?

    @ddd329
    Я бы посоветовал книгу Крэга Лармана "Применение UML 2.0 и шаблонов проектирования".
    Ну а так можно начинать проектировать простые приложения с Базы Данных, думаю для начинающих это проще и эффективнее. Можно конечно посоветовать почитать Эрика Эванса про его методологию DDD (Domain Driven Design - проектирование на основе предметной области), но думаю мозг сломаешь и на ранних этапах от нее пользы точно не будет.
    Что касается проектирования UI, то здесь могу посоветовать паттерн MVP (Model-View-Presenter).

    А то, что прочитанный вами материал неполный, то интересно как вы это определили? Спросили у экспертов?
    Вообщем в книге Крэга Лармана много чего есть, сначала следует начать с нее.
    Ответ написан
    1 комментарий
  • Нужно ли создавать интерфейсы для одного класса?

    @ddd329
    Смотря какой класс.
    Если это сущность предметной области, то нет, не стоит.
    Если это сервисы, то да, стоит.
    Ответ написан
    Комментировать
  • Как залезть на несколько уровней абстракции ниже, не плодя кривой код?

    @ddd329
    Вот самый подходящий паттерн Цепочка обязанностей
    Ответ написан
    Комментировать
  • Межмодульная коммуникация в расширяемых приложениях?

    @ddd329
    Нее, интеграция посредством СООБЩЕНИЙ штука не такая простая, она в основном требуется в больших корпоративных приложениях, когда существует множество приложений, между которыми необходимо настроить взаимодействие.
    В Вашем случае все намного проще для того, чтобы разбить монолит на отдельные модули. Есть такой паттерн как "Plugin", который описан в книге Фаулера по шаблонам корпоративных приложений.
    Я бы сделал так: создал отдельный проект, где приведены контракты модулей, т.е. программные интерфейсы. Ну а далее в других проектах идет реализация этих контрактов/интерфейсов...
    Ответ написан
    Комментировать
  • Проектирование структуры приложений для начинающего?

    @ddd329
    Могу дать такие советы, как вижу это я.

    Разделить приложение на три уровня:
    1) Presentation - уровень представления, при помощи которого пользователь взаимодействует с приложением;
    2) Business Logic - слой бизнес-логики;
    3) Persistence - слой где хранятся данные, но обычно это реляционная БД.

    Если это настольное приложение, то слой Presentation разбей на три компонента согласно паттерну MVP (Model-View-Presenter), если это классическое веб-приложение, то паттерну MVC (Model-View-Controller).

    Слой бизнес-логики реализуй согласно паттерну Transaction Script, ну либо паттерну Модель предметной области, где для начала будет анемичная модель (anemic model), которая полностью совпадает со схемой БД, а логику храни в сервисах. Далее когда наберешься скиллов, то можешь пробовать из анемичной модели предметной области сделать богатую (rich model), для этого можешь обратить внимание на методологию DDD (Domain-Driven-Design).

    Ну и слой хранения, тут пока тупо через средства ORM...

    Ну примерно так, ничего нового и волшебного тут нету.
    Ответ написан
    Комментировать
  • Как спроектировать проверку?

    @ddd329
    Привет! Ну если вопрос касается проектирования, то тут сразу бросается в глаза понятие Service. В предметной области его желательно не использовать, т.к. данный термин очень перегруженный и имеет много понятий в программировании. Я видел в одном проекте его заменили на Product, но ладно не суть...
    Паттерн "Спецификация" я думаю тут не особо уместен. Можно сделать так, что каждый Сотрудник содержит в себе поле со списком Документов, и для того чтобы выяснить может ли сотрудник оказывать услугу, то можно примерно так:
    if (employee.СanProvideService(service)) ...
    Ответ написан
    Комментировать
  • Как собрать мысли в кучу при большом рефакторинге?

    @ddd329
    Тут могу посоветовать пока только Фаулера и его книгу про рефакторинг ссылка.
    Есть еще одна книга по работе с унаследованным кодом ссылка, но перевод ее настолько ужасен, что как бы и не советую, но те кто читал ее в оригинале, говорят что очень хороша!
    Я считаю, что никакими советами и статьями здесь не обойдешься, надо читать.
    Читай, иначе обречен на неудачу!
    Ответ написан
    Комментировать
  • C чего начинать проектирование ПО: со структуры БД или бизнес-логики?

    @ddd329
    На этот вопрос я бы ответил так: начинать проектирование надо не со схемы базы данных, и не с бизнес-логики. Конечно, я и сам обычно начинаю создание именно с проектирования схемы БД, но в целом тогда, когда предметная область мне знакома и ясна.
    Вы создаете приложение, а значит вам необходимо знать и понимать кто будет использовать вашу систему и, главное - какие проблемы будет решать ваш программный продукт. И это очень важно!
    Например: вам необходимо автоматизировать деятельность платной библиотеки. Использовать ее будут администратор, сотрудник библиотеки и читатель.
    Далее, нам необходимо решить какие сценарии использования (так называемые use case) будет реализовано в нашем приложении, т.е. как эти люди (actor) будут использовать нашу систему.
    Администратор - управление сотрудниками библиотеки, учет книг;
    Сотрудник библиотеки - выдача книг, возврат книг, продажа абонементов;
    Читатель - резервирование книг, продление книг, оплата книг и т.д.

    А вот когда мы понимаем, кто и как будет использовать наш программный продукт, тогда мы уже можем приступать к реализации бизнес-слоя. Причем не обязательно, что вам необходимо строить полноценную модель предметной области, вы можете ее не строить, удобный шаблон реализации бизнес-слоя - это сценарий транзакции (Transaction Script).
    Если все же решили делать модель предметной области, то тут необходимо решить какая она будет, анемичная (anemic ) или богатая (rich). В первом случае вся логика сосредоточена в сервисах бизнес-слоя, а сами сущности предметной области простые контейнеры данных, которые обычно один в один совпадают со схемой базы данных. Во втором случае, основная логика бизнес-поведения сосредоточена в классах бизнес-сущностей.
    Ну как-то так...
    Ответ написан
    Комментировать
  • DDD, aggregate root, entity, repository?

    @ddd329
    Ну тогда АГРЕГАТ будет состоять из одной СУЩНОСТИ - City
    Ответ написан
  • Как следует организовать работу с entity?

    @ddd329
    Сущности и агрегаты нужны для реализации бизнес-логики, чтобы ты не смог в базу данных записать недостоверную и/или противоречивую информацию, и все!
    На экране ты отображаешь не сущности и агрегаты, а скорее информацию о них... Когда ты думаешь о выводе данных на экран, то не должен даже мыслить агрегатами, потому как агрегаты являются единицами изменения, а не порция для отображения.
    Поэтому можешь обращаться на прямую в БД с запросом выдать тебе информацию, или создать отдельную Модель Чтения, и через ORM читать данные.

    Создавать сущность LocalizedDisease не имеет смысла, так как не реализует новое поведение. Вообще сущность это в идеале только поведение, и не важно какие у него данные, то есть принцип здесь - "Говори а не спрашивай"
    Ответ написан
    Комментировать
  • DDD, Aggregate root без ORM, как сохранять?

    @ddd329
    Без ORM, есть простые шаблоны. Твой репозиторий имеет метод Save, не важно обновил или создал новый АГРЕГАТ, все это передаешь методу Save, т.е. один метод вместо двух - Add и Delete. Допустим, ты обновляешь АГРЕГАТ, который состоит из трех сущностей, а в базе существуют три таблицы, т.е. каждая сущность маппиться на свою таблицу. Та сущнсость которая представляет корень АГРЕГАТА, будет использовать оператор UPDATE в SQL запросе, а дочерние сущности надо удалить (DELETE FROM..) и вставить заново(INSERT INTO). Все это делается в одной транзации базы данных, никакой вам Unit Of Work не нужен...

    Попробуйте...
    Ответ написан
    Комментировать