В ней говорится, что обращение из пользовательского интерфейса к бизнес-логике надо обязательно выполнять через Фасад.
Вот картинка:
В связи с этим два вопроса:
1) Получается, что этот Фасад должен знать как обработать все запросы, поступающие от клиента.
Значит, это по сути God-object. Верно?
Но это же анти-паттерн! Разве так правильно делать?
2) А нужен ли этот Фасад для веб-приложений?
Ведь в веб-приложениях клиент и сервер "общаются" через веб. На стороне сервера есть единая "точка", которая принимает все запросы.
Можно ли эту "точку" считать Фасадом?
Здравствуйте, zelenprog, Вы писали:
Z>1) Получается, что этот Фасад должен знать как обработать все запросы, поступающие от клиента. Z>Значит, это по сути God-object. Верно? Z>Но это же анти-паттерн! Разве так правильно делать?
Кажется, что скорее делегировать непостредственно обработчику, а не самому. С этой тз с Фасадом все ок.
Z>2) А нужен ли этот Фасад для веб-приложений? Z>Ведь в веб-приложениях клиент и сервер "общаются" через веб. На стороне сервера есть единая "точка", которая принимает все запросы. Z>Можно ли эту "точку" считать Фасадом?
Z>Здравствуйте!
Z>Прочитал вот эту статью: Z>"Охота на мифический MVC. Построение пользовательского интерфейса" Z>https://habr.com/ru/articles/322700/
Z>В ней говорится, что обращение из пользовательского интерфейса к бизнес-логике надо обязательно выполнять через Фасад. Z>Вот картинка:
Z>Image: Охота на мифический MVC. Универсальная схема MVC _ статья.png
Z>В связи с этим два вопроса:
Z>1) Получается, что этот Фасад должен знать как обработать все запросы, поступающие от клиента. Z>Значит, это по сути God-object. Верно? Z>Но это же анти-паттерн! Разве так правильно делать?
Z>2) А нужен ли этот Фасад для веб-приложений? Z>Ведь в веб-приложениях клиент и сервер "общаются" через веб. На стороне сервера есть единая "точка", которая принимает все запросы. Z>Можно ли эту "точку" считать Фасадом?
Не надо на этом сильно заморачиваться. Первична не архитектура, а принципы разработки, которые к ней приводят.
Z>>1) Получается, что этот Фасад должен знать как обработать все запросы, поступающие от клиента. Z>>Значит, это по сути God-object. Верно? Z>>Но это же анти-паттерн! Разве так правильно делать?
S>Кажется, что скорее делегировать непостредственно обработчику, а не самому. С этой тз с Фасадом все ок.
Чтобы делегировать обработчику, фасад должен знать интерфейс этого обработчика.
Если учесть, что слой бизнес-логики содержит не один, а много обработчиков, то получается, что фасад должен знать интерфейсы всех этих обработчиков.
Значит, Фасад будет "знать" по сути всю бизнес-логику (то есть "зависеть" от всех обработчиков).
Это же и есть God-object.
Что-то тут не так. А как же принцип разделения ответственности?
Здравствуйте, zelenprog, Вы писали:
Z>Чтобы делегировать обработчику, фасад должен знать интерфейс этого обработчика. Z>Если учесть, что слой бизнес-логики содержит не один, а много обработчиков, то получается, что фасад должен знать интерфейсы всех этих обработчиков. Z>Значит, Фасад будет "знать" по сути всю бизнес-логику (то есть "зависеть" от всех обработчиков).
Не саму бизнес-логику, а только правила ее вызова.
Z>Это же и есть God-object. Z>Что-то тут не так. А как же принцип разделения ответственности?
Вопрос терминологии. Легко обосновать, что это God-object. И так же легко притащить сюда SRP. Единственная ответственность: фасад предоставлет упрощенный интерфейс к системе (заворачивает систему в черный ящик)
Ответственность разделяют, чтобы снизить сложность системы.
Задай себе вопросы:
— этот класс облегчает работу с системой со стороны клиента (вызывающего кода)?
— с этим классом легко разобраться, чтобы его исправлять?
Б>Вопрос терминологии. Легко обосновать, что это God-object. И так же легко притащить сюда SRP. Единственная ответственность: фасад предоставлет упрощенный интерфейс к системе (заворачивает систему в черный ящик)
Б>Ответственность разделяют, чтобы снизить сложность системы.
Б>Задай себе вопросы: Б>- этот класс облегчает работу с системой со стороны клиента (вызывающего кода)? Б>- с этим классом трудно разобраться, чтобы его исправлять?
Б>Если ответы "да", то это полезный класс.
В общем согласен.
Но почему тогда предлагают делать Фасад только для слоя Бизнес-логики?
По идее Фасад может быть полезен и для любого другого слоя.
Получается, что по хорошему все слои должны взаимодействовать друг с другом через Фасады?
Здравствуйте, zelenprog, Вы писали:
Z>Получается, что по хорошему все слои должны взаимодействовать друг с другом через Фасады?
Если называть фасадом единую точку входа с узким интерфейсом, то так и происходит:
— Перед слоем контроллеров — роутер, вызывает конкретные обработчики
— Перед слоем бизнес-логики — фасады для каждого домена (вызывает сервисы / функции доменной логики)
— Перед слоем инфры (порты справа в чистой архитектуре) — фасады/адаптеры к внешним системам
Z>>>1) Получается, что этот Фасад должен знать как обработать все запросы, поступающие от клиента. Z>>>Значит, это по сути God-object. Верно? Z>>>Но это же анти-паттерн! Разве так правильно делать?
S>>Кажется, что скорее делегировать непостредственно обработчику, а не самому. С этой тз с Фасадом все ок.
Z>Чтобы делегировать обработчику, фасад должен знать интерфейс этого обработчика. Z>Если учесть, что слой бизнес-логики содержит не один, а много обработчиков, то получается, что фасад должен знать интерфейсы всех этих обработчиков. Z>Значит, Фасад будет "знать" по сути всю бизнес-логику (то есть "зависеть" от всех обработчиков). Z>Это же и есть God-object. Z>Что-то тут не так. А как же принцип разделения ответственности?
Справедливое замечание, но кажется, что зависит от реализации. Да и фасадов может быть больше чем один, т.е.
несколько фасадов может покрывать бизнес-логику. Вот тут про это пишут -- https://stackoverflow.com/a/37644965/241446
Короче, зависит от реализации.
Здравствуйте, zelenprog, Вы писали:
Z>В ней говорится, что обращение из пользовательского интерфейса к бизнес-логике надо обязательно выполнять через Фасад. Z>Вот картинка:
Фасад или не фасад, дело десятое. UI и БЛ нужно изолировать друг от друга. Обоснование — разная частота и причины изменений, т.е. можно и нужно менять эти вещи независимо друг от друга, а так же высокая сложность одного из компонентов
Фасад нужен в т.ч. и для веб-приложений, см пример в конце. Всё дело в сложности — чем она выше, чем актуальнее изолироваться.
Ваш условный фасад 25 лет назад выглядел вот так
controller.execute(item.command, args); // обычно такой вызов прятался в инфраструктуру, вызывать его напрямую обычно не было нужды
Унутре контроллер найдет команду, которая реализует ну вот например "toggle.show.utilization"
связывание контролера и команд делается по имени, например, так
{
"toggle.show.utilization": "commands/ShowUtilization" // если хотите задавать через файл конфигурации, плагины итд
}
@Handler("toggle.show.utilization") // можно было и так, но это для бесноватых любителей магии и неявного связывания
class ShowUtilization {
do(ctx) {
// вычисляем все изменения
const utilization = Utilization.calculate(ctx.model, ctx.config, app.config);
// применяем все изменения
const changes = model.apply(utilization);
return changes; // вернуть нужно подсказку для UI, что именно изменилось в модели, что бы проще было перерисовывать
}
undo(ctx) {
...
}
redo(ctx) {
....
}
}
Бенефиты — ui знает только как вызвать контроллер. Контроллер знает только обобщенный интерфейс команд. Команда знает протокол работы с бл, но ничего про саму бл.
Сейчас, спустя 25 лет, это переизобретено под называнием Redux, см жээс фронтенд.
Ключевые отличиян
Было
controller.execute(item.command, args)
controller вызывает команду а потом обновляет view — или шлет сигнал, или вызывает у каждой метод update
Стало
store.dispatch(item.action, args);
view обновляется через store.subscribe(state => view.render(state))
+ вместо команд у вас редюсеры-мидлвары, приседания с иммутабельностью и конские издержки по перформансу и памяти как следствие. зато крайне простой и тривиальный код. Хотя это спорно — без бутылки не разобрать, чего там намешают в редюсерах и мидлварах. Выяснить, кто кого когда вызывает и почему — как правило квест.
On May 20, 2024, 4:46 PM, zelenprog <140063@users.rsdn.org> wrote:
Z>Можно ли эту «точку» считать Фасадом?
1) При правильном подходе не должно быть никакого God-объекта. Под фасадом понимается интерфейс сервиса, а конкретная реализация сервиса определяется конфигурацией. Сервис зачастую всего лишь шлет события нотификации. Далее в точках отслеживания этих событий (UI) происходит обработка.
2) В веб-приложении тоже самое, только еще добавляется прослойка с сервлетом(-ми) (RS/WS не важно).
⸻ ❧ “If you don’t like the road you’re walking, start paving another one.” — Dolly Parton
Z>Здравствуйте!
Z>Прочитал вот эту статью: Z>"Охота на мифический MVC. Построение пользовательского интерфейса" Z>https://habr.com/ru/articles/322700/
Z>В ней говорится, что обращение из пользовательского интерфейса к бизнес-логике надо обязательно выполнять через Фасад. Z>Вот картинка:
Z>Image: Охота на мифический MVC. Универсальная схема MVC _ статья.png
Z>В связи с этим два вопроса:
Z>1) Получается, что этот Фасад должен знать как обработать все запросы, поступающие от клиента. Z>Значит, это по сути God-object. Верно? Z>Но это же анти-паттерн! Разве так правильно делать?
Z>2) А нужен ли этот Фасад для веб-приложений? Z>Ведь в веб-приложениях клиент и сервер "общаются" через веб. На стороне сервера есть единая "точка", которая принимает все запросы. Z>Можно ли эту "точку" считать Фасадом?
Все очень сильно зависит.
Задача фасада в данном случае изолировать доменные сущности от UI.
Может получить так: имеем доменную сущность, она прорастает во все представления или модели представления. Потом разрабы доменной модели говорят, мы сейчас сущность распилим и данные будут приходить вообще по другому.
и вот такое изменение может затронуть очень больше количество кода, а еще могут не дай бог сериализовать эту модель в настройки и придется писать миграции и таскать ее везде.
По этому в развесистом приложении вешают фасад/адаптер, который интерфейс доменной модели преобразует в интерфейс модели представления и добавляет развязку сущностей и позволяет с меньшим количеством изменений менять либо доменную модель либо модель представления.
Вообще картинки странно нарисованы, в слоено компонентной архитектуре связи "знает" обычно идут сверху вниз.
Главное во всех MVC MVP MVVM соблюдать модульность и сегрегированные интерфейсы. Вырожденно писать под паттерны нафиг не надо.
При этом этих фасадов может быть 100500, и никаких god object