Каждые 15 минут модуль анализирует состояние кластера и выполняет вытеснение подов, соответствующих условиям, описанным в активных стратегиях. Вытесненные поды вновь проходят процесс планирования с учетом текущего состояния кластера. Это позволяет перераспределить рабочие нагрузки в соответствие с выбранной стратегией.
Модуль основан на проекте descheduler.
Особенности работы модуля
- Модуль может учитывать класс приоритета пода (параметр spec.priorityClassThreshold), ограничивая работу только подами, у которых класс приоритета ниже заданного порога;
- Модуль не вытесняет под в следующих случаях:
- под находится в пространстве имен
d8-*
илиkube-system
; - под имеет priorityClassName
system-cluster-critical
илиsystem-node-critical
; - под связан с локальным хранилищем;
- под связан с DaemonSet;
- вытеснение пода нарушит Pod Disruption Budget (PDB);
- нет доступных узлов для запуска вытесненного пода.
- под находится в пространстве имен
- Поды с классом приоритета
Best effort
вытесняются раньше, чем поды с классамиBurstable
иGuaranteed
.
Для фильтрации подов и узлов модуль использует механизм labelSelector
Kubernetes:
podLabelSelector
— ограничивает поды по меткам;namespaceLabelSelector
— фильтрует поды по пространствам имен.nodeLabelSelector
— выбирает узлы по меткам.
Стратегии
HighNodeUtilization
Концентрирует нагрузку на меньшем числе узлов. Требует настройку планировщика и включение автоматического масштабирования.
Чтобы использовать HighNodeUtilization
, необходимо явно указать профиль планировщика high-node-utilization для каждого пода (этот профиль не может быть установлен как профиль по умолчанию).
Стратегия определяет недостаточно нагруженные узлы и вытесняет с них поды, чтобы распределить их компактнее, на меньшем числе узлов.
Недостаточно нагруженный узел — узел, использование ресурсов которого меньше всех пороговых значений, заданных в секции параметров strategies.highNodeUtilization.thresholds.
Стратегия включается параметром spec.strategies.highNodeUtilization.enabled.
В GKE нельзя настроить конфигурацию планировщика по умолчанию, но можно использовать стратегию optimize-utilization
или развернуть второй пользовательский планировщик.
Использование ресурсов узла учитывает extended-ресурсы и рассчитывается на основе запросов и лимитов подов (requests and limits), а не их фактического потребления. Такой подход обеспечивает согласованность с работой kube-scheduler, который использует аналогичный принцип при размещении подов на узлах. Это означает, что метрики использования ресурсов, отображаемые Kubelet (или командами вроде kubectl top
), могут отличаться от расчетных показателей, так как Kubelet и связанные инструменты отображают данные о реальном потреблении ресурсов.
LowNodeUtilization
Более равномерно нагружает узлы.
Стратегия выявляет недостаточно нагруженные узлы и вытесняет поды с других, избыточно нагруженных узлов. Стратегия предполагает, что пересоздание вытесненных подов произойдет на недостаточно нагруженных узлах (при обычном поведении планировщика).
Недостаточно нагруженный узел — узел, использование ресурсов которого меньше всех пороговых значений, заданных в секции параметров strategies.lowNodeUtilization.thresholds.
Избыточно нагруженный узел — узел, использование ресурсов которого больше хотя бы одного из пороговых значений, заданных в секции параметров strategies.lowNodeUtilization.targetThresholds.
Узлы с использованием ресурсов в диапазоне между thresholds
и targetThresholds
считаются оптимально используемыми. Поды на таких узлах вытесняться не будут.
Стратегия включается параметром spec.strategies.lowNodeUtilization.enabled.
Использование ресурсов узла учитывает extended-ресурсы и рассчитывается на основе запросов и лимитов подов (requests and limits), а не их фактического потребления. Такой подход обеспечивает согласованность с работой kube-scheduler, который использует аналогичный принцип при размещении подов на узлах. Это означает, что метрики использования ресурсов, отображаемые Kubelet (или командами вроде kubectl top
), могут отличаться от расчетных показателей, так как Kubelet и связанные инструменты отображают данные о реальном потреблении ресурсов.
RemoveDuplicates
Предотвращает запуск нескольких подов одного контроллера (ReplicaSet, ReplicationController, StatefulSet) или заданий (Job) на одном узле.
Стратегия следит за тем, чтобы на одном узле не находилось больше одного пода ReplicaSet, ReplicationController, StatefulSet или подов одного задания (Job). Если таких подов два или больше, модуль вытесняет лишние поды, чтобы они лучше распределились по кластеру.
Описанная ситуация может возникнуть, если некоторые узлы кластеры вышли из строя по каким-либо причинам, и поды с них были перемещены на другие узлы. Как только вышедшие из строя узлы снова станут доступны для приема нагрузки, эту стратегию можно будет использовать для выселения дублирующих подов с других узлов.
Стратегия включается параметром strategies.removeDuplicates.enabled.
RemovePodsViolatingInterPodAntiAffinity
Вытесняет поды, нарушающие правила inter-pod affinity и anti-affinity.
Стратегия гарантирует, что поды, нарушающие правила inter-pod affinity и anti-affinity, будут удалены с узлов.
Например, если на узле находится Под1, а также Под2 и Под3, имеющие правила anti-affinity, которые запрещают им работать на одном узле с подом Под1, то Под1 будет вытеснен с узла, чтобы Под2 и Под3 смогли работать. Такая ситуация может возникнуть, когда правила inter-pod affinity для Под2 и Под3 создаются когда поды уже запущены на узле.
Стратегия включается параметром strategies.removePodsViolatingInterPodAntiAffinity.enabled.
RemovePodsViolatingNodeAffinity
Вытесняет поды, нарушающие правила node affinity.
Стратегия гарантирует, что все поды, которые нарушают правила node affinity, в конечном счете будут удалены с узлов.
По сути, в зависимости от настроек параметра strategies.removePodsViolatingNodeAffinity.nodeAffinityType,
стратегия превращает правило requiredDuringSchedulingIgnoredDuringExecution
node affinity пода в правило requiredDuringSchedulingRequiredDuringExecution
, а правило preferredDuringSchedulingIgnoredDuringExecution
в правило preferredDuringSchedulingPreferredDuringExecution
.
Пример для nodeAffinityType: requiredDuringSchedulingIgnoredDuringExecution
. Есть под, который был назначен на узел, соответствующий правилу requiredDuringSchedulingIgnoredDuringExecution
node affinity на момент размещения. Если со временем этот узел перестанет удовлетворять правилу node affinity, и если появится другой доступный узел, соответствующий этому правилу, стратегия вытеснит под с узла, на который он был изначально назначен.
Пример для nodeAffinityType: preferredDuringSchedulingIgnoredDuringExecution
. Есть под, который был назначен на узел, т.к. на момент размещения отсутствовали другие узлы, удовлетворяющие правилу preferredDuringSchedulingIgnoredDuringExecution
node affinity. Если со временем в кластере появится доступный узел, соответствующий этому правилу, стратегия вытеснит под с узла, на который он был изначально назначен.
Стратегия включается параметром strategies.removePodsViolatingNodeAffinity.enabled.