{"id":14106,"url":"\/distributions\/14106\/click?bit=1&hash=5b1c362bb484a3a1cce6bca3456d67fbaba6c95569816bec34c5a85ebfa3d189","title":"\u041a\u0430\u043a \u0443\u043f\u0440\u0430\u0432\u043b\u044f\u0442\u044c \u043a\u043e\u043c\u0430\u043d\u0434\u043e\u0439 \u043f\u0440\u043e\u0435\u043a\u0442\u0430 ","buttonText":"","imageUuid":""}

Для чего используем библиотеку реактивного программирования NgRx

Пользователи сайтов или приложений ожидают, что интерфейс будет мгновенно реагировать на их действия. Нажал кнопку «Положить в корзину» — сразу же кнопка товара поменялась на «В корзине», а в верхнем меню возле значка корзины появилось количество товаров.

Реактивный подход к разработке подразумевает, что программа сама отслеживает события и реагирует на них. Это похоже на работу в таблицах Excel: пользователь меняет значение одной ячейки — и все взаимосвязанные ячейки автоматически меняют свое значение.

В статье расскажем, в чем суть реактивного программирования, в каких проектах оно необходимо, а в каких излишне и почему мы используем для разработки реактивных продуктов NgRx, библиотеку на фреймворке Angular.

Подробнее о фреймворке и его возможностях мы рассказали в статье «Какие задачи решаем с помощью Angular. На примере системы учета Posiflora»

Как работает реактивный сайт

Чтобы сделать путь пользователя от входа на сайт до оплаты заказа простым и удобным, нужно продумать каждое его действие и предусмотреть автоматические реакции на них. Любое действие пользователя можно разложить на этапы:

  1. Событие — действие пользователя с интерфейсом сайта. Например, клиент выбрал товары на сайте и добавляет их в корзину.

  2. Запрос сайта к серверу — какой товар покупатель хочет положить в корзину и в каком количестве.

  3. Ответ сервера — информация об успешной операции.

  4. Реакция — изменение интерфейса на действие пользователя:

  • кнопка «Добавить в корзину» на товаре меняется на «В корзине»;

  • меняется значок самой корзины;

  • обновляются сумма и количество товара в корзине.

Пользователь видит только изменение надписи на кнопке, в то время как программа уже пообщалась с сервером и подтвердила операцию

Чтобы программа реагировала на действия пользователя, разработчик описывает переменные, которые содержат данные. В нашем примере переменная — корзина, а данные — ее состояние: вид и количество товаров. Когда приходит запрос предоставить или обновить данные, сайт отвечает и выдает нужный результат: обновляются состав и значок корзины, надпись на кнопке.

При традиционном подходе все действия разработчику нужно прописывать вручную: изменить кнопку, обновить число и сумму. Для небольших проектов это удобно. Но если программе нужно обрабатывать много потоков данных из разных источников, сложно заранее продумать и описать все реакции на все запросы. Разработчик может допустить ошибку, забыть обновить переменную или не учесть какой-то запрос.

Реактивный подход подразумевает, что программа сама отслеживает события и реагирует на них. Процесс разработки в этом случае выглядит так:

  • Сначала разработчик определяет в программе:

    ~ реактивную переменную — источник события (Publisher). В нашем примере это состояние кнопки «Добавить в корзину»;

    ~ зависимые переменные — подписчики события (Subscribers). В примере это значок корзины, количество товара, сумма корзины, надпись на кнопке.

  • Когда происходит событие — пользователь нажимает кнопку, состояние источника меняется, — подписчики получают эту информацию и автоматически меняют свое состояние: вид корзины, число товаров в корзине, сумма и текст кнопки.

В реактивном программировании подписчики следят за изменением источника и автоматически изменяют свое состояние

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

Почему мы выбираем библиотеку NgRx для реактивного программирования

NgRx — библиотека для реактивного программирования приложений во фреймворке Angular от компании Google. Библиотеки делают разработку проще благодаря набору готовых решений: функций, объектов, классов. Разработчики OrbitSoft используют NgRx в проектах, где нужно упростить и ускорить обработку данных, поступающих на сервер.

