Комментарии (2)
Ответ сгенерирован нейросетью и может содержать ошибки
Что такое Affinity в Kubernetes?
Affinity (Сходство / Сродство) в Kubernetes — это набор правил, которые позволяют администраторам влиять на планирование (scheduling) подов на узлы (nodes) с большей гибкостью, чем простые селекторы. Это механизм декларативного управления тем, где и с кем должен быть размещен под, учитывая не только метки узлов, но и текущее состояние уже запущенных на них рабочих нагрузок.
Концептуально, Affinity расширяет базовые возможности nodeSelector и taints/tolerations, предлагая более выразительный, "мягкий" (soft) и сложный (multi-rule) язык. Она разделяется на два основных типа:
- Node Affinity (Сродство с узлами): Определяет, на каких узлах может или должен быть запланирован под. Аналогично
nodeSelector, но мощнее. - Inter-pod Affinity/Anti-affinity (Сродство / анти-сродство между подами): Определяет, должен ли под быть запланирован на том же узле (или в той же зоне), что и другие поды, обладающие определенными метками, или, наоборот, избегать их.
Ключевые компоненты и операторы
Правила Affinity задаются в спецификации пода (или Deployment, StatefulSet и т.д.) в секции .spec.affinity. Основные строительные блоки:
-
requiredDuringSchedulingIgnoredDuringExecution(Обязательное правило): Жесткое требование, которое должно быть выполнено для успешного планирования пода. Если подходящего узла нет, под останется в состоянииPending. Аналог жесткого правила (hard).requiredDuringSchedulingIgnoredDuringExecution: nodeSelectorTerms: - matchExpressions: - key: disktype operator: In values: - ssd -
preferredDuringSchedulingIgnoredDuringExecution(Предпочтительное правило): "Мягкое" предпочтение. Планировщик попытается его выполнить, но если не сможет — все равно разместит под где-либо. Имеет вес (weight, от 1 до 100) для расстановки приоритетов между несколькими предпочтениями.preferredDuringSchedulingIgnoredDuringExecution: - weight: 80 preference: matchExpressions: - key: zone operator: In values: - zone-a -
operator(Оператор): Определяет логику сопоставления меток. Основные операторы:
* `In`, `NotIn` — значение метки в (или не в) указанном списке.
* `Exists`, `DoesNotExist` — метка существует (или не существует) на узле/поде.
* `Gt`, `Lt` — значение метки больше или меньше указанного числового значения.
Практические примеры использования
1. Node Affinity: Размещение на узлах с SSD
apiVersion: v1
kind: Pod
metadata:
name: cache-pod
spec:
affinity:
nodeAffinity:
requiredDuringSchedulingIgnoredDuringExecution:
nodeSelectorTerms:
- matchExpressions:
- key: hardware
operator: In
values:
- ssd
preferredDuringSchedulingIgnoredDuringExecution:
- weight: 70
preference:
matchExpressions:
- key: topology.kubernetes.io/zone
operator: In
values:
- eu-west-1a
containers:
- name: redis
image: redis:alpine
Что делает манифест: Под ОБЯЗАТЕЛЬНО будет размещен на узле с меткой hardware=ssd. При этом ПРЕДПОЧТИТЕЛЬНО, чтобы этот узел находился в зоне eu-west-1a.
2. Pod Anti-Affinity: Распределение инстансов приложения для высокой доступности
apiVersion: apps/v1
kind: Deployment
metadata:
name: web-app
spec:
replicas: 3
selector:
matchLabels:
app: web-store
template:
metadata:
labels:
app: web-store
spec:
affinity:
podAntiAffinity:
requiredDuringSchedulingIgnoredDuringExecution:
- labelSelector:
matchExpressions:
- key: app
operator: In
values:
- web-store
topologyKey: kubernetes.io/hostname
containers:
- name: nginx
image: nginx:latest
Что делает манифест: Каждый под этого Deployment будет избегать узлов, на которых уже работает под с меткой app=web-store. Ключ topologyKey: kubernetes.io/hostname указывает область привязки — отдельный узел. Это гарантирует, что все 3 реплики будут размещены на трех разных физических узлах, повышая отказоустойчивость.
Анти-сродство (Anti-affinity) и топологические домены
Особенно мощным является использование Pod Anti-affinity с topologyKey. Топологический ключ — это метка узла, которая определяет домен логического или физического уровня:
kubernetes.io/hostname— отдельный узел.topology.kubernetes.io/zone— зона доступности в облаке (AZ).topology.kubernetes.io/region— регион.
Это позволяет распределять поды не просто по разным узлам, но и по разным зонам или даже регионам, что критично для построения гео-избыточных и отказоустойчивых приложений.
Важные нюансы
- Производительность: Сложные правила межподового сродства/анти-сродства (особенно
requiredDuringScheduling) требуют от планировщика больше вычислений и могут замедлять планирование в больших кластерах. Их следует использовать обдуманно. - "IgnoredDuringExecution": Часть названия означает, что правила учитываются только при планировании. Если метки на узле или подах изменятся после запуска пода, он не будет перезапущен или перемещен автоматически. Для этого нужны другие механизмы (например,
descheduler). - Сочетание с Taints/Tolerations: Правила Affinity работают вместе с taints. Сначала под должен "перенести" taint узла (иметь matching toleration), и только затем применяются правила Affinity для выбора среди допустимых узлов.
Итог: Affinity — это незаменимый инструмент для реализации сложных требований к размещению workload'ов в Kubernetes. Он позволяет перейти от простого "этот под на этом типе узлов" к стратегиям "эти сервисы должны быть вместе для производительности", а "эти инстансы — максимально далеко друг от друга для надежности", что является краеугольным камнем эффективного управления производственным кластером.