Автомасштабирование обеспечивает эффективность и надёжность приложения. Оно автоматически адаптирует ресурсы в соответствии с потребностями. В периоды пиковой нагрузки — увеличивает, в более спокойные периоды — уменьшает для снижения затрат. Эта гибкость особенно полезна для обработки непредсказуемого трафика: приложения остаются отзывчивыми и не используют ресурсов больше, чем необходимо. Перевели статью о том, как настроить Kafka Scaler на основе задержки подписчика (consumer lag).

Сustom Metrics Autoscaler Operator

Сustom Metrics Autoscaler Operator (далее — оператор автомасштабирования на основе пользовательских метрик) расширяет возможности масштабирования Red Hat OpenShift, особенно для приложений на основе event-driven — событийно-ориентированной — архитектуры. Стандартный Horizontal Pod Autoscaler (HPA) в основном масштабирует приложения на основе показателей использования CPU и памяти. Эти показатели не всегда являются лучшими индикаторами. Например, использование CPU и памяти может оставаться низким, даже когда приложение обрабатывает большой объём запросов или данных. Это несоответствие может привести к недоиспользованию ресурсов или, наоборот, к неспособности эффективно справляться с пиковыми нагрузками.

Оператор автомасштабирования на основе пользовательских метрик предлагает сложные стратегии масштабирования. Он может регулировать ресурсы в ответ на события из внешних источников, таких как Kafka. Это даст больше контроля над масштабированием приложения. Кроме того, этот оператор позволяет масштабировать рабочие нагрузки до нуля. То есть оптимизировать использование ресурсов, когда нет активной рабочей нагрузки. Оператор автомасштабирования на основе пользовательских метрик упрощает управление бессерверными рабочими нагрузками в OpenShift. Он основан на проекте KEDA (Kubernetes Event-Driven Autoscaler), который предоставляет широкий набор средств масштабирования. 

Чтобы не путаться в терминологии, будем использовать следующие термины Kafka:

  • Тема (Topic)

  • Подписчики (Consumer)

  • Издатель (Producer)

  • Группа (Group), раздел (Partition)

Kafka Scaler

Kafka Scaler отслеживает задержки подписчика в темах, чтобы динамически масштабировать приложение. Задержка подписчика (consumer lag) — это разница между самым новым отправленным сообщением и последним обработанным сообщением. Зная эту задержку, мы можем точнее масштабировать приложение, потому что мы учитываем насколько эффективно оно обрабатывает входящие записи.

Когда задержка подписчика превышает заданный порог — это сигнал, что приложение отстаёт в обработке входящих сообщений. Поэтому оператор масштабирует количество экземпляров приложения подписчика, чтобы справиться с возросшей нагрузкой. По мере уменьшения задержки, указывающей на то, что сообщения обрабатываются должным образом, он сокращает количество экземпляров. Так обеспечивается эффективная обработка сообщений Kafka. Мы можем масштабировать ресурсы вверх или вниз в зависимости от спроса в реальном времени и поддерживать оптимальную производительность приложения.

На рисунке ниже показана логика масштабирования приложения вверх и вниз на основе задержки подписчика. На рисунке 1(а) задержка велика, и кажется, что подписчик не успевает за поступающими записями. На рисунке 1(b) оператор автомасштабирования на основе пользовательских метрик масштабировал приложение подписчика, и задержка подписчика уменьшилась. На рисунке 1(c) приложение масштабируется вниз, поскольку задержка подписчика уменьшилась.

Стандартная архитектура Kafka Producer-Consumer Application. Источник
Стандартная архитектура Kafka Producer-Consumer Application. Источник

Архитектура

В этом разделе мы рассмотрим архитектуру автомасштабирования на основе пользовательских метрик в контексте Kafka Scaler и то, как компоненты связаны и работают вместе.

Архитектура оператора автомасштабирования на основе пользовательских метрик с участием Kafka. Источник
Архитектура оператора автомасштабирования на основе пользовательских метрик с участием Kafka. Источник

Рассмотрим компоненты:

  1. Controller: контроллер непрерывно отслеживает настроенные ресурсы ScaledObject, управляет динамическим масштабированием рабочих нагрузок на основе определённых триггеров и критериев метрик. Это обеспечивает оптимальное распределение ресурсов. Как только контроллер обнаруживает ресурс ScaledObject, он получает информацию от ScaledObject и создаёт Horizontal Pod Autoscaler для приложения.

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

  1. Metrics Adapter: адаптер метрик преобразует исходные метрики, такие как задержка подписчика в нашем случае, в формат, понятный OpenShift, предоставляя эти пользовательские метрики HPA. Сервер метрик действует как интерфейс между сервером API OpenShift и внешними метриками, предоставляя необходимые данные контроллеру HPA.

  1. Scaler: Основная роль скейлера — подключаться к внешней системе и получать метрики или данные, указывающие на текущую нагрузку или спрос. В нашем случае Kafka scaler использует учётные данные из TriggerAuthentication для аутентификации в кластере Kafka и получает задержку подписчика для указанной темы и группы подписчиков. Затем он отправляет метрики задержки подписчиков обратно адаптеру метрик.

  1. HPA: Horizontal Pod Autoscaler оценивает метрики, полученные от адаптера метрик, по критериям масштабирования, определённым в ScaledObject. HPA взаимодействует с API OpenShift, чтобы масштабировать модули вверх/вниз через развёртывание. Количество реплик развёртывания увеличивается, если задержка превышает пороговое значение. В случае, если задержка ниже или равна порогу, установленному в ScaledObject, количество реплик сокращается, чтобы минимизировать использование ресурсов.

