Habilitar IPs públicas para los nodos de AKS

En la mayoría de los escenarios no es necesario que los nodos de tu clúster de AKS estén expuestos a través de una IP pública. Es por ello, y por temas de seguridad, que por defecto estos no tengan una asignada. Sin embargo hay algunos escenarios donde sí existe esta necesidad. Hoy quiero contarte cómo habilitar IPs públicas a los nodos de tu clúster en Azure.

Aplicación de prueba

Para probar esto voy a lanzar el siguiente despliegue, con tres réplicas de un Nginx que serán repartidas entre mis nodos, además de un servicio del tipo NodePort, eligiendo como puerto el 30007 de cada una de las máquinas virtuales que actúan como workers, para que no se elija de manera aleatoria:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx-deployment
  labels:
    app: nginx
spec:
  replicas: 3
  selector:
    matchLabels:
      app: nginx
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
        - name: nginx
          image: nginx
          ports:
            - containerPort: 80

---
apiVersion: v1
kind: Service
metadata:
  name: nginx-service
spec:
  type: NodePort
  selector:
    app: nginx
  ports:
    - port: 80
      targetPort: 80
      nodePort: 30007

Si despliegas este YAML y compruebas dónde están los pods ubicados verás que estos deberían de estar repartidos entre los nodos que tengas disponibles:

➜ kubectl get pods -o wide
NAME                                                              READY   STATUS    RESTARTS   AGE   IP           NODE                                  NOMINATED NODE   READINESS GATES
nginx-deployment-7bffc778db-7nh7h                                 1/1     Running   0          29s   10.244.8.6   aks-publicnodes-26643339-vmss000000   <none>           <none>
nginx-deployment-7bffc778db-9pwm6                                 1/1     Running   0          29s   10.244.7.5   aks-publicnodes-26643339-vmss000002   <none>           <none>
nginx-deployment-7bffc778db-9zg9m                                 1/1     Running   0          29s   10.244.6.8   aks-publicnodes-26643339-vmss000001   <none>           <none>

Por otro lado, si compruebas los servicios que están desplegados, verás que tienes uno llamado nginx-service del tipo NodePort y mapeado al puerto 30007, tal y como hemos definido:

➜ kubectl get svc
NAME            TYPE        CLUSTER-IP    EXTERNAL-IP   PORT(S)        AGE
kubernetes      ClusterIP   10.0.0.1      <none>        443/TCP        41h
nginx-service   NodePort    10.0.87.107   <none>        80:30007/TCP   19h

Habilitar IPs para los nodos de AKS

Ahora que ya tienes una aplicación con la que probar este escenario, lo siguiente que vamos a hacer es habilitar las IPs para los nodos worker de tu clúster. Lo primero que necesitas hacer es habilitar una característica, todavía en Preview, llamada Node Public IP con los siguientes comandos:

# Enable public IPs for the Nodes
#  Node Public IP (preview): https://docs.microsoft.com/es-es/azure/aks/use-multiple-node-pools#assign-a-public-ip-per-node-for-your-node-pools-preview

# Install and update the latest aks-preview extension
az extension add --name aks-preview
az extension update --name aks-preview
az extension list

# Register for the Node Public IP feature
az feature register --name NodePublicIPPreview --namespace Microsoft.ContainerService

# It may take several minutes for the feature to register
az feature list -o table --query "[?contains(name, 'Microsoft.ContainerService/NodePublicIPPreview')].{Name:name,State:properties.state}"

Debes asegurarte de que tienes la última versión de la extensión aks-preview para Azure CLI. Una vez hecho esto ya puedes registrar la característica con nombre NodePublicIPPreview. Este proceso puede durar varios minutos, por lo que es necesario que compruebes cada cierto tiempo que se ha registrado con el último comando que te comparto.

Una vez que tienes la característica habilitada para tu suscripción, el siguiente paso es crear un nuevo pool de nodos indicando el parámetro –enable-node-public-ip.

#It has to be a new nodepool to enable Public IP
az aks nodepool add -g $RESOURCE_GROUP --cluster-name $AKS_NAME -n publicnodes --enable-node-public-ip

Una vez que termine esta acción puedes ver cuáles son las IPs asignadas a cada uno de los nodos con el siguiente comando:

VMSS_RG="MC_AKS-Demos_returngis_northeurope"
VMSS_NAME="aks-publicnodes-26643339-vmss"

az vmss list-instance-public-ips -g $VMSS_RG -n $VMSS_NAME -o table

Como ves, es necesario recuperar el nombre del grupo de recursos generado para el Virtual Machine Scale Set y el nombre de este. El resultado será parecido al siguiente:

➜ az vmss list-instance-public-ips -g $VMSS_RG -n $VMSS_NAME -o table
IdleTimeoutInMinutes    IpAddress      Name    ProvisioningState    PublicIpAddressVersion    PublicIpAllocationMethod    ResourceGroup                       ResourceGuid
----------------------  -------------  ------  -------------------  ------------------------  --------------------------  ----------------------------------  ------------------------------------
30                      52.158.47.14   pub1    Succeeded            IPv4                      Static                      MC_AKS-Demos_returngis_northeurope  465b19eb-74a3-4c45-826a-6422ce267686
30                      52.158.32.76   pub1    Succeeded            IPv4                      Static                      MC_AKS-Demos_returngis_northeurope  453ccbfb-f2d9-46cb-8454-0ea73b127e83
30                      13.74.240.248  pub1    Succeeded            IPv4                      Static                      MC_AKS-Demos_returngis_northeurope  322711b7-81a9-468d-bbb6-4d70683be766

Por lo tanto, en mi ejemplo, a la hora de acceder a los nginx debería de ser a través de las siguientes direcciones, siempre indicando el puerto 30007:

#My IPS
http://52.158.47.14:30007
http://52.158.32.76:30007
http://13.74.240.248:30007

Sin embargo, te darás cuenta de que todavía no puedes acceder. Esto es debido a que necesitas crear una regla dentro del network security group asociado al Virtual Machine Scale Set, únicamente para el puerto de este ejemplo:

#enable NGS
NG_NAME="aks-agentpool-26643339-nsg"

az network nsg rule create -g $VMSS_RG --nsg-name $NG_NAME \
--name "Port30007" --priority 100 --destination-port-ranges 30007 --access Allow

Si ahora intentas acceder a través de las IPs públicas de cada uno de los nodos, por el puerto que está mapeado a los Nginx, podrás comprobar que puedes acceder sin problemas.

¡Saludos!