Kubernetes Autoscaling в 2026: HPA, VPA, KEDA, Cluster Autoscaler и Karpenter

Валерий Волков

Время прочтения 13 минут

Autoscaling в Kubernetes работает не на одном уровне. HPA, VPA, KEDA, Cluster Autoscaler и Karpenter решают разные задачи: одни меняют число pod’ов, другие помогают подобрать requests и limits, третьи добавляют или убирают ноды кластера.

Если разобрать более подробно, то:

  • HPA (Horizontal Pod Autoscaler) масштабирует количество реплик, когда нагрузка хорошо видна через CPU, память или внутренние метрики приложения.
  • VPA (Vertical Pod Autoscaling) помогает подобрать размер pod’а: requests и limits, от которых зависят планирование, стоимость и расчёт загрузки для HPA.
  • KEDA (Kubernetes Event-driven Autoscaling) нужна, когда главный сигнал находится вне pod’а: очередь, Kafka lag, события, расписание или облачная метрика.
  • Cluster Autoscaler добавляет или убирает ноды в рамках заранее заданных node groups, когда pod’ам не хватает места.
  • Karpenter гибче подбирает capacity под требования pod’ов: типы инстансов, зоны, spot/on-demand, лимиты NodePool и consolidation.

Главная ошибка — выбрать инструмент не под тот сигнал. HPA может увеличить реплики, но не добавит ноды. KEDA может увидеть очередь, но не исправит неверные requests. VPA может подсказать размер pod’а, но не спасёт от резкого роста трафика. Cluster Autoscaler и Karpenter могут дать ёмкость, но не решат, сколько реплик нужно приложению.

Экономия тоже не появляется от самого факта включения autoscaler. На стоимость влияют requests, minReplicas, maxReplicas, лимиты node pool, время прогрева, политика scale-down, SLO и допустимость холодного старта. Поэтому правильный порядок такой: сначала определить сигнал нагрузки, затем объект масштабирования, потом границы роста и сжатия, и только после этого выбирать HPA, VPA, KEDA, Cluster Autoscaler или Karpenter.

Почему одного HPA обычно недостаточно 

Команда включает HPA, видит рост числа реплик и считает масштабирование закрытым. Через неделю выясняется другое: часть pod’ов висит в Pending, очередь Kafka растёт быстрее, чем CPU, ночной scale-to-zero даёт холодный старт, а счёт за AWS, Google Cloud или Azure почти не снижается.

Проблема обычно не в HPA. Он просто отвечает за свой уровень — количество реплик. Если pod’ам негде запускаться, нужен autoscaling уровня нод. Если нагрузка видна не по CPU, а по длине очереди или lag consumer’а, нужен событийный сигнал. Если pod’ы годами живут с неверными requests, масштабирование будет принимать решения на искажённой базе.

Поэтому ключевой вопрос звучит не “какой autoscaler лучше”, а “что именно нужно масштабировать”: количество pod’ов, размер pod’а или ноды кластера. 

Три уровня autoscaling в Kubernetes

После TL;DR важно зафиксировать базовую идею: в Kubernetes масштабируется не абстрактная “нагрузка”, а конкретные объекты. Инструмент может работать правильно, но не решать проблему, если выбран не тот уровень масштабирования.

Например, API-сервис получает рост трафика. HPA увеличивает Deployment с 5 до 20 реплик, но часть новых pod’ов остаётся в Pending: на текущих нодах нет свободных CPU и памяти с учётом requests. В этом случае HPA уже сделал свою работу — запросил больше реплик. Дальше проблема переходит на уровень кластера: нужны Cluster Autoscaler или Karpenter, которые добавят вычислительную ёмкость.

Перед выбором инструмента полезно разделить зоны ответственности:

Уровень Что меняет Инструменты Типичный сигнал 
Реплики приложения Число pod’ов HPA, KEDA CPU, память, внешние метрики, очередь, события 
Размер pod’а requests и limitsVPA Историческое потребление CPU/RAM 
Ноды кластера Доступную вычислительную ёмкость Cluster Autoscaler, Karpenter Pending pod’ы, недоиспользованные ноды 

