La gestión adecuada de aplicaciones en entornos productivos de Kubernetes requiere el conocimiento de componentes especializados como DaemonSets y StatefulSets. Estos objetos ofrecen soluciones específicas para distintos casos de uso, permitiendo implementar arquitecturas robustas y escalables. Dominando estos conceptos, podrás optimizar el despliegue de aplicaciones que requieran alta disponibilidad o persistencia de datos.
¿Qué son los DaemonSets y StatefulSets en Kubernetes?
Los DaemonSets y StatefulSets son objetos de Kubernetes diseñados para casos de uso específicos en entornos productivos. Cada uno tiene características particulares que los hacen adecuados para diferentes situaciones, especialmente cuando se requiere un comportamiento predecible en cuanto a la ejecución y persistencia de los pods.
Un DaemonSet garantiza que todos los nodos (o un conjunto específico de nodos) ejecuten una copia de un pod. Cuando se agregan nodos al clúster, se les añade automáticamente un pod del DaemonSet. La característica principal es que cada réplica configurada en un DaemonSet se ejecuta en un nodo a la vez. Esto significa que si configuramos 3 o 4 réplicas, necesitaríamos la misma cantidad de nodos.
Por otro lado, un StatefulSet está diseñado para aplicaciones que requieren persistencia e identificadores estables. A diferencia de los Deployments regulares, los StatefulSets mantienen una identidad persistente para cada pod, lo que resulta útil para aplicaciones con estado como bases de datos.
¿Cómo crear un DaemonSet en Kubernetes?
Para crear un DaemonSet, necesitamos definir su especificación en un archivo YAML. La estructura es similar a otros objetos de Kubernetes, con algunas particularidades:
En este ejemplo, definimos un DaemonSet con un pod que ejecuta Nginx. Es importante definir los recursos que nuestros pods utilizarán, como se muestra en la sección de resources. Esto establece que el pod tendrá asignados inicialmente 64Mi de memoria y 250m de CPU, con límites de 128Mi y 500m respectivamente.
Para crear este DaemonSet, ejecutamos:
kubectl apply -f daemonset.yaml
Y podemos verificar su creación con:
kubectl get ds
¿Cómo implementar StatefulSets con almacenamiento persistente?
Los StatefulSets generalmente se utilizan junto con volúmenes persistentes (PV) y reclamos de volúmenes persistentes (PVC) para mantener el estado de las aplicaciones. Antes de crear un StatefulSet, necesitamos configurar estos recursos de almacenamiento:
Una característica importante de los StatefulSets es que requieren un servicio "headless" (ClusterIP: None). Este servicio permite que cada pod del StatefulSet tenga una dirección DNS estable, lo que facilita la comunicación entre pods.
Al crear este StatefulSet, notarás que los pods se crean con nombres predecibles:
nginx-sts-0nginx-sts-1
¿Cuáles son los casos de uso y limitaciones de DaemonSets y StatefulSets?
Casos de uso para DaemonSets:
Agentes de monitoreo: como Prometheus, que necesitan ejecutarse en cada nodo
Recolección de logs: herramientas como Logstash o Fluentd
Proxies de red: como kube-proxy
Daemons de almacenamiento: que necesitan ejecutarse en cada nodo
Casos de uso para StatefulSets:
Bases de datos: MySQL, PostgreSQL (para desarrollo, no siempre recomendado para producción)
Sistemas distribuidos: Kafka, Elasticsearch
Aplicaciones que requieren identidades persistentes
Limitaciones:
Tanto los DaemonSets como los StatefulSets tienen restricciones importantes a considerar:
No permiten rollbacks inmediatos como los Deployments
Solo se pueden escalar o reducir de un pod a la vez
Esto puede afectar la experiencia del usuario dependiendo del dominio de aplicación
Es importante entender estas limitaciones para determinar si estos objetos son adecuados para tu caso de uso específico o si sería mejor utilizar otras alternativas como los Deployments.
El poder de Kubernetes radica en su capacidad para desacoplar componentes y crear pods efímeros cuando sea necesario, proporcionando soluciones específicas para diferentes escenarios de despliegue a través de sus diversos objetos y recursos.
¿Has utilizado DaemonSets o StatefulSets en tus proyectos? ¿Qué otros casos de uso crees que serían adecuados para estos objetos? Comparte tu experiencia en los comentarios.
¡Qué tal, Luis Rogelio! No, no se contienen. De hecho, son como dos herramientas distintas en la misma caja: ambos son controladores, pero tienen naturalezas opuestas.
Un Deployment es el encargado de escalar; su trabajo es garantizar que un número determinado de réplicas de tus pods esté vivo, generalmente para servir tráfico según la demanda. Es como tener varios cajeros en un banco: si hay mucha gente, abres más ventanillas.
Un DaemonSet es un "siempre presente": asegura que una copia de un pod específico corra en todos los nodos (o en los que tú elijas) del clúster. Es como el sistema de seguridad del banco: no importa cuánta gente haya, siempre tiene que haber un sensor en cada esquina.
Son primos, no padre e hijo. ¿Ves por qué intentar meter uno dentro del otro sería como intentar usar un martillo para clavar un tornillo?
Muy buena explicación de como aplicar y utilizar los deamonsets y statefulsets, así como en que casos utilizarlos y sus limitaciones. Sin embargo, siento que le falto más detalle a la explicación de qué son estos objetos :(
En cpu: "250m" se refiere a 250 milicores, que kubernetes divide cada core del cpu en "1000 milicores" para su administración granular de los recursos.
En DaemonSet, se crean recursos dependiendo del número de nodos que tengas en ejecución, la idea del DaemonSet es tener una réplica en cada nodo.
Creo la explicación de Statefulset no fue del todo clara pero me ayude de Gemini y lo entendí con lo siguiente.
Un StatefulSet es el controlador diseñado para bases de datos ("Mascotas"). A diferencia de los Deployments ("Ganado"), garantiza que cada Pod tenga una identidad única, una dirección de red fija y un disco duro físico exclusivo.
A continuación, los 3 pilares que lo hacen funcionar, ilustrados con código y comandos reales.
1. Identidad Fija (Nombres Secuenciales)
Los Pods no tienen sufijos aleatorios. Se nombran en un orden estricto (0, 1, 2...) y si uno muere, renace exactamente con el mismo nombre para no romper la base de datos.
Ejemplo en la terminal (kubectl get pods):
Bash
# En un Deployment verías nombres como: nginx-deployment-7f89b4-x2z
# En un StatefulSet, verás esto:$ kubectl get pods -l app=nginx-app
NAMEREADYSTATUSRESTARTSAGEnginx-sts-01/1Running0 5m
nginx-sts-11/1Running0 4m
nginx-sts-21/1Running0 2m
2. Red Directa (Headless Service)
Para que la aplicación sepa exactamente a qué base de datos conectarse (ej. enviar escrituras solo al nodo Maestro), se usa un Servicio "sin cabeza" que no balancea el tráfico, sino que le da un nombre de dominio DNS a cada Pod.
Ejemplo de YAML (Headless Service):
YAML
apiVersion: v1
kind:Servicemetadata:name: nginx-service
spec:clusterIP:None # <--Esto lo convierte en Headlessselector:app: nginx-app
ports:- port:80
Ejemplo en la terminal (Resolución DNS): Si otro contenedor dentro del clúster intenta comunicarse con la base de datos, no llama a una IP aleatoria, usa el nombre exacto del Pod seguido del nombre del servicio:
Bash
# Haciendo ping directamente al Pod0 desde otro lugar del clúster:$ ping nginx-sts-0.nginx-service.default.svc.cluster.localPING nginx-sts-0.nginx-service...(10.42.0.15):56 data bytes
64 bytes from10.42.0.15: icmp_seq=0 ttl=64 time=0.042 ms
3. Discos Independientes (volumeClaimTemplates)
En un StatefulSet NUNCA usas la propiedad volumes estándar dentro del Pod, porque eso forzaría a todos a usar el mismo disco. Se usa volumeClaimTemplates como una fábrica para crear un disco nuevo por cada Pod.
Ejemplo de YAML (El StatefulSet):
YAML
apiVersion: apps/v1
kind:StatefulSetmetadata:name: nginx-sts
spec:serviceName: nginx-service
replicas:2template: # ... metadata y containers ...volumeMounts:- name: nginx-storage
mountPath:/usr/share/nginx/html
# La fábrica de discos:volumeClaimTemplates:- metadata:name: nginx-storage
spec:accessModes:["ReadWriteOnce"]resources:requests:storage: 1Gi
Ejemplo en la terminal (kubectl get pvc): Cuando aplicas el YAML anterior, Kubernetes genera automáticamente un PVC distinto para cada Pod. El nombre del PVC siempre es: <nombre-del-template>-<nombre-del-pod>.
¿Quién crea realmente los discos pvc-8f9a2b53... que vimos arriba? El StorageClass. Es el puente que habla con AWS, Azure o tu entorno local para crear el disco físico.
Ejemplo en la terminal (kubectl get sc): Para saber quién está fabricando tus discos, puedes listar las clases de almacenamiento. La que tiene (default) es la que el StatefulSet usa si no le especificas otra.