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

Вступление

Мы, как разработчики, выбираем тот или иной вид обмена информацией в зависимости от размера системы и требований. В большинстве случаев для координации сервисов можно использовать шаблон с брокером, например, на основе RabbitMQ или kafka. Иногда поток событий, SLA и уровень контроля над системой таковы, что готовые сообщения нам не подходят. Конечно, вы можете немного усложнить систему и использовать ZeroMQ или nanomsg. Поступая таким образом, вы берете на себя ответственность за транспортный уровень и формирование кластера. Но если системе не хватает пропускной способности или стандартной емкости кластера Erlang, то вопрос о добавлении дополнительной сущности требует изучения и экономического обоснования.

Тема реактивных распределенных приложений довольно обширна. Чтобы соответствовать формату статьи, сегодня мы сосредоточимся на однородных средах, построенных на Erlang / Elixir. Экосистема Erlang / OTP позволяет нам реализовать реактивную архитектуру с минимальными затратами времени и усилий. В любом случае нам понадобится уровень обмена сообщениями.

Теоретическая основа

Инжиниринг начинается с определения целей и ограничений. Основная цель не находится в области развития ради развития. Что нам нужно, так это получить безопасный и масштабируемый инструмент, который позволит нам создавать и разрабатывать современные приложения различного уровня. Приложения могут варьироваться от односерверных приложений, обслуживающих небольшую аудиторию, до кластеров из 50–60 узлов или кластерных федераций. Таким образом, наша главная цель - максимизировать прибыль за счет снижения затрат на разработку системы и владение ею.

Выделим 4 требования к целевой системе:

  • S возможность вызова. Отдельные блоки можно масштабировать как по вертикали, так и по горизонтали. Также должна быть возможность масштабировать всю систему по горизонтали без ограничений;
  • E, управляемый природой. Система всегда готова обработать поток событий и обработать его;
  • L надежность, которая гарантирована. Время - деньги, поэтому пользователям не следует ждать слишком долго;
  • Жуткая толерантность. Все уровни и сервисы должны автоматически восстанавливаться в случае сбоя.

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

Событийная природа

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

Масштабируемость

Масштабируемость и производительность системы часто идут рука об руку. Компоненты приложения должны иметь возможность использовать все доступные ресурсы. Чем эффективнее мы можем использовать мощности и чем оптимальнее наши методы обработки, тем меньше денег мы тратим на оборудование.
На одной машине Erlang создает среду с высокой степенью параллелизма. Баланс между параллелизмом и параллелизмом может быть установлен путем выбора количества потоков ОС, доступных для виртуальной машины Erlang, а также количества планировщиков, которые используют эти потоки.

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

На уровне кластера также существует проблема использования. Важно равномерно распределять нагрузку между машинами в кластере и не перегружать сеть. Представьте: пользовательский трафик попадает на балансировщики нагрузки (например, haproxy, nginx и т. Д.). Эти балансировщики распределяют запросы между доступными обработчиками в пуле серверов. В инфраструктуре приложений служба, реализующая требуемый интерфейс, - это всего лишь последняя миля. Он должен запросить ряд других служб для ответа на первоначальный запрос. Внутренние запросы также требуют маршрутизации и балансировки.
Для правильного управления потоками данных обмен сообщениями должен предоставлять разработчикам интерфейс для управления маршрутизацией и распределением нагрузки. В результате разработчики смогут использовать шаблоны микросервисов и решать как рутинные задачи, так и нестандартные.

С точки зрения бизнеса масштабируемость - один из инструментов управления рисками. Главное здесь - удовлетворить потребности клиента и эффективно использовать оборудование:

  • Если вы постепенно улучшите производительность оборудования, оно не будет простаивать из-за недостатков программного обеспечения. Erlang отлично масштабируется по вертикали и может использовать все ядра ЦП и доступную память;
  • В облачных средах мы можем управлять количеством оборудования в зависимости от текущей или прогнозируемой нагрузки и обеспечивать SLA.

Отказоустойчивость

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

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

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

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

Ответная реакция

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

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

Предварительное заключение

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

Во второй части статьи мы поговорим о нюансах реализации точек обмена и схемах обмена сообщениями.

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

Конец первой части.

Фото Лука Браво