Эта таблица помогает избежать частой ошибки: пытаться одним autoscaler’ом закрыть все уровни. HPA и KEDA отвечают за количество реплик, но не гарантируют, что для них найдётся место. VPA помогает подобрать размер pod’а, но не создаёт больше реплик при резком росте трафика. Cluster Autoscaler и Karpenter добавляют или убирают ноды, но не решают, сколько экземпляров приложения нужно запустить.

Поэтому HPA, VPA, KEDA, Cluster Autoscaler и Karpenter не стоит воспринимать как прямые замены друг другу. Они отвечают на разные вопросы: сколько pod’ов нужно, какого они размера и хватает ли в кластере места для их запуска.

Autoscaling на уровне приложения: HPA, VPA и KEDA

После разделения уровней можно перейти к первому слою — приложению. Здесь обычно выбирают между HPA, VPA и KEDA, но они отвечают на разные вопросы. HPA и KEDA меняют число реплик, VPA помогает подобрать размер pod’а. Если это смешать, autoscaling начнёт реагировать не на ту проблему.

HPA: когда сигнал виден внутри pod’а

HPA масштабирует Deployment, ReplicaSet или StatefulSet по количеству pod’ов. Обычно его используют для web/API-сервисов, где нагрузка хорошо отражается в CPU, памяти или пользовательских метриках: например, запросах в секунду, latency или размере внутренней очереди.

Важная деталь: CPU utilization считается относительно requests. Если pod потребляет 500 millicores при request 1 CPU, для HPA это 50%. Если тот же pod потребляет 500 millicores при request 250 millicores, это уже 200%.

Поэтому неверные requests искажают решение HPA. Завышенные значения дают поздний scale-up и лишнюю зарезервированную capacity. Заниженные — агрессивный рост реплик, CPU throttling, нестабильные метрики и шумные алерты. HPA хорошо работает только тогда, когда базовый размер pod’а задан близко к реальности.

VPA: когда проблема в размере pod’а

VPA решает другую задачу: подбирает requests и limits. Он полезен, если сервис давно работает с устаревшими лимитами, постоянно недозаказывает память или наоборот резервирует слишком много CPU и RAM.

Но VPA не заменяет HPA при росте трафика. Если запросов стало в пять раз больше, одному правильно размеренному pod’у всё равно может быть мало. VPA помогает понять, какого размера должен быть pod, но не отвечает на вопрос, сколько реплик нужно приложению.

При совместной работе VPA и HPA по CPU или памяти нужна осторожность. VPA меняет requests, а HPA считает загрузку относительно этих значений. Если не задать правила, один инструмент может менять базу расчёта, а второй — реагировать на изменившуюся метрику.

KEDA: когда сигнал приходит извне

KEDA нужна там, где главный сигнал находится не внутри pod’а. Это может быть длина очереди RabbitMQ или SQS, Kafka lag, расписание, событие, облачная метрика или другой внешний источник.

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

KEDA часто не конкурирует с HPA, а управляет HPA под капотом, добавляя источники сигналов, которых нет в обычной CPU-настройке. Для batch-сценариев есть KEDA ScaledJob: он запускает задачи по событиям, но это отдельный режим, а не универсальная замена Deployment.

Коротко выбор на уровне приложения можно описать так:

  • Сигнал внутри pod’а — HPA;
  • Неверный размер pod’а — VPA;
  • Сигнал вне pod’а — KEDA;
  • Batch-события — KEDA ScaledJob;
  • Pod’ам негде запускаться — нужен autoscaling уровня нод.

Если HPA или KEDA уже создали новые pod’ы, но они остались в Pending, проблема больше не на уровне приложения. Дальше нужно смотреть на ёмкость кластера: хватает ли нод, какие есть node groups или NodePool, и кто должен добавить capacity.