Конфигурация Kafka Scaler

TriggerAuthentication

TriggerAuthentication имеет решающее значение для обеспечения возможности скейлера аутентифицироваться и подключаться к внешней системе. В нашем случае — к кластеру Kafka, чтобы получать метрики, необходимые для принятия решений о масштабировании. Kafka Scaler требует определённых данных аутентификации, таких как сертификаты, механизмы SASL и учётные данные. Эти данные будут различаться в зависимости от настроек аутентификации вашего кластера Kafka. Поэтому конфигурация TriggerAuthentication должна соответствовать методу аутентификации кластера Kafka.

Аутентификация SASL PLAINTEXT/SHA512

Если ваш кластер Kafka настроен на аутентификацию с использованием SASL_PLAINTEXT или SASL_SHA512, вам потребуется секрет, содержащий эти пары «ключ-значение».

kind: Secret
apiVersion: v1
metadata:
  name: kafka-auth-secret
data:
  tls: "enable | disable" base64
  ca: "kafka_cluster_certificate" base64
  sasl: "plaintext | scram_sham256 | scram_sham512" base64
  username: "username" base64
  password: "password" base64
type: Opaque

Это ассоциируется с TriggerAuthentication CR:

kind: Secret
apiVersion: v1
metadata:
  name: kafka-auth-secret
data:
  tls: "enable | disable" base64
  ca: "kafka_cluster_certificate" base64
  cert: "user_certificate" base64
  key: "user_private_key" base64
type: Opaque

Конфигурация mTLS

Если в вашем кластере Kafka используется аутентификация mTLS, настройте скейлер с помощью секрета, содержащего эти пары «ключ-значение»:

kind: Secret
apiVersion: v1
metadata:
  name: kafka-auth-secret
data:
  tls: "enable | disable" base64
  ca: "kafka_cluster_certificate" base64
  cert: "user_certificate" base64
  key: "user_private_key" base64
type: Opaque

TriggerAuthentication должен выглядеть следующим образом:

apiVersion: keda.sh/v1alpha1
kind: TriggerAuthentication
metadata:
 ...
spec:
  secretTargetRef:
    - key: cert
  name: kafka-auth-secret
  parameter: cert
    - key: key
  name: kafka-auth-secret
  parameter: key
    - key: tls
  name: kafka-auth-secret
  parameter: tls
    - key: ca
  name: kafka-auth-secret
  parameter: ca

Обратите внимание! Если ключ находится в формате PKCS8, оператор пользовательских метрик не сможет его использовать. Вы должны преобразовать его в формат PKCS5, известный как формат RSA. Чтобы выполнить преобразование, выполните следующие действия:

Преобразование приватного ключа в формате PKCS8 в PKCS5 (RSA)

1. Получите закрытый ключ и пароль пользователя:

oc get secret -o json -n | jq -r '.data["user.key"]'| base64 --decode > user.key

2. Преобразуйте закрытый ключ pkcs8 в pkcs5:

openssl rsa -in user.key -out user-rsa.pem

3. Перекодируйте в base64:

RSA_KEY=$(base64 /path/to/user-demo-rsa.pem)

4. Добавьте закодированный файл в свой секрет:

oc patch secret ch-custom-metrics-autoscaler.demo-user -p '{"data":{"user-rsa.key":"$RSA_KEY"}}'

ScaledObject

ScaledObject — это ключевой компонент, который выступает в роли пользовательского ресурса. С помощью него определяется поведение скейлера. Он управляет тем, как и когда происходит масштабирование на основе определённых метрик. Чтобы лучше понять доступные параметры, давайте рассмотрим пример пользовательского ресурса scaledObject:

apiVersion: keda.sh/v1alpha1
kind: ScaledObject
metadata:
 ...