Вот главные причины использования этой библиотеки.

Меньше ошибок в работе продукта

При работе с большими массивами данных всегда есть риск ошибок. Ошибки приводят к сбоям в работе программы — пользователям это не нравится. Реактивное программирование снижает вероятность ошибок. Статичные данные привязывают к источнику изменений и дают команду обновлять их при наступлении события — данные обновляются автоматически и независимо друг от друга. Поэтому реактивное приложение или сайт работает быстрее, а количество сбоев уменьшается.

Также снизить вероятность ошибок помогает фундаментальный стек Angular — TypeScript, или строго типизированное программирование. Когда разработчик вводит переменную, он сразу указывает ее тип — так система понимает, с какими данными переменная будет работать. В дальнейшем это упрощает доработку и изменение кода: даже сторонний разработчик поймет цель назначения переменной и не допустит ошибок.

Гибкое управление данными

Например, покупатель кладет в корзину товар, но ничего не происходит: ни сумма, ни количество товара в корзине не изменяются. Он в нетерпении жмет на кнопку «Добавить в корзину» еще несколько раз.

В классическом программировании разработчик должен позаботиться о том, чтобы множество кликов не передавало на сервер сигнал о многократном добавлении в корзину. Ему нужно предусмотреть блокировку кнопки или не давать отправку сигнала при многократных кликах.

В реактивном программировании есть возможность автоматически прервать предыдущий запрос и создать новый. Или, наоборот, подписчики забирают данные из первого события, а на остальные не реагируют. Разработчик может предусмотреть разные реакции на событие, а библиотека со множеством вариантов решений позволяет ему быть гибким.

Сортировка полученных данных

Источник может отправлять очень много данных. Не все из них нужны конкретному подписчику. Чтобы убрать лишние и переделать их в понятный подписчику формат, данные нужно отсортировать, перевести в нужный вид и выдать пользователю.

Например, в CRM источник отправляет подписчикам данные по продажам: общий объем продаж, суммы по магазинам, средний чек, количество сделок и другие. Один из подписчиков — окошко на панели инструментов, где отображается, в каком магазине сегодня самая большая выручка. Этому подписчику не нужна вся информация по продажам — только максимальный размер выручки на сегодня и имя торговой точки.

Чтобы отсортировать нужную информацию, данные от источника передаются в пайпы (pipes) — инструменты, которые последовательно выполняют какую-то цепочку действий. В нашем примере один пайп фильтрует из всех данных только суммы продаж по отдельным магазинам, другой сортирует их и выбирает наибольшую, третий переводит данные в денежный формат и отдает подписчику. Подписчик реагирует: в окошке на панели CRM пользователь видит магазин с максимальной выручкой и ее объем.

Предсказуемая структура кода

Некоторые библиотеки позволяют компоновать код, как удобно разработчику. Это не всегда хорошо. Чтобы другие разработчики тоже могли работать с программой, части кода должны располагаться в предсказуемом месте. Например, контроллер — после модели.

Во фреймворке Angular разработчик пишет код по заданной структуре. Это упрощает изменения, тестирование и отладку продукта. Для заказчика это тоже плюс: продукт можно быстрее внедрить и начать зарабатывать.

Еще у Angular есть инструменты командной строки, которые позволяют создавать новые компоненты. Например, часто используемый компонент — базовое описание тестов. Он позволяет автоматически предотвратить некоторые ошибки в коде еще до того, как продукт попадет к тестировщикам. Так, если в большой проект пришел новый разработчик, автоматические тесты помогут найти и исправить ошибки еще до пререлиза.

Готовые компоненты для интерфейсов

В Angular можно добавлять готовые компоненты дизайн-системы Material Design: баннеры, чекбоксы, формы, кнопки. Они помогают создавать современный интерфейс и упрощают сборку и верстку сайта. Дизайнеру не нужно заново отрисовывать компоненты, он вставляет в макет готовые и настраивает по брендбуку заказчика. Фронтенд-разработчик добавляет в проект набор компонентов Angular Material и подключает на каждой из страниц те, что нужны по макету.