Autoscaling уровня нод: Cluster Autoscaler и Karpenter

Cluster Autoscaler и Karpenter работают не с количеством реплик приложения, а с вычислительной ёмкостью кластера. Их главный сигнал — pod’ы в Pending, которым не хватило места, или ноды, которые можно убрать после снижения нагрузки.
 

Cluster Autoscaler: предсказуемые node groups

Cluster Autoscaler, или CA, — классический autoscaler уровня нод. Он смотрит на pod’ы, которые не удалось запланировать, проверяет, можно ли добавить ноду в существующую node group, и увеличивает размер этой группы.

При снижении нагрузки CA ищет ноды, с которых pod’ы можно безопасно переселить, и уменьшает node group. Такой подход хорошо подходит для кластеров с заранее заданными группами: general-purpose, GPU, memory-optimized и другими.

Главное ограничение CA — он работает в рамках уже описанных node groups. Если группе разрешены только определённые типы инстансов, зоны или размеры, CA масштабирует именно этот набор. Это предсказуемо и удобно для контроля, но иногда менее гибко: кластер может ждать конкретный тип ноды, хотя в облаке доступна более дешёвая или быстрее создаваемая альтернатива.

Karpenter: гибкий подбор capacity

Karpenter решает ту же задачу динамичнее. Он подбирает ноду под фактические требования pod’ов: CPU, память, архитектуру, зону, тип инстанса, ограничения по стоимости и доступности.

В Karpenter важное понятие — NodePool. Это набор правил, по которым можно создавать ноды для определённых нагрузок. Например, можно ограничить типы инстансов, зоны, spot/on-demand-стратегию, лимиты по ресурсам и требования к размещению.

Ещё один важный механизм — consolidation, то есть уплотнение и удаление недоиспользованных нод. Karpenter может понять, что pod’ы можно разместить дешевле или плотнее, создать новую ноду, переселить нагрузку и убрать лишнюю ёмкость.

Но такая гибкость требует ограничений. Уплотнение связано с добровольными эвиктами, поэтому его нужно согласовывать с PodDisruptionBudget, disruption budgets, graceful shutdown и требованиями доступности. Иначе экономия на нодах может превратиться в нестабильность приложений.

Как выбрать между CA и Karpenter

Практическое различие можно свести к трём правилам:

  • Cluster Autoscaler проще для кластеров с понятными node groups и умеренной динамикой.
  • Karpenter полезнее, когда важны быстрый подбор capacity, разные типы инстансов, spot/on-demand, дорогие node pool и активное уменьшение простоя.
  • Оба инструмента не заменяют HPA, VPA и KEDA: они размещают pod’ы, но не решают, сколько pod’ов должно быть у приложения.

Поэтому autoscaling уровня нод нужно рассматривать как продолжение application autoscaling. HPA или KEDA могут попросить больше pod’ов, VPA может уточнить их размер, но только Cluster Autoscaler или Karpenter обеспечивают место, где эти pod’ы смогут запуститься.

После этого можно переходить к практическому выбору по сигналу нагрузки: CPU, память, очередь, batch-задачи, нестабильный трафик или дорогие node pool требуют разных комбинаций инструментов.

Decision matrix: какой autoscaler выбрать по сигналу нагрузки

Когда уровни autoscaling разделены, выбирать инструмент удобнее по сигналу. Нужно понять, где возникло узкое место: внутри приложения, во внешнем потоке событий, в размере pod’а или на уровне нод.

Матрица выбора выглядит так:

Сигнал или сценарий Основной инструмент Что проверить дополнительно 
CPU-нагрузка web/API HPA requests, minReplicas, maxReplicas, задержку старта pod’ов
RAM-нагрузка HPA по memory или VPA Memory requests/limits, утечки памяти, cache-поведение
Очередь, Kafka lag, consumer backlog KEDA maxReplicaCount, cooldown, скорость обработки одной реплики
Событийная нагрузка с простоями KEDA scale-to-zero Холодный старт, прогрев приложения, допустимую latency
Batch-задачи KEDA ScaledJob или Kubernetes Jobs Параллелизм, квоты, backoff, влияние на сервисы с SLO
Pod’ы в PendingCluster Autoscaler или Karpenter requests, quotas, affinity, лимиты node group или NodePool
Дорогие node pool Karpenter Лимиты NodePool, spot/on-demand, consolidation, PDB
Постоянно неверный размер pod’ов VPA min/max allowed, режим VPA, совместимость с HPA

