Как общаться между разными частями при использовании MVVM в iOS - PullRequest
0 голосов
/ 29 мая 2019

Я провел свое исследование, но, поскольку у меня недостаточно опыта, я не знаю, как лучше всего реализовать связь класса UserManger при использовании шаблона проектирования MVVM.

Так что мой таймерприложение, которое получило синхронизацию с облаком.Пока что у меня HomeViewController, TimerViewModel, TimerModel, UserManager.

Объект UserManager заботится о проверке подлинности User, а также о передаче состояния проверки подлинности другимклассы.

Состояния: .notSigned, .signing и .signed

Здесь мне нужно больше объяснений.С каким объектом UserManager должен сообщать обновленное состояние аутентификации?Это принадлежит контроллеру представления или модели представления?

И еще вопрос.Я не знаю, предполагают ли UserManager общение только с одним классом, или это нормально для одновременного общения со многими объектами.Я думаю, что большинство объектов одновременно должны знать, подписан ли пользователь или нет.Если это правда, какой тип связи я реализую?

Для одного ко многим я думаю реализовать протокол Observable, описанный в этой статье .При необходимости я могу скопировать код вместо ссылки на статью.

Надеюсь, я хорошо это описал.Я буду признателен за любой ответ.Или какие-то новые идеи, общие идеи о том, как настроить объектную коммуникацию через приложение.Вы знаете какую-нибудь хорошую статью об этом?

1 Ответ

1 голос
/ 29 мая 2019

Вся бизнес-логика должна быть внутри ViewModel. ViewModel должна вызывать любой метод внутри UserManager. UserManager должен вернуть результат, проанализированный как Модель, в ViewModel. Затем ViewModel необходимо отформатировать данные и предупредить ViewController о завершении события / данных / сети и т. Д.


Примеры форматирования данных:

  • Допустим, сетевой запрос дает вам firstName и lastName. Но у вас есть только 1 ярлык для отображения полной вещи. ViewModel должен добавить эти строки вместе (с пробелом) и предоставить свойство fullName для VC.
  • Если вы получили двойной, но вам нужно отформатировать его в валюте и отобразить символ.
  • Получение метки времени и форматирование в строку даты.

Это то, что должен делать ViewModel. Так что они могут быть протестированы независимо от кода пользовательского интерфейса и жизненного цикла.


Сообщение:

Вы можете использовать стандартные разработки Apple API и создать протокол ViewModel с делегатом и обратным вызовом. Каждая виртуальная машина подтверждает протокол, VC устанавливает себя в качестве делегата своей виртуальной машины и запускает ваш код в функции обратного вызова делегата VC.


Нейминг:

Слово «Менеджер» вышло из употребления, потому что обычно это слово используется по умолчанию, когда использование класса неясно. По этой причине у него тысяча разных определений. Класс, отвечающий за выполнение сетевых запросов и / или сохранение состояния, должен называться «Сервис». т.е. "UserService".


Состояние совместного использования:

Я, вероятно, собираюсь рассердить многих людей этим. Но когда необходимо разделить состояние между несколькими VC, компонентами, виртуальными машинами и т. Д., Я следую шаблонам проектирования / архитектуре, которые имеет Angular. Я делаю свои классы обслуживания одиночек. Пусть они хранят состояние. Затем каждая модель представления имеет один источник правды для каждого элемента и может форматировать его по своему желанию.

Другие люди используют такие среды, как RxSwift, и используют Observables и аналогичные технологии. Мое личное мнение таково, что это огромное излишество, включает в себя огромную кривую обучения, означает добавление большого количества больших библиотек и влечет за собой большой риск для проекта. Я предпочитаю придерживаться шаблонов, уже доступных и работающих в экосистеме, и упростить задачу.


Редактировать: один ко многим:

Это может зависеть от вашего варианта использования и архитектурных решений. Я обнаружил, что можно избежать проблемы «один ко многим» в большинстве моих случаев использования, так как синглтон сохраняет состояние и заставляет VC запускать что-то в ViewModel при каждом вызове viewDidAppear. Каждый раз, когда открывался ВК, он получал последние данные и продолжал. Причина, по которой я стараюсь избегать «один-ко-многим», заключается в том, что в большинстве случаев на экране присутствует только 1 виртуальный канал, и в любой момент времени выполняется код (использование childViewControllers является исключением). Я обнаружил, что можно полностью обойти эту проблему и сделать приложения простыми, изменив способ взаимодействия с данными, а не изменив структуру API-интерфейсов Apple.

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

NotificationCenter - не мой любимый подход, но если бы у меня была ситуация один ко многим, которую я не мог избежать, я бы попробовал. Как уже упоминалось в статье, есть некоторые недостатки быстрых функций, которые вы можете получить с помощью этого средства. Это, по крайней мере, имеет то преимущество, что это то, что было вокруг в течение долгого времени и хорошо понято и вряд ли сильно изменится. Там не будет большой кривой обучения, если другие разработчики работают над этим приложением.

Другой подход, упомянутый в статье, интересен, создавая собственную урезанную версию RxSwift для добавления наблюдателей в проект. В настоящий момент моя проблема с RxSwift заключается в том, что люди не используют его в сочетании с синглетонами или какой-то центральной точкой контроля. Когда у вас есть Observable на объекте A, Observed by B, у которого также есть другая Observable Observable от C, которая вызывает функцию на D, которая наблюдается E, F и G .... и так далее. Этот стиль кода невероятно запутан, труден для чтения, подвержен ошибкам и труден для отладки. До тех пор, пока этого избегают и его единый объект, который имеет наблюдаемую и все ViewModels, наблюдают, я думаю, что-то подобное будет хорошо, если вы захотите приложить усилия для его создания и обслуживания.

...