spec:
  advanced:
    horizontalPodAutoscalerConfig:
  name: kafka-hpa
  behavior:
    scaleDown:
      stabilizationWindowSeconds: 300 (1)
    scaleUp:
      stabilizationWindowSeconds: 30 (1)
    restoreToOriginalReplicaCount: true (2)
  cooldownPeriod: 60  (3)
  maxReplicaCount: 10 (4)
  minReplicaCount: 1  (5)
  pollingInterval: 10 (6)
  idleReplicaCount: 0 (7)
  scaleTargetRef: (8)
    apiVersion: apps/v1
    kind: Deployment
    name: consumer-demo
  Triggers: (9)
    - authenticationRef: (10)
    kind: TriggerAuthentication
    name: <your_triggerAuthentication_name>
  metadata:
    bootstrapServers: <your_bootstrapserver>

    consumerGroup: <your_consumergroup>
    lagThreshold: <threshold>
    topic: <your_topic>
  type: kafka
  1. StabilizationWindowSeconds — это время в секундах, в течение которого учитываются предыдущие рекомендации по масштабированию при принятии решения о масштабировании вверх или вниз ваших реплик. Это помогает скейлеру не слишком остро реагировать на краткосрочные изменения и вместо этого принимать решения о масштабировании на основе более широкого представления о том, что происходило в последнее время. Например, ваша система проверяет показатели масштабирования каждые 10 секунд. Это является вашим pollInterval, и вы установили значение StabilizationWindowSeconds равным 150 секундам. В этой конфигурации система будет учитывать 15 последних показателей (150 [с] / 10 [с]), чтобы принять решение о масштабировании вашего приложения вверх или вниз.

  1. restoreToOriginalReplicaCount: если значение равно true, то после того, как масштабирование, основанное на событиях, больше не требуется, развёртывание будет возвращено к исходному количеству реплик. Если значение равно false, то количество реплик будет поддерживаться на основе параметров min/max.

  1. cooldownPeriod: период охлаждения предназначен специально для сценария, когда масштабирование уменьшается до нуля. За масштабирование от одного до любого большего числа реплик отвечает Kubernetes Horizontal Pod Autoscaler.

  1. maxReplicaCount: максимальное количество реплик, которое HPA может масштабировать. Если установить слишком низкое значение, это может ограничить способность приложения обрабатывать большие нагрузки; слишком высокое значение может привести к потенциальному перерасходу ресурсов. Важно отметить, что в группе подписчиков Kafka максимальное эффективное количество подписчиков ограничено количеством разделов в теме. Если вы добавите больше подписчиков, чем разделов, дополнительные подписчики будут простаивать. Поэтому значение maxReplicaCount следует установить максимум равным количеству разделов в вашей теме.

  1. minReplicaCount: минимальное количество реплик, которое HPA должен поддерживать для целевого ресурса.

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

  1. idleReplicaCount: когда триггеры неактивны, ресурсы масштабируются до значения idleReplicaCount, которое установлено равным 0. Как только появляется какая-либо активность, ресурс быстро масштабируется до minReplicaCount. В настоящее время поддерживается только значение 0.

  1. scaleTargetRef: определяет, какое развёртывание предназначено для автомасштабирования.

  1. Triggers: в разделе триггеров определяется, какой скейлер использовать. В нашем случае мы используем Kafka Scaler и параметры, связанные со скейлером, такие: имя темы (topic name), загрузочный сервер (bootstrap server), группа подписчиков (consumer group), пороговое значение (threshold) и т. д.

  1. authenticaitonRef: ссылка на объект TriggerAuthentication, который будет использоваться скейлером для аутентификации во внешней системе.

Настройка порогового значения

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

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

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

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

Важно протестировать Kafka Scaler при различных условиях нагрузки. Нагрузочное тестирование помогает вам наблюдать за поведением и эффективностью скейлера. У вас появятся идеи, как доработать настройки пороговых значений в будущем.

Сценарии настройки

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

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

  • Быстрое масштабирование (низкая инерция): этот сценарий предназначен для ситуаций, когда критически важен быстрый отклик на изменения рабочей нагрузки. Цель состоит в том, чтобы быстро увеличить ресурсы, когда есть всплеск спроса (например, внезапный приток сообщений), и аналогично быстро уменьшить их, когда спрос падает. Такая настройка идеальна для рабочих нагрузок с внезапными краткосрочными колебаниями.

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

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

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

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

Сценарий

Stabilization Window Seconds

Cooldown Period

Max Replica Count

Min Replica Count

Polling Interval

Быстрое масштабирование (низкая инерция)

Низкое значение

Минимальное значение

Высокое значение

Низкое значение

Низкое значение

Медленное масштабирование (высокая инерция)

Увеличенное значение

Высокое значение

Умеренное значение

Высокое значение

Увеличенный интервал

Использовать известные пиковые периоды

От умеренного до высокого

Умеренное

Высокое значение

С поправкой на среднюю нагрузку

Умеренное

Начальная нагрузка

Низкое значение

Низкое значение

Высокое значение

Умеренное значение

Низкое значение

Постоянно высокая нагрузка

Умеренное

Не актуально

Очень высокое

Высокое

Умеренно высокое

Итоги

Мы рассмотрели интеграцию автоскейлера пользовательских метрик с триггером Kafka и то, как он регулирует ресурсы в зависимости от требований к обработке данных. Мы объяснили ключевые компоненты — TriggerAuthentication и ScaledObject — и их параметры. Описали различные составляющие автоскейлера пользовательских метрик.

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


Если у вас возникают проблемы в работе с Apache Kafka, приходите в Слёрм на курс Apache Kafka База. Наши спикеры расскажут: 

  • как настраивать распределенный отказоустойчивый кластер; 

  • как отслеживать метрики; 

  • как равномерно распределять нагрузки. 

Первые 3 темы можно пройти бесплатно. 

? Запишитесь на бесплатный на мини-курс и ознакомьтесь с программой полного курса на нашем сайте.

Комментарии (0)