Introducción a Kubernetes
Warning: This information may be outdated. Please note the date of the post.
Te recomiendo si no conoces Docker ir esta entrada antes de continuar con este post.
En este post vamos a dar una breve introducción de Kubernetes:
- ¿Qué es Kubernetes?
- Características mas notables
- Arquitectura de Kubernetes
- Recursos de kubernetes
- Crear un despliegue con Kubernetes
- Escalar el POD activo
- Actualización nueva versión
¿Qué es Kubernetes?
Kubernetes es un orquestador de contenedores que actualmente es uno de los más populares del mercado. La orquestación de contenedores surge de la necesidad de automatizar el despliegue, la gestión, el escalado, la interconexión y disponibilidad de las aplicaciones.
Este software agrupa un conjunto de contenedores que mantienen una aplicación en unidades lógicas para hacer más fácil la gestión de los mismos.
Está escrito en Go y fue lanzado por Google en un principio, que se unió a Linux Foundation para crear la Cloud Native Computing Foundation que es quien lo gestiona.
Características mas notables
- Kubernetes trabaja sobre un clúster de equipos, que permite que si algún nodo deja de funcionar, el cluster sigue en pleno funcionamiento y las aplicaciones implementadas en él también sigan operativas. De forma que los contenedores que se estaban ejecutando en el nodo que ha fallado se distribuye a otro equipo para seguir operativos.
- Despliega aplicaciones de forma rápida y las escala al vuelo.
- Integra los cambios sin interrupciones.
- Permite limitar recursos.
- Es importante saber que es un proyecto centrado en la puesta en PRODUCCIÓN de contenedores. La gestión del mismo es el papel principal de un administrador de sistemas DEVOPS.
- El proyecto kubernetes está pensado para desplegarse en nube (pública, privada o híbrida).
- Es extensible y autoreparable.
Arquitectura de Kubernetes

-> Tenemos múltiples controllers o controladores:
- API Server: Es el servidor de la API de Kubernetes que valida y configura los objetos de la API incluyendo (pods,servicios,replicaset..) además proporciona la interfaz necesaria para interactuar.
- Scheduler: Con el mismo se puede programar un componente en el mismo software y forma parte del plano de control.
- Controller Manager: Es un demonio que integra los bucles de control centrales.
- etcd: Base de datos no relacional para alta disponibilidad.
-> Tenemos múltiples nodos que soportan la carga de trabajo (llamados workers):
- Infraestructura física
- Sistema operativo
- Contenedores
- kubelet (Recibe las ordenes del controller y se comunica con el containerruntime para ejecutarlas)
- kube-proxy (Conectividad de los contenedores a través de la red.)
Recursos de kubernetes