Готовые компоненты Material Design значительно ускоряют верстку сайтов

Разработали реактивный видеопортал с использованием библиотеки NgRx

Мы использовали метод реактивного программирования Angular для видеопортала сети клиник пластической хирургии. Заказчик проводит тренинги для врачей и регулярно выкладывает на сайт видеоролики и файлы с обучающими материалами.

Первоначальный видеопортал сильно устарел: тормозил и выдавал ошибки. Мы его оптимизировали: теперь страницы открываются мгновенно, большие файлы загружаются полностью, портал выдерживает более 10 тысяч зрителей во время прямых трансляций. Подробнее о проекте — в статье «OrbitSoft починил: как мы переписали медицинский видеопортал с нуля». В этом проекте реактивное программирование применялось ко всем данным, которые мы получали с бэкенда.

Настроили фоновую загрузку файлов

После оптимизации сайта файлы стали загружаться в фоновом режиме, а клиенту приходят оповещения о выполнении процесса. Пока загружается видео, пользователи могут продолжать работать с сайтом, а в поп-ап-окне отображается прогресс загрузки.

Это стало возможным благодаря реактивному программированию: при загрузке нового файла программа делит его на части и поочередно загружает. Как только добавлена новая порция видео, назначенные подписчики события (Subscribers) получают оповещения и обновляют информацию о загруженных файлах.

Подписчик отображает статус: на сколько процентов загружен файл, его тип и размер

Создали систему уведомлений о начале трансляции

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

Чтобы это происходило, разработчик назначил событие — начало трансляции — и определил подписчика — сервис отправки сообщений. Как только администратор запускает трансляцию, подписчик рассылает уведомления пользователям, которые оставили контактные данные.

Оптимизировали поиск по сайту

Реактивное программирование позволило улучшить поиск по сайту и быстрее отвечать на запросы пользователей.

Когда пользователь вводит фразу в строке поиска любого раздела, он видит предварительные результаты. Если он выбирает «Посмотреть все», сайт показывает ему страницу со всеми результатами, где содержится эта фраза.

Пользователь начал вводить запрос, и портал сразу предлагает ему результаты по всем разделам: 20 видео, трансляция и 2 новости. Чтобы посмотреть выдачу по всем разделам, нужно кликнуть на общее количество результатов

Чтобы так получалось, разработчик определил подписчика и событие — ввод текста в строку поиска. Когда пользователь вводит поисковую фразу, подписчик реагирует на событие — анализирует все страницы сайта и показывает результат пользователю. Если человек переформулировал или изменил запрос, предыдущий запрос отменяется. Подписчик получает новые данные, и процесс с подбором подходящих страниц повторяется. В классическом подходе распределять данные по страницам пришлось бы вручную.

Кому не подойдет реактивное программирование на Angular

Небольшим компаниям

Реактивная разработка подходит компаниям, которым нужно обрабатывать большое количество данных и распределять их по разным участкам проекта. Например, когда пользователь нажимает одну кнопку, а у него одновременно обновляется таблица, график и другие элементы на странице. В этом случае велик риск ошибки разработчика, а реактивное программирование снижает такую вероятность.

В небольших проектах реактивная разработка избыточна: не нужно усложнять код, если процессов немного.

Новичкам в разработке

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

0
Комментарии
-3 комментариев
Раскрывать всегда
{"hash":"6d762cd3","params":{"id":"https%3A%2F%2Fvk.com%2Fvideo_ext.php%3Foid%3D-22522055%26id%3D456243063%26hd%3D2","service":3,"title":"\u0422\u043e\u043f-25 \u0441\u0442\u0430\u0440\u0442\u0430\u043f\u043e\u0432 Sber500 \u0432 \u044d\u0444\u0438\u0440\u0435","isLegacy":true,"isHidden":false}}