CKA · Módulo 5 K8s v1.34 Workloads & Scheduling 15%

Scheduling: dónde corren los pods

El scheduler decide en qué nodo va cada pod. Este módulo son las herramientas para influir en esa decisión: forzar un nodo, atraer, repeler, reservar recursos y distribuir cargas. Acá el multi-node de tu cluster por fin importa.

Duración60 min
DominioWorkloads & Scheduling
Cierrael dominio 15%
Requieremulti-node
Por defecto el scheduler (lo viste en el Módulo 1) reparte los pods solo, buscando nodos con recursos. Pero a veces querés control: "este pod SOLO en nodos con SSD", "no pongas estos dos juntos", "reservá al menos tanto CPU". Este módulo son los mecanismos para eso: nodeSelector y affinity (atraer), taints y tolerations (repeler), requests/limits (recursos), y topology spread (distribuir). Todos modifican la decisión del scheduler.
5.1
nodeSelector y Node Affinity
Atraer pods a ciertos nodos por labels.
5.2
Taints y Tolerations
Repeler pods de ciertos nodos, salvo los que toleran.
5.3
Resources: requests y limits
Reservar y limitar CPU/memoria. Afecta el scheduling.
5.4
Pod Affinity y Topology Spread
Juntar/separar pods entre sí, distribuir uniforme.
5.1
Atraer · 15 min

nodeSelector y Node Affinity

"Quiero que este pod corra en nodos con tal característica."
Práctica · Etiquetar y atraer

Primero: etiquetar un nodo

# Poner un label a un nodo
k label node w1 disktype=ssd

# Ver labels de los nodos
k get nodes --show-labels
k get nodes -l disktype=ssd

nodeSelector — la forma simple

spec:
  nodeSelector:
    disktype: ssd
  containers:
  - name: app
    image: nginx

El pod SOLO irá a nodos con el label disktype=ssd. Si ninguno lo tiene, queda Pending.

Node Affinity — la forma flexible

spec:
  affinity:
    nodeAffinity:
      requiredDuringSchedulingIgnoredDuringExecution:
        nodeSelectorTerms:
        - matchExpressions:
          - key: disktype
            operator: In
            values: ["ssd", "nvme"]
El nombre larguísimo requiredDuringSchedulingIgnoredDuringExecution se lee: "requerido AL schedular, ignorado si cambia DESPUÉS". O sea: decide al colocar el pod, pero si el label del nodo cambia luego, el pod ya colocado no se mueve.
Teoría · nodeSelector vs affinity

La diferencia

nodeSelectornode Affinity
Simple: label = valorExpresiones (In, NotIn, Exists...)
Solo AND exactoOR, rangos, negación
Solo "requerido"requerido O preferido

required vs preferred

  • required: regla dura. Si no se cumple, el pod queda Pending.
  • preferred: regla blanda. El scheduler lo intenta, pero si no puede, lo coloca igual en otro lado.
Regla práctica: si te alcanza con "label = valor", usá nodeSelector (más corto, menos error). Si necesitás lógica (varios valores, preferencias, negación), usá nodeAffinity.
5.2
Repeler · 15 min

Taints y Tolerations

Lo inverso a affinity: el nodo rechaza pods, salvo los que "toleran" el taint.
Práctica · Manchar y tolerar

Poner un taint a un nodo

# Formato: key=value:efecto
k taint node w1 gpu=true:NoSchedule

# Quitar el taint (mismo comando + guion al final)
k taint node w1 gpu=true:NoSchedule-

Ahora ningún pod se schedulea en w1... salvo los que toleren ese taint.

Toleration en el pod

spec:
  tolerations:
  - key: "gpu"
    operator: "Equal"
    value: "true"
    effect: "NoSchedule"
  containers:
  - name: app
    image: nginx
Ya viste taints en acción: el control plane tiene un taint node-role.kubernetes.io/control-plane:NoSchedule que evita que corran pods normales ahí. En el cluster single-node de práctica lo quitaste con el - para poder correr pods.
Teoría · Los 3 efectos

Los efectos de un taint

EfectoQué hace
NoScheduleNo schedulea pods nuevos sin toleration
PreferNoScheduleEvita, pero no prohíbe
NoExecuteAdemás EXPULSA pods existentes sin toleration

Affinity vs Taints — la diferencia clave

Affinity es el pod diciendo "quiero ir a tal nodo" (atracción, desde el pod).

Taint es el nodo diciendo "no quiero pods, salvo excepciones" (repulsión, desde el nodo).

Se complementan: taint reserva un nodo, toleration da el permiso de entrar, y affinity puede además dirigir el pod ahí.

Un toleration NO garantiza que el pod vaya a ese nodo — solo le da permiso de ir. Para forzar que vaya, combinás toleration (permiso) + nodeAffinity/nodeSelector (dirección).
5.3
Recursos · 15 min

Requests y Limits