Conceptos:
¿Qué es un POD?
¿Qué es ReplicaSet?
¿Qué es Deployment?
Es la unidad de más alto nivel que podemos gestionar en Kubernetes. Se encarga de que todo esto funciones:
- Control de replicas
- Escalabilidad de pods
- Actualizaciones continuas
- Despliegues automáticos
- Rollback a versiones anteriores
¿Qué son los Servicios?
¿Qué es ingress?
Pues así a grandes rasgos resumimos:
Kubernetes es un software que actúa sobre un clúster de nodos donde se ponen en funcionamiento varios contenedores, hay varios controladores o nodos que se encargan de mandar trabajo a otros nodos (los workers) que son los que ejecutan el trabajo. Este trabajo consiste en gestionar aplicaciones de forma más organizada, rápida y eficaz.
Teniendo en cuenta este resumen pasamos a la práctica.
Crear un despliegue con Kubernetes
Nuestro objetivo en este punto es desplegar una aplicación en Kubernetes.
Necesitaremos:
- Una aplicación simple para usar. En mi caso vamos a utilizar una que tengo subida en mis repositorios de DockerHub: cgmarquez95/pruebanginx.
- Descargar kubectl y minikube
- Tener un sistema de virtualización (Docker,Virtualbox,KVM…)
Instalación de minikube
Aquí tenemos la documentación oficial de minikube:
Es una implementación más ligera de Kubernetes que crea un cluster de un sólo nodo y es ideal para pruebas.
En mi caso lo voy a instalar en Debian, usando la paquetería de Debian.
curl -LO https://storage.googleapis.com/minikube/releases/latest/minikube_latest_amd64.deb
sudo dpkg -i minikube_latest_amd64.deb
- La versión que tenemos actualmente de minikube es:
celiagm@debian:~/kubernetes$ minikube version
minikube version: v1.17.1
Instalación de kubectl
Sin más lo descargamos tal y como indica en la documentación oficial de kubernetes
sudo apt-get update && sudo apt-get install -y apt-transport-https gnupg2 curl
curl -s https://packages.cloud.google.com/apt/doc/apt-key.gpg | sudo apt-key add -
echo "deb https://apt.kubernetes.io/ kubernetes-xenial main" | sudo tee -a /etc/apt/sources.list.d/kubernetes.list
sudo apt-get update
sudo apt-get install -y kubectl
La versión de kubectl es:
celiagm@debian:~/kubernetes$ kubectl version
Client Version: version.Info{Major:"1", Minor:"22", GitVersion:"v1.22.1", GitCommit:"632ed300f2c34f6d6d15ca4cef3d3c7073412212", GitTreeState:"clean", BuildDate:"2021-08-19T15:45:37Z", GoVersion:"go1.16.7", Compiler:"gc", Platform:"linux/amd64"}
Server Version: version.Info{Major:"1", Minor:"20", GitVersion:"v1.20.2", GitCommit:"faecb196815e248d3ecfb03c680a4507229c2a56", GitTreeState:"clean", BuildDate:"2021-01-13T13:20:00Z", GoVersion:"go1.15.5", Compiler:"gc", Platform:"linux/amd64"}
WARNING: version difference between client (1.22) and server (1.20) exceeds the supported minor version skew of +/-1
Iniciar minkube y obtener la ip
Una vez instalados los dos paquetes vamos a proceder a iniciar minikube que levantará un nodo virtual
minikube start
Con kubectl comprobamos los nodos que tenemos disponibles
celiagm@debian:~/kubernetes$ kubectl get nodes
NAME STATUS ROLES AGE VERSION
minikube Ready control-plane,master 51s v1.20.2
celiagm@debian:~/kubernetes$ kubectl cluster-info
Kubernetes control plane is running at https://192.168.49.2:8443
KubeDNS is running at https://192.168.49.2:8443/api/v1/namespaces/kube-system/services/kube-dns:dns/proxy
To further debug and diagnose cluster problems, use 'kubectl cluster-info dump'.
En mi caso como hemos dicho anteriormente se ha creado un contenedor en Docker virtualizando este servicio.
celiagm@debian:~/kubernetes$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
628ab184370c gcr.io/k8s-minikube/kicbase:v0.0.17 "/usr/local/bin/entr…" 8 minutes ago Up 8 minutes 127.0.0.1:49156->22/tcp, 127.0.0.1:49155->2376/tcp, 127.0.0.1:49154->5000/tcp, 127.0.0.1:49153->8443/tcp minikube
Tambien podemos ver el estado de minikube
celiagm@debian:~/kubernetes$ minikube status
minikube
type: Control Plane
host: Running
kubelet: Running
apiserver: Running
kubeconfig: Configured
timeToStop: Nonexistent
Obtener la ip de minikube.
celiagm@debian:~/kubernetes$ minikube ip
192.168.39.34
Crear deployment
Primero creamos un despliegue con la aplicación que tenemos en docker, yo voy a usar la siguiente cgmarquez95/pruebanginx:v2
celiagm@debian:~/kubernetes$ kubectl create deployment web-nginx --image=cgmarquez95/pruebanginx:v2
deployment.apps/web-nginx created
Comprobamos que está disponible
celiagm@debian:~/kubernetes$ kubectl get deploy
NAME READY UP-TO-DATE AVAILABLE AGE
web-nginx 1/1 1 1 16s
Crear servicio
Ahora vamos a exponer el puerto 80 de nuestro nginx especificando un tipo NodePort para poder acceder desde el exterior y ver nuestra aplicación en el navegador.
En otras palabras:
El servicio va mapear un puerto aleatorio que va desde el 30000 al 40000 de nuestro host físico al puerto 80 de nuestro contenedor.
También tenemos el tipo ClusterIP que permite el acceso a la aplicación internamente.
La ejecución sería:
kubectl expose deployment web-nginx --port=80 --type=NodePort
Salida:
celiagm@debian:~/kubernetes$ kubectl expose deployment web-nginx --port=80 --type=NodePort
service/web-nginx exposed
celiagm@debian:~/github/onebit$ kubectl get services
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 10m
web-nginx NodePort 10.106.84.137 <none> 80:30680/TCP 9m34s
De manera que podemos acceder a la ip del nodo maestro (minikube) con el puerto asignado y debería de verse la página inicial de nuestro Nginx, que en este caso la modificamos en el post anterior con Docker.