Эта матрица помогает назначить владельца решения. HPA и KEDA отвечают за число реплик. VPA помогает подобрать размер pod’а. Cluster Autoscaler и Karpenter отвечают за ёмкость кластера.

Для web/API-сервиса с CPU-нагрузкой обычно достаточно HPA, но только если requests заданы близко к реальному потреблению. Если requests завышены, HPA может поздно реагировать на рост. Если занижены — можно получить агрессивный scale-up, throttling и шумные алерты.

Для consumer’ов важнее смотреть не только на CPU, а на очередь или lag. Если очередь растёт, а CPU ещё низкий, HPA по CPU запоздает. В этом случае KEDA лучше отражает реальную проблему: сколько сообщений накопилось и как быстро их нужно разобрать.

Для batch-задач важно ограничить параллелизм. Иначе autoscaling может создать много краткоживущих pod’ов, быстро поднять дорогие ноды и вытеснить сервисы с SLO. Здесь нужны квоты, лимиты Jobs, backoff-политика и понятные границы влияния на кластер.

Если pod’ы уже созданы, но остаются в Pending, менять пороги HPA или KEDA бесполезно. Проблема перешла на уровень нод: нужно смотреть Cluster Autoscaler или Karpenter, лимиты node group или NodePool, доступные зоны, типы инстансов, quotas и ограничения размещения.

На практике выбор почти всегда комбинированный. API может использовать HPA по CPU, VPA в рекомендательном режиме для уточнения requests и Karpenter для контроля дорогих пулов нод. Consumer может масштабироваться KEDA по lag, но при росте реплик ему всё равно нужен autoscaler уровня нод.

Autoscaling и оптимизация расходов: где экономия, а где скрытая переплата

Autoscaling может снизить расходы, но не гарантирует экономию автоматически. Он убирает лишнюю ёмкость только тогда, когда правильно заданы границы: requests, minReplicas, maxReplicas, лимиты node pool, политика scale-down и допустимое время прогрева.

Проблема в том, что один и тот же параметр влияет сразу на две стороны: стоимость и надёжность. Если держать слишком много реплик и слишком крупные ноды, инфраструктура будет дорогой. Если слишком агрессивно всё уменьшать, можно получить холодный старт, рост p95/p99 latency и pod’ы в Pending во время пика.

Простой пример: API работает в трёх зонах. Если minReplicas=6, сервис держит тёплый резерв и быстрее переживает утренний пик. Если снизить минимум до 2, счёт уменьшится, но при старте нагрузки pod’ам и нодам может потребоваться несколько минут на запуск. Для внутреннего сервиса это допустимо, а для критичного API — уже риск нарушения SLA.

Основные настройки лучше смотреть как компромиссы:

Настройка Что даётГде риск 
minReplicasДержит минимальный запас или снижает расходы в простоеСлишком низкое значение даёт холодный старт и рост latency 
maxReplicasОграничивает расходы и защищает downstream-системыСлишком низкий потолок может не выдержать пик 
requestsВлияют на планирование, HPA и плотность размещенияЗавышение даёт переплату, занижение — throttling и OOM 
cooldown / stabilization windowСглаживает уменьшение реплик после пикаСлишком быстрый scale-down вызывает flapping 
Лимиты node pool / NodePoolНе дают разрастись дорогим нодамПри жёстких лимитах pod’ы могут остаться в Pending
ConsolidationУбирает недоиспользованные нодыАгрессивные эвикты могут ударить по доступности 

