Saltar al contenido principal

Servicios en Kubernetes

Los servicios en Kubernetes son un recurso fundamental para exponer aplicaciones, agrupar pods y gestionar el acceso a los recursos dentro y fuera del clúster. Dado que los pods son efímeros y sus IPs pueden cambiar constantemente, los servicios proporcionan una IP estable (y DNS) y balancean las peticiones entre los pods asociados.

Dentro vídeo: https://youtu.be/LIramFKvf3E Servicios en Kubernetes

Resumen: El Service actúa como una puerta de entrada estable, y los endpoints son la lista dinámica de pods a los que realmente se dirige el tráfico.

Comparativa rápida de tipos de servicios en Kubernetes

TipoAccesible desdeExposición externaUso típico
ClusterIPDentro del clústerNoComunicación interna entre pods
NodePortDentro y fuera (IP nodo)Sí (puerto del nodo)Acceso externo sencillo, pruebas
LoadBalancerDentro y fueraSí (IP pública)Exposición pública en cloud
ExternalNameDentro del clústerNo (redirige DNS)Redirigir a servicios externos por DNS

Diagrama visual de un servicio trabajando en conjunto con un deployment

Tipos de servicios en Kubernetes

ClusterIP (por defecto)

  • Es el tipo de servicio por defecto.
  • Crea una IP interna accesible solo dentro del clúster.
  • Balancea el tráfico entre los pods seleccionados mediante endpoints.
  • No es accesible desde fuera del clúster.

Ejemplo YAML:

apiVersion: v1
kind: Service
metadata:
name: mi-servicio-clusterip
spec:
selector:
app: mi-app
ports:
- port: 8080
targetPort: 80
type: ClusterIP

Ya hemos visto lo sencillo que es definir estos objetos y exponer nuestras aplicaciones. Pero, ¿cómo sabe el service a que pods debe redirigir el tráfico?

Esto es posible gracias a los selectores y los endpoints. Los selectores simplemente definen qué pods deben ser parte del servicio, basándose en etiquetas (labels) que se asignan a los pods. Recordad el apartado de conceptos básicos y la importancia de las etiquetas en Kubernetes.

Los endpoints por otra parte, son un objeto que mantiene una lista actualizada de las IPs de los pods que cumplen con el selector del servicio. Así, el Service puede redirigir el tráfico a los pods correctos, incluso si estos cambian de IP o se reemplazan. Recordemos que cada pods tiene una IP única asignada por el clúster, y los pods pueden ser efímeros, es decir, pueden aparecer y desaparecer con frecuencia.

Endpoints

Este objeto mantiene una lista actualizada de las IPs de los pods que cumplen con el selector del servicio. Así, el Service puede redirigir el tráfico a los pods correctos. Se crean automáticamente cuando se crea un Service y normalmente no es necesario interactuar directamente con ellos.

Aun así, por fines educativos, podemos ver cómo funcionan. Para ver los endpoints podemos utilizar los siguientes comandos:

kubectl get endpoints
kubectl get ep <nombre-servicio>

Esto nos mostrará un listado de los endpoints asociados a cada servicio, mostrando las IPs de los pods que están siendo balanceados por el servicio.

NodePort

  • Expone el servicio fuera del clúster a través de un puerto del nodo (rango 30000-32767).
  • Permite acceder al servicio usando la IP del nodo y el puerto asignado.
  • Internamente sigue balanceando entre los endpoints de los pods.
  • Útil para pruebas o acceso sencillo desde fuera del clúster.

Ejemplo YAML:

apiVersion: v1
kind: Service
metadata:
name: mi-servicio-nodeport
spec:
selector:
app: mi-app
ports:
- port: 8080
targetPort: 80
nodePort: 30080 # Opcional, si no se indica se asigna automáticamente
type: NodePort

LoadBalancer

  • Crea un balanceador de carga externo (en cloud providers compatibles) y asigna una IP pública.
  • El balanceador dirige el tráfico al NodePort, que a su vez lo distribuye entre los endpoints de los pods.
  • Ideal para exponer servicios a Internet de forma sencilla.

Ejemplo YAML:

apiVersion: v1
kind: Service
metadata:
name: mi-servicio-loadbalancer
spec:
selector:
app: mi-app
ports:
- port: 80
targetPort: 80
type: LoadBalancer

ExternalName

  • No crea un proxy ni IP propia.
  • Mapea el nombre del servicio a un DNS externo.
  • Útil para redirigir tráfico a servicios fuera del clúster (por ejemplo, una base de datos gestionada).

Ejemplo YAML:

apiVersion: v1
kind: Service
metadata:
name: mi-servicio-externalname
spec:
type: ExternalName
externalName: ejemplo.com

Nota: Ingress no es un tipo de Service, sino un recurso que permite gestionar el acceso externo (HTTP/HTTPS) a los servicios del clúster mediante reglas de enrutamiento. Suele trabajar junto a servicios de tipo ClusterIP o NodePort.

Casos de uso recomendados

  • ClusterIP: Comunicación interna entre microservicios.
  • NodePort: Pruebas locales, acceso sencillo desde fuera del clúster sin balanceador externo.
  • LoadBalancer: Exposición pública de aplicaciones en cloud.
  • ExternalName: Integración con servicios externos vía DNS.

Caso práctico exponiendo una aplicación web

Para concluir esta sección, vamos a exponer una aplicación web sencilla utilizando un Service de tipo NodePort.

apiVersion: v1
kind: Service
metadata:
name: web-service
spec:
selector:
app: web-app
ports:
- port: 80
targetPort: 8080
nodePort: 30080 # Puerto accesible desde fuera del clúster
type: NodePort

Ahora podremos acceder a la aplicación web desde cualquier nodo del clúster usando la IP del nodo y el puerto 30080. Podemos probarlo con:

curl http://<IP_DEL_NODO>:30080

Conclusiones e relación con Ingress

Los servicios son esenciales para exponer aplicaciones y repartir el tráfico entre los pods.

En un caso real, estos servicios se combinarían con un Ingress Controller para gestionar el acceso externo de forma más avanzada, permitiendo enrutar tráfico HTTP/HTTPS a diferentes servicios según dominios o rutas.

Esto lo veremos en la siguiente sección, Ingress Controller.


Volver al índice