Obtener todos los elementos activos
celiagm@debian:~$ kubectl get all
NAME READY STATUS RESTARTS AGE
pod/web-nginx-688484dfdc-n652r 1/1 Running 0 40h
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 40h
service/web-nginx NodePort 10.106.84.137 <none> 80:30680/TCP 40h
NAME READY UP-TO-DATE AVAILABLE AGE
deployment.apps/web-nginx 1/1 1 1 40h
NAME DESIRED CURRENT READY AGE
replicaset.apps/web-nginx-688484dfdc 1 1 1 40h
Escalar el POD activo
Una de las ventajas de Kubernetes es la potencia que tiene al escalar los diferentes elementos.
Si queremos un balanceo de carga solo tenemos que escalar.
celiagm@debian:~$ kubectl scale deploy web-nginx --replicas=3
deployment.apps/web-nginx scaled
celiagm@debian:~$ kubectl get pods
NAME READY STATUS RESTARTS AGE
web-nginx-688484dfdc-gkcgj 1/1 Running 0 38s
web-nginx-688484dfdc-n652r 1/1 Running 0 40h
web-nginx-688484dfdc-xtl9m 1/1 Running 0 38s
Si accedemos al navegador varias veces, aunque no sea aparentemente visible se produce un balanceo de carga entre los tres nuevos contenedores.
Actualización nueva versión
Kubernetes no crea nuevas imágenes como docker sino que las utiliza.
Vamos a docker a crear una nueva versión de nuestra imagen (v3) y vamos a tratar de actualizar el despliegue que tenemos en nuestro Kubernetes de forma continuada.
Me salto la parte en la que creo la nueva versión de la imagen en Docker porque este procedimiento ya está en el post de Introduccción a Docker
Ejecutamos el siguiente comando para actualizar la nueva versión de nuestra aplicación.
kubectl set image deployment web-nginx *=cgmarquez95/pruebanginx:v3
Salida:
celiagm@debian:~/nginx$ kubectl set image deployment web-nginx *=cgmarquez95/pruebanginx:v3
deployment.apps/web-nginx image updated
celiagm@debian:~/nginx$ kubectl get all
NAME READY STATUS RESTARTS AGE
pod/web-nginx-688484dfdc-gkcgj 0/1 Terminating 0 5h1m
pod/web-nginx-688484dfdc-n652r 1/1 Running 0 45h
pod/web-nginx-688484dfdc-xtl9m 0/1 Terminating 0 5h1m
pod/web-nginx-7bc68bfff6-fxvc4 1/1 Running 0 13s
pod/web-nginx-7bc68bfff6-pxgsw 1/1 Running 0 4s
pod/web-nginx-7bc68bfff6-rhbjw 0/1 ContainerCreating 0 2s
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 45h
service/web-nginx NodePort 10.106.84.137 <none> 80:30680/TCP 45h
NAME READY UP-TO-DATE AVAILABLE AGE
deployment.apps/web-nginx 3/3 3 3 45h
NAME DESIRED CURRENT READY AGE
replicaset.apps/web-nginx-688484dfdc 1 1 1 45h
replicaset.apps/web-nginx-7bc68bfff6 3 3 2 13s
Funcionamiento del despliegue de la nueva version (v3)
