более 6 лет Cоавтор библиотеки Cicerone Соавтор библиотеки RxPM Автор статьи «Заблуждения Clean Architecture» (54 плюса, 133000+ просмотров, в 600+ закладках)
более 6 лет Cоавтор библиотеки Cicerone Соавтор библиотеки RxPM Автор статьи «Заблуждения Clean Architecture» (54 плюса, 133000+ просмотров, в 600+ закладках)
разработчиков • Хайп вокруг новых “архитектур” «Архитектура отражает важные проектные решения по формированию системы, где важность определяется стоимостью изменений» Гради Буч
Не зависит от UI, БД, и внешнего мира «Цель архитектуры программного обеспечения – уменьшить человеческие трудозатраты на создание и сопровождение системы» Роберт Мартин
приложение • Мы просто клиент (списки показывать) • Незачем не зависеть от Android Нужно, потому что: • На мобиле бывает много логики. • При создании записи мы уже не клиент. • Мультиплатформа может выстрелить, а в SDK бывают баги. • Есть другие плюсы архитектуры.
and Adapters) • Onion Architecture • DCI (Data-Context-Interaction) • BCE (Boundary-Control-Entity) Эти архитектуры похожи: • Делят на уровни • Отделен уровень бизнес-правил • Обладают характеристиками хорошей архитектуры
• Организации компонентов «Принципы SOLID определяют, как выкладывать кирпичами стены, образующие комнаты, а принципы организации компонентов – как размещать комнаты в зданиях» Роберт Мартин
которого зависят разные акторы. • Принцип открытости/закрытости (OCP) Делите систему на компоненты так, чтобы компоненты выше были защищены от изменений на нижних уровнях.
которого зависят разные акторы. • Принцип открытости/закрытости (OCP) Делите систему на компоненты так, чтобы компоненты выше были защищены от изменений на нижних уровнях. • Принцип подстановки Барбары Лисков (LSP) Реализации интерфейсов должны быть заменяемыми (совместимы).
которого зависят разные акторы. • Принцип открытости/закрытости (OCP) Делите систему на компоненты так, чтобы компоненты выше были защищены от изменений на нижних уровнях. • Принцип подстановки Барбары Лисков (LSP) Реализации интерфейсов должны быть заменяемыми (совместимы). • Принцип разделения интерфейсов (ISP) Не создавайте зависимости от модулей, содержащих больше, чем требуется.
которого зависят разные акторы. • Принцип открытости/закрытости (OCP) Делите систему на компоненты так, чтобы компоненты выше были защищены от изменений на нижних уровнях. • Принцип подстановки Барбары Лисков (LSP) Реализации интерфейсов должны быть заменяемыми (совместимы). • Принцип разделения интерфейсов (ISP) Не создавайте зависимости от модулей, содержащих больше, чем требуется. • Принцип инверсии зависимостей (DIP) Зависьте от стабильных абстракций вместо изменчивых конкретных элементов системы.
Составляйте компонент из классов, тесно связанных между собой. • Принцип согласованного изменения (CCP) Собирайте в компонент то, что изменяется по одной причине и в одно время.
Составляйте компонент из классов, тесно связанных между собой. • Принцип согласованного изменения (CCP) Собирайте в компонент то, что изменяется по одной причине и в одно время. • Принцип совместного повторного использования (CRP) Не зависьте от компонентов, имеющих неиспользуемые классы.
зависимостях компонентов (используя DIP или создав новый компонент от которого зависят другие). • Принцип устойчивых зависимостей (SDP) Зависьте от устойчивых. Трудно изменяемые компоненты не должны зависеть от изменчивых компонентов.
зависимостях компонентов (используя DIP или создав новый компонент от которого зависят другие). • Принцип устойчивых зависимостей (SDP) Зависьте от устойчивых. Трудно изменяемые компоненты не должны зависеть от изменчивых компонентов. • Принцип устойчивости абстракций (SAP) Делайте устойчивые компоненты абстрактными, а неустойчивые конкретными.
• Определяет отношения между компонентами. • Упрощает разработку, развертывание и сопровождение. • Выделяет политики, отодвигая на задний план детали. «Хороший архитектор максимизирует количество непринятых решений» Роберт Мартин
разной скоростью: • Разделение по уровням. (UI, бизнес-правила, БД, прочее) • Разделение по вариантам использования. (пересекая уровни) Где провести границы нам подсказали SRP и ССP. Разделение
к центру - выше уровень. • Сущности (Бизнес-правила уровня предприятия). • Варианты использования (Бизнес-правила приложения). • Адаптеры интерфейсов (Presenter, Gateway). • Фреймворки и драйверы (UI, БД, Web).
в сторону высокоуровневых политик. Внутренние круги ничего не знают о внешних: • Имена из внешних, не упоминаться в коде внутренних. • Форматы данных из внешних не используются внутренними.
приложениями. • Это объекты с методами. • В обособленном приложении выделяйте в сущности самые высокоуровневые правила. «Сущность - это бизнес в чистом виде и больше ничего» Роберт Мартин
для всех приложений: • Когда контакты считать одинаковыми. • Как объединять контакты. (Какое имя выбрать, если контакты совпали по номеру телефона. Какую дату и тп.) Contact -name: String -phones: List<String> -created: Date +same(contact: Contact) +combine(other: Contact)
только как часть приложения. • Используют сущности для достижения своих целей. • Это объект с методом, реализующим бизнес-правило. «Хорошие архитектуры опираются на варианты использования» Роберт Мартин
сколько лишних контактов объединилось Порядок действий: 1. Взять все контакты. 2. Найти среди них похожие. 3. Объединить. 4. Удалить объединенные с другими контакты. 5. Сохранить новый список контактов. 6. Отобразить количество удаленных лишних.
одно и то же. Interactor – объект, реализующий вариант использования (use case), используя бизнес-объекты (entities). Мы можем назвать наш вариант использования из примера как CombineContactsUseCase, так и CombineContactsInteractor. Это дело вкуса.
стоит делать отдельным объектом, не объединяя много вариантов в один класс. Объединяя много вариантов использования в один класс вы нарушите SRP и ISP. И лишитесь подробного описания вариантов использования в структуре проекта.
Gateway – объект, который инкапсулирует доступ к внешней системе или ресурсу. martinfowler.com/eaaCatalog/gateway.html Repository – посредник между доменом и слоями преобразования данных, использующий для доступа к данным интерфейс, подобный коллекциям. martinfowler.com/eaaCatalog/repository.html
нарушите SRP, ISP, OCP, DIP и правило зависимостей. Объединяя варианты использования вашего приложения со способами и источниками получения данных, вы делаете шаг назад от чистой архитектуры.
DIP чтобы развернуть зависимость. • Boundaries - пограничные интерфейсы, порты. • Входные и выходные Boundaries и данные находятся во внутреннем круге. Presenter Input Boundary <I> Output Boundary <I> Use Case Interactor Input Data <DS> Output Data <DS>
лишних знаний друг о друге. • Помогают отложить преждевременные решения. «Разработка архитектуры программного обеспечения – это искусство проведения разделяющих линий, которые я называю границами» Роберт Мартин
(DTO). • Способ передачи не важен. • Главное чтобы простые, независимые структуры данных. • Всегда в форме более удобной для внутреннего круга. Рекомендации от Дядюшки Боба: • Не передавайте объекты сущностей или записи БД. • И не включайте ссылки на сущности в DTO.
(например, RxJava), то у вас получится такая схема. Publisher и Subscriber логически формируют Output Boundary. Presenter Input Boundary <I> Publisher <I> Subscriber <I> Output Data <DS> Input Data <DS> Use Case Interactor
Мысли: Иногда бывают кейсы, когда надо слушать сервер и реагировать как на ввод, переключая экраны или запуская UseCase. Это очень похоже на обязанности Controller в веб-приложениях. Мы могли бы использовать подобные сущности в мобильных приложениях для таких кейсов..
ничего страшного, чтобы … вызывать Gateway из Presenter’a, минуя Interactor» Я заблуждался: Симон Браун называет это «окружным антишаблоном портов и адаптеров». Это потенциальный компромисс, который может иметь плохие последствия.
сомневаться в актуальности Сlean Architecture. • MVP (хайп в 2015) • MVVM (хайп в 2016 и в 2018) • RxPM (не было хайпа, просто рекламирую) • VIPER (iOs больше, в 2015 хайп вроде был) • MVI (хайп в 2017 и сейчас)
сравнивать нельзя. Всё перечисленное – это шаблоны проектирования пользовательского интерфейса. Нельзя вот так сравнивать их с Clean. Эти шаблоны являются частью чистой архитектуры и расположены в слое адаптеров интерфейсов.
набор классов из описания Сlean Architecture, который преподносится как реализация чистой архитектуры. Набор классов с нужными именами это еще не архитектура.
это чисто для UI. Мне же кажется, что MVI вполне можно использовать шире, организовав так, чтобы удовлетворять принципам чистой архитектуры. Но это не точно. А что думаете вы?
рекомендации, следуя которым мы упрощаем создание и сопровождение наших систем. «Правила не изменились. Несмотря на появление новых языков, фреймворков и парадигм, правила остались теми же, как во времена, когда в 1946-м Алан Тьюринг написал первый программный код» Роберт Мартин
github.com/terrakok/Cicerone «And remember, we are all pirates by nature; and the rules I'm talking about here are really more like guidelines…» Uncle Bob 10 лет на рынке 40+ сотрудников 200+ проектов #6 Tagline #6 Ruward #8 Рейтинг Рунета