TeqFW: Events basic

Дата публикации: 2022-01-05

JavaScript, который является основным языком для создания teq-приложений, очень хорошо подходит для асинхронного программирования. В асинхронном программировании “события” играют очень важную роль. В этой публикации я в очень общем виде описываю, каким образом “события” используются в Tequila Framework.

Что такое “событие”

Событие — это значимое изменение состояния приложения (например, “пользователь аутентифицирован”). С событием обязательно связаны некие данные (“идентификатор пользователя”). Событие возникает, как результат выполнения некоторого действия (“проверка входного имени и пароля и сопоставление их идентификатору пользователя”) и само является причиной для выполнения других действий (“загрузка профиля пользователя”).

Image 2

Итого, в самом простом случае мы имеем два функциональных объекта и один дата-объект: Event Producer изменяет состояние приложения и генерирует сообщение о событии (Event Message), передаваемое одному или нескольким Event Handler’ам, которые реагируют на изменение состояния.

Событие прежде всего характеризуется своим типом (например, onClick) и связанным с ним набором данных (например, MouseEvent).

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

Локальные и трансграничные события

Teq-приложение, как правило, состоит из двух частей — фронта (в браузере) и бэка (nodejs-приложение на сервере). Если и генератор события, и обработчик находятся в пределах одной части (оба на фронте или оба на бэке), то такое событие считается локальным. Если в разных частях — трансграничным.

Сообщения о трансграничных событиях передаются по интернету в текстовом виде (JSON) и должны содержать только такие данные, которые могут быть сериализованы в JSON и десериализованы из него без потерь. Сообщения о локальных событиях находятся в пределах выполнения одного программного процесса и к ним подобные ограничения не применяются.

Наименование событий

Имя события (его тип) должно быть уникально в пределах всего приложения. Так как в teq-приложениях используются namespace’ы, то вполне естественным является решение, когда отдельному событию соответствует отдельный es6-модуль, логическое имя которого и является именем события:

es6-модуль помимо имени события инкапсулирует также структуру данных (DTO) для сообщения о событии.

Обработка локальных событий

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

emit(eventName, message) {}
subscribe(eventName, handler) {}
unsubscribe(subscription) {} Подписчик сообщает генератору, на какое его событие он хочет получать сообщения, и предоставляет генератору обработчик для реакции на событие. Когда генератор фиксирует наступление нужного события, он отправляет сообщение с деталями события обработчику:
Image 3

Поскольку все действия происходят либо только на фронте (браузер), либо только на бэке (nodejs), то обработка локальных событий является тривиальной по отношению к обработке событий трансграничных.

Обработка трансграничных событий

В трансграничных событиях генератор событий находится на одной стороне (фронт или бэк), а подписчик — на другой (бэк или фронт). Между ними — нестабильный канал связи (поскольку мы говорим за мобильные web-приложения). Событие, которое происходит на фронте, генерирует сообщение, которое доставляется на бэк, и уже там соответствующий обработчик выполняет с ним необходимые действия:

Image 4

Генератор событий отправляет сообщения в очередь, которая мониторит состояние канала связи между сторонами и отправляет сообщения на другую сторону по мере возможности. На второй стороне находится представитель (“посольство”), который позволяет через него подписаться на любое событие, происходящее на “той” стороне. Как только представитель получает сообщение о событии через сеть, он перенаправляет его соответствующему обработчику.

Принцип обработки идентичен как для направления “фронт — бэк”, так и для обратного направления.

Резюме

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