Reservar recursos afecta dónde cabe el pod. Limitarlos afecta qué puede consumir.
Práctica · Definir recursos

requests y limits en un pod

spec:
  containers:
  - name: app
    image: nginx
    resources:
      requests:        # lo que RESERVA
        cpu: "250m"
        memory: "128Mi"
      limits:          # el TECHO que puede usar
        cpu: "500m"
        memory: "256Mi"

Límites a nivel namespace

# LimitRange: defaults por pod en un namespace
# ResourceQuota: tope total del namespace
k get limitrange
k get resourcequota
Las unidades importan: CPU en m (millicores: 1000m = 1 core), memoria en Mi/Gi (binario) o M/G (decimal). El HPA del Módulo 4 usa el requests.cpu como base del %.
Teoría · Request vs Limit

La distinción crucial

RequestLimit
Lo que reservaEl techo máximo
El scheduler lo usa para decidir dónde cabeEl kubelet lo hace cumplir en runtime
Garantía mínimaCorte máximo

Cómo afecta el scheduling

El scheduler suma los requests de los pods ya en un nodo y ve si el pod nuevo "entra" en lo que queda. Si ningún nodo tiene requests libres suficientes, el pod queda Pending (aunque haya CPU real ociosa: se mira el request reservado, no el uso real).

Qué pasa al superar el limit

  • CPU: se throttlea (se frena, no se mata)
  • Memoria: se mata el container (OOMKilled)
"Pod Pending por recursos" es un clásico de troubleshooting: mirás los requests del pod vs lo disponible en los nodos con k describe node (sección Allocated resources).
5.4
Relación entre pods · 15 min

Pod Affinity y Topology Spread

Juntar o separar pods entre sí, y distribuirlos de forma pareja.
Práctica · Relaciones

Pod Anti-Affinity — separar réplicas

# "No pongas dos pods de esta app en el mismo nodo"
spec:
  affinity:
    podAntiAffinity:
      requiredDuringSchedulingIgnoredDuringExecution:
      - labelSelector:
          matchLabels:
            app: web
        topologyKey: kubernetes.io/hostname

Topology Spread — distribución pareja

spec:
  topologySpreadConstraints:
  - maxSkew: 1
    topologyKey: kubernetes.io/hostname
    whenUnsatisfiable: DoNotSchedule
    labelSelector:
      matchLabels:
        app: web

Reparte los pods de app=web lo más parejo posible entre nodos (diferencia máxima de 1).

Teoría · Los conceptos

Pod affinity vs node affinity

Node affinity (5.1): "quiero ir a nodos con tal LABEL".

Pod affinity/anti-affinity: "quiero (o NO quiero) estar cerca de OTROS PODS con tal label".

El topologyKey

Define qué es "estar cerca". kubernetes.io/hostname = mismo nodo. Otros labels de topología pueden ser zona, región (en la nube). Es la unidad de agrupación.

Casos de uso típicos

  • Anti-affinity: repartir réplicas en nodos distintos (alta disponibilidad)
  • Affinity: poner el cache cerca de la app que lo usa
  • Topology spread: distribución uniforme para no sobrecargar un nodo
Anti-affinity con topologyKey: hostname es el patrón clásico de HA: garantiza que si un nodo cae, no te llevás todas las réplicas juntas.
Cierre del módulo

Lo que te llevás del Módulo 5

Resumen · Comandos clave

Para tu agenda

# Labels de nodos
k label node NODE key=value
k get nodes --show-labels

# Taints
k taint node NODE key=val:NoSchedule
k taint node NODE key=val:NoSchedule-   # quitar

# Ver recursos de un nodo (para debug de Pending)
k describe node NODE   # sección Allocated resources

# Conceptos que van en el YAML del pod:
#  nodeSelector / affinity.nodeAffinity  (atraer a nodos)
#  tolerations                           (permiso ante taints)
#  resources.requests / limits           (reservar / limitar)
#  affinity.podAntiAffinity              (separar pods)
#  topologySpreadConstraints             (distribuir)
Teoría · Lo esencial

Las 4 ideas que no se negocian

  • nodeSelector/affinity = el pod elige nodo por label (atracción).
  • Taints/tolerations = el nodo repele; la toleration da permiso (repulsión).
  • requests deciden dónde cabe (scheduling); limits cortan el uso (runtime).
  • pod affinity = relación entre pods; topology spread = distribución pareja.
El hilo del módulo: todo esto son formas de influir en el scheduler. Por defecto reparte solo; estas herramientas te dan control cuando lo necesitás. Y varias explican "pods Pending" en troubleshooting.
Checkpoint Módulo 5: atracción (affinity), repulsión (taints), recursos (requests/limits), y relaciones entre pods dominados. Cierra Workloads & Scheduling (15%). Siguiente: Módulo 6 — Services & Networking.
Módulo 5 completado · Cierra Workloads & Scheduling (15%) · Siguiente: Services & Networking