48
Чистая архитектура с VIPER Сергей Крапивенский, ведущий iOS-разработчик Rambler&Co

Сергей Крапивенский

Embed Size (px)

Citation preview

Чистая архитектура с VIPER Сергей Крапивенский, ведущий iOS-разработчик

Rambler&Co

Грязная архитектура

2

Грязная архитектура

• Огромные классы с кучей ответственностей

• Сильная связанность компонентов

• Трудно дебажить

• Трудно вносить изменения

• Невозможно покрыть тестами

• Хочется все сжечь 🔥

3

Чистая архитектура

• Простые компоненты с четкими обязанностями

• Слабая связанность

• Легко покрывается тестами

• Легко вносить изменения

• Просто понять

4

MVC от Apple: ожидание

5

MVC от Apple: реальность

6

MVC от Apple

7

Как появился VIPER

8

08.2012 12.2013 06.2014 05.20152014-2015

Как появился VIPER

9

08.2012 12.2013 06.2014 05.20152014-2015

Как появился VIPER

10

08.2012 12.2013 06.2014 05.20152014-2015

Как появился VIPER

11

08.2012 12.2013 06.2014 05.20152014-2015

Как появился VIPER

12

08.2012 12.2013 06.2014 05.20152014-2015

Идея VIPER

• Приложение разбивается на блоки с однотипной структурой

• Принцип разбиения - по user story

• User story простым языком описывает поведение приложения

13

User story

Пример - лента фото в Instagram

Задача - отобразить последние фото друзей

При необходимости можно перейти на другие истории

14

User story

Список лайков к нашим фото - другая история

Это простые примеры: 1 экран = 1 история

15

User story

На одном экране может быть несколько разных историй

16

User story

На одном экране может быть несколько разных историй

1. Лента фотографий

17

1. Лента фотографий

2. Таб-бар для переключения ленты

3. Панель с информацией о пользователе

User story

На одном экране может быть несколько разных историй

1. Лента фотографий

2. Таб-бар для переключения ленты

18

1. Лента фотографий

2. Таб-бар для переключения ленты

3. Панель с информацией о пользователе

User story

На одном экране может быть несколько разных историй

1. Лента фотографий

2. Таб-бар для переключения ленты

3. Панель с информацией о пользователе

19

Действия модуля

• Получает данные

• Преобразовывает данные для отображения

• Реагирует на действия пользователя

• Переходит на другие модули при необходимости

20

Канонический модуль VIPER

E

PRESENTERVIEW INTERACTOR

WIREFRAME

E

21

E

PRESENTERVIEW INTERACTOR

WIREFRAME

E

22

Канонический модуль VIPER

Отображает полученные от Presenter данные

Информирует Presenter о действиях пользователя

E

PRESENTERVIEW INTERACTOR

WIREFRAME

E

23

Канонический модуль VIPER

Содержит всю бизнес-логику

E

PRESENTERVIEW INTERACTOR

WIREFRAME

E

24

Канонический модуль VIPER

Подготавливает данные для отображения View

Обрабатывает действия пользователя

E

PRESENTERVIEW INTERACTOR

WIREFRAME

E

25

Канонический модуль VIPER

Отвечает за навигацию модуля

Инициализирует модуль и инжектирует зависимости

E

PRESENTERVIEW INTERACTOR

WIREFRAME

E

26

Канонический модуль VIPER

Простые модельные объекты

Не содержат никакой логики

Что мы изменили?

• Разделили Wireframe

• Добавили слой сервисов

• Сделали View слоем

• Формализовали переходы между модулями

• Написали тулзу для кодогенерации

27

Разделили Wireframe

• Wireframe не удовлетворяет SRP

• Wireframe = Router + Assembly

• Router отвечает за навигацию

• Assembly отвечает за сборку модуля

• Dependency Injection с помощью Typhoon Framework

• https://github.com/appsquickly/Typhoon

28

Добавили слой сервисов

• “Вся бизнес логика” звучит страшно 😱

• Сервисы - слой ниже интерактора

• 1 сервис = 1 тип сущностей (новости, сообщения, etc)

• Сервисы можно переиспользовать в разных модулях

• Сервисы зависят от объектов нижнего уровня

29

Слой View

• Тяжелое наследие UIViewController

• Работа с коллекциями не должна быть во View

• Layout и анимации можно вынести из View

• Эти задачи относятся к отображению данных

• Так View превратился в слой

30

Переходы между модулями

• То, о чем никто не говорит 🙊

• У каждого модуля есть <ModuleInput> и <ModuleOutput>

• Эти протоколы реализует презентер

• Пример: переход из модуля А в модуль B

• Роутер модуля А передает данные в презентер модуля B

• Презентер модуля B возвращает результат в презентер модуля А

31

Кодогенерация

• С VIPER нужно создать кучу классов

• Каркас всех модулей однотипен

• Руками создавать долго и сложно

• Программисту лень писать руками? Нужен скрипт

• Generamba!

• https://github.com/rambler-ios/Generamba

32

Что у нас получилось

33

Что у нас получилось

34

Афиша.Рестораны

Категории ресторанов

Рестораны в категории

Экран ресторана

35

Афиша.Рестораны

36

VIEW

Категории ресторанов

STORYBOARDsegue

VIEW

Рестораны в категории

instantiate

37

VIEW

Категории ресторанов

STORYBOARDsegue

VIEW

Рестораны в категории

instantiate

ASSEMBLYbuild

38

VIEW

Категории ресторанов

segueVIEW

Рестораны в категории

INTERACTOR

PRESENTER ROUTER

SERVICE

39

VIEW

Рестораны в категории

INTERACTOR

PRESENTER ROUTER

SERVICE

VIEW

Экран ресторана

INTERACTOR

PRESENTERROUTER

SERVICE

categoryId

categories (Core Data)

restaurantId

restaurant (Core Data)

restaurant (PONSO)

categories (PONSO)

40

Чистая архитектура

• Простые компоненты с четкими обязанностями

• Слабая связанность

• Легко покрывается тестами

• Легко подвергается изменениям

• Просто понять

41

Чистая архитектура

• Простые компоненты с четкими обязанностями

• Слабая связанность

• Легко покрывается тестами

• Легко подвергается изменениям

• Просто понять

42

Чистая архитектура

• Простые компоненты с четкими обязанностями

• Слабая связанность

• Легко покрывается тестами

• Легко подвергается изменениям

• Просто понять

43

Чистая архитектура

• Простые компоненты с четкими обязанностями

• Слабая связанность

• Легко покрывается тестами

• Легко подвергается изменениям

• Просто понять

44

Чистая архитектура

• Простые компоненты с четкими обязанностями

• Слабая связанность

• Легко покрывается тестами

• Легко подвергается изменениям

• Просто понять

45

Чистая архитектура

• Простые компоненты с четкими обязанностями

• Слабая связанность

• Легко покрывается тестами

• Легко подвергается изменениям

• Просто понять

46

Rambler 😍 VIPER

• Рамблер.Конференции - open-source приложение

• Generamba - кодогенератор

• VIPER McFlurry - набор полезных утилит

• The Book Of VIPER - все что мы знаем о VIPER

• И еще некоторые плюшки

• https://github.com/rambler-ios

47

Спасибо!

serkrapiv

sergey.krapivenskiy

rambler-ios