Перейти до вмісту

Модуль 9.2: Керовані брокери повідомлень та Event-Driven Kubernetes

Складність: [COMPLEX] | Час на виконання: 2.5 год | Передумови: Модуль 9.1 (Інтеграція реляційних БД), основи Kubernetes Deployments

Чому цей модуль важливий

Розділ «Чому цей модуль важливий»

У березні 2023 року логістична компанія, що обробляла 2 мільйони подій відстеження посилок на день, запустила RabbitMQ як StatefulSet у своєму кластері GKE. Система працювала ідеально вісім місяців. Потім настав період розпродажів. Обсяг подій зріс до 11 мільйонів на день. Спрацював алярм по пам’яті RabbitMQ, заблокувавши всі вхідні повідомлення. Під час перезапуску вузлів кластер увійшов у стан split-brain (розрив свідомості). 340 000 подій було втрачено назавжди. Клієнти не могли відстежити посилки 6 годин, а штрафи за порушення SLA склали $1.2 мільйона.

Висновок постмортему був жорстким: “Ми намагалися керувати складною розподіленою системою, не маючи глибокої експертизи в RabbitMQ. Нам слід було використовувати керований сервіс.” За два тижні вони перейшли на Amazon SQS. В SQS немає алярмів по пам’яті, немає проблем зі split-brain і не треба налаштовувати дзеркалювання черг. Він просто масштабується під будь-яке навантаження.

Цей модуль навчить вас інтегрувати керовані брокери — SQS/SNS, Google Pub/Sub та Azure Service Bus — із вашим Kubernetes. Ви дізнаєтеся, як використовувати KEDA для автомасшабування на основі довжини черги, як працювати з чергами “мертвих листів” (Dead-Letter Queues) та як гарантувати обробку повідомлень без дублікатів.


Основи обміну повідомленнями

Розділ «Основи обміну повідомленнями»

Перш ніж занурюватися в хмарні сервіси, розберемо два головні патерни:

  1. Point-to-Point (Черга): Один відправник -> Один отримувач. Повідомлення зникає з черги, як тільки його хтось забрав. (напр. SQS Queue).
  2. Publish-Subscribe (Топік): Один відправник -> Багато отримувачів. Повідомлення копіюється в усі активні підписки. (напр. SNS Topic, Pub/Sub).

Більшість хмарних брокерів гарантують доставку at-least-once (мінімум один раз). Це означає, що іноді (рідко) додаток може отримати одне й те саме повідомлення двічі. Важливо: Ваш код має бути ідемпотентним. Це означає, що якщо ви обробите одну й ту саму оплату два рази, гроші з клієнта мають знятися лише один раз.


Порівняння хмарних брокерів

Розділ «Порівняння хмарних брокерів»
ФункціяAWS SQS/SNSGoogle Pub/SubAzure Service Bus
МасштабуванняМайже нескінченнеПланетарний масштабЗалежить від тарифу
Макс. розмір256 КБ10 МБ256 КБ - 100 МБ
FIFO (черговість)Так (спеціальні черги)Так (Ordering keys)Так (Sessions)
Dead-letterВбудованоВбудованоВбудовано

KEDA: Автомасшабування за подіями

Розділ «KEDA: Автомасшабування за подіями»

Традиційний Kubernetes масштабує поди за CPU або пам’яттю. Але для обробника черги це не має сенсу: якщо в черзі мільйон повідомлень, а CPU воркера 10% — Kubernetes не додасть нових подів.

KEDA (Kubernetes Event-Driven Autoscaling) вирішує це. Вона “дивиться” прямо в чергу (SQS, Pub/Sub тощо) і каже Kubernetes: “У нас завал, запускай ще 50 подів!”.

Scale-to-Zero: KEDA може повністю видалити всі поди, якщо черга порожня, і запустити їх знову, як тільки з’явиться хоча б одне повідомлення. Це економить купу грошей.


Що робити, якщо повідомлення викликає помилку в коді? Без DLQ воно буде повертатися в чергу вічно, “вбиваючи” ваш процесор. DLQ (Черга мертвих листів) — це спеціальний “відстійник”. Якщо повідомлення не вдалося обробити 3 рази поспіль, брокер переносить його в DLQ. Ви можете налаштувати алерт: “якщо в DLQ з’явилося повідомлення — значить у нас баг”.


ПомилкаЧому це стаєтьсяЯк виправити
Масштабування по CPUСтандартна логіка HPAВикористовуйте KEDA для масштабування за довжиною черги
Немає ідемпотентностіНадія, що повідомлення прийде 1 разЗавжди використовуйте унікальні ID повідомлень для перевірки в базі даних
Відсутність DLQ”Код ніколи не помиляється”Завжди налаштовуйте DLQ для кожної черги продакшну
Низький Visibility TimeoutПовідомлення повертається в чергу раніше, ніж под встиг його обробитиVisibility Timeout має бути на 50% більшим за максимальний час роботи вашого коду

1. Що таке "Visibility Timeout" (таймаут видимості) в SQS?

Це час, протягом якого повідомлення стає невидимим для інших отримувачів після того, як його забрав перший под. Якщо за цей час под не видалив повідомлення (не підтвердив успіх), воно знову стає видимим для всіх.

2. Коли варто використовувати масштаб до нуля (scale-to-zero) у KEDA?

Коли обробка не є супер-терміновою (напр. генерація звітів або бекапи) і черга часто буває порожньою. Пам’ятайте: перший запуск пода після нуля може зайняти 30-60 секунд (холодний старт).


Практична вправа: Масштабування черги

Розділ «Практична вправа: Масштабування черги»
  1. Встановіть KEDA у свій кластер через Helm.
  2. Створіть ScaledObject, який стежить за вашою хмарною чергою.
  3. Налаштуйте параметри:
    • queueLength: "50" (один под на 50 повідомлень).
    • minReplicaCount: 0.
    • maxReplicaCount: 10.
  4. Забийте чергу 500 повідомленнями і подивіться, як Kubernetes миттєво запустить 10 подів.

Переходьте до Модуля 9.3: Взаємодія з Serverless — ви навчитеся з’єднувати Kubernetes із Lambda та Cloud Functions, створюючи гібридні системи, що поєднують потужність кластера та гнучкість безсерверних функцій.