requests особенно важны. Они влияют сразу на три вещи: как HPA считает загрузку, как scheduler размещает pod’ы и насколько плотно нагрузка укладывается на ноды. Завышенные requests покупают неиспользуемую ёмкость. Заниженные выглядят экономно только до тех пор, пока не начинаются CPU throttling, OOM, рестарты и странные решения autoscaler’а.

minReplicas и maxReplicas задают границы поведения. Минимум определяет, сколько тёплой capacity команда готова держать заранее. Максимум ограничивает расходы и защищает зависимости: базу данных, брокер, внешние API. Но если максимум слишком жёсткий, autoscaling сам станет причиной нарушения SLA во время пика.

Время прогрева тоже нужно считать частью масштабирования. Autoscaler не создаёт полезную ёмкость мгновенно: сначала появляется сигнал, затем создаётся pod, при необходимости поднимается нода, скачивается образ, проходят readiness-пробы, открываются соединения и прогреваются кэши. Если весь путь занимает 3–5 минут, minReplicas=0 подходит не всем.

Поэтому экономия в Kubernetes — это не “свести всё к нулю ночью”. Правильная цель — управлять запасом: держать его там, где он нужен для SLA, и убирать там, где он просто маскирует неверные requests, слишком высокие минимумы или дорогие ноды без реальной нагрузки.

Следующий шаг — применить эту логику к типовым сценариям: API, очередям, batch-задачам, нестабильному трафику и дорогим node pool.

Настройка под типовые сценарии

API-сервисы

Для критичного API не стоит механически снижать minReplicas. В расчёт нужно включать не только CPU, но и весь путь старта: загрузку образа, запуск pod’а, readiness-пробы, подключение к зависимостям и прогрев кэша.

Если задержка растёт раньше CPU, одного HPA по CPU может быть мало. Тогда стоит добавить метрику запросов в секунду, latency или другую прикладную метрику, которая лучше показывает реальную нагрузку на сервис.

Очереди Kafka, RabbitMQ и SQS

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

maxReplicaCount в KEDA не стоит ставить “с запасом на максимум”. Он должен учитывать ограничения downstream-систем: базы данных, внешнего API, брокера или сервиса, куда consumer отправляет результат. Слишком быстрый рост consumer’ов может не ускорить обработку, а перегрузить зависимость.

Batch-задачи и событийная нагрузка

Для batch-сценариев нужно заранее ограничить параллелизм, число активных задач и квоты namespace. Иначе фоновая обработка может вытеснить API-сервисы или создать дорогую краткоживущую ёмкость.

Здесь помогают лимиты на Jobs, аккуратные backoffLimit и TTL, отдельные node pool или NodePool, а также приоритеты через PriorityClass. Главная цель — не дать пакетной нагрузке занять весь кластер только потому, что появилось много событий.

Нестабильный трафик

Для коротких пиков обычно нужен быстрый рост и более осторожное уменьшение. Scale-up должен реагировать достаточно быстро, а scale-down лучше сглаживать через stabilization window и паузу перед уменьшением реплик.

Это снижает flapping — ситуацию, когда pod’ы создаются и удаляются быстрее, чем успевают приносить пользу. В нестабильном трафике слишком агрессивная экономия часто ухудшает p95/p99 сильнее, чем экономит деньги.

Дорогие node pool

Для GPU, memory-optimized или крупных on-demand-инстансов важно задавать лимиты NodePool или node group. Иначе обычная нагрузка может случайно попасть на дорогую ёмкость, а autoscaling быстро разгонит счёт.

Здесь нужны taints/tolerations, affinity, лимиты NodePool, отдельные правила для spot/on-demand и осторожная consolidation. Karpenter удобен для гибкого выбора инстансов, но его нужно ограничивать PDB, disruption budgets и требованиями доступности.

Общий контроль остаётся одинаковым для всех сценариев: если новые pod’ы переходят в Pending, настройка реплик уже упёрлась в ёмкость кластера. В этот момент нужно проверять Cluster Autoscaler или Karpenter, лимиты node pool, квоты и доступные типы инстансов, а не продолжать менять пороги HPA или KEDA.

Заключение

Практический выбор autoscaling в Kubernetes начинается не с инструмента, а с сигнала и уровня управления. Если растёт нагрузка внутри приложения, нужны HPA или корректировка requests через VPA. Если растёт очередь или внешний поток событий, логичнее KEDA. Если pod’ы уже созданы, но не размещаются, проблема перешла на уровень нод — здесь работают Cluster Autoscaler или Karpenter.

Главный риск в том, что autoscaler может быть включён, но управлять не той сущностью. Рабочий порядок такой: определить сигнал, понять объект масштабирования, задать границы роста и сжатия, проверить задержки запуска, SLO и стоимость. Только после этого autoscaling становится не источником случайных расходов, а управляемым механизмом capacity planning.

FAQ

Чем HPA отличается от KEDA?

HPA масштабирует количество реплик по CPU, памяти или метрикам, доступным через Kubernetes metrics API. KEDA добавляет внешние сигналы: очереди, Kafka lag, события, расписание, cloud-метрики. На практике KEDA часто управляет HPA под капотом, но даёт ему источники нагрузки, которых нет в обычной CPU-настройке.

Можно ли использовать HPA и VPA вместе?

Можно, но осторожно. VPA меняет requests, а HPA по CPU и памяти считает загрузку относительно этих requests. Если оба инструмента без правил влияют на одну и ту же нагрузку, реакция HPA может стать нестабильной. Часто VPA используют в рекомендательном режиме, а HPA оставляют для масштабирования реплик.

Почему pod’ы остаются в Pending, хотя HPA работает?

Потому что HPA увеличивает число pod’ов, но не добавляет ноды. Если scheduler не находит свободные CPU или память с учётом requests, новые pod’ы остаются в Pending. В этом случае нужно проверять Cluster Autoscaler или Karpenter, лимиты node group или NodePool, quotas, affinity и доступные типы инстансов.

Когда выбирать Karpenter вместо Cluster Autoscaler?

Karpenter полезен, когда нужна более гибкая работа с capacity: разные типы инстансов, дорогие node pool, spot/on-demand, лимиты NodePool, consolidation и быстрый подбор нод под требования pod’ов. Cluster Autoscaler проще и предсказуемее для классических node groups с умеренной динамикой.

Безопасен ли scale-to-zero?

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

Что сильнее всего влияет на стоимость autoscaling?

Сильнее всего влияют requests, minReplicas, maxReplicas, лимиты node pool или NodePool, время прогрева, политика scale-down и consolidation. Сам факт включения autoscaler не гарантирует экономию: если границы заданы неверно, масштабирование может даже увеличить счёт.

Список источников

1. Kubernetes Documentation — Horizontal Pod Autoscaling


2. Kubernetes Autoscaler / Cluster Autoscaler FAQ


3. KEDA Documentation — ScaledObject specification


4. Karpenter Documentation — NodePools

Подпишитесь на нашу рассылку и получайте статьи и новости

    Ознакомьтесь с другими нашими материалами

    • Snapshots vs Backups vs Replication что реально защищает данные в облаке

      Snapshots, backups и replication защищают от разных рисков. Snapshot помогает быстро откатиться к точке во времени, backup нужен для возврата к прошлому состоянию, а replication...

    • Disaster Recovery в облаке RTO,RPO, pilot light, warm standby и DR-план для SMB

      Disaster Recovery в облаке для SMB начинается не с выбора «самой надёжной» архитектуры, а с двух бизнес-вопросов: сколько компания может позволить себе простоя и сколько данных...

    • DDoS-защита в облаке: L3/L4/L7, Anycast, rate limiting и план реагирования

      Когда сервис начинает отдавать 5xx, растёт latency, а CDN показывает аномальный трафик, первая ошибка — включать (или наоборот, выключать) всё подряд. Один и тот же симптом “сервис...