Por que k8s wordpress e mysql example usam serviço headless para wordpress-mysql?

Sep 16 2020

O exemplo é descrito aqui - https://kubernetes.io/docs/tutorials/stateful-application/mysql-wordpress-persistent-volume/

O objeto de serviço para o wordpress-mysql é:

apiVersion: v1
kind: Service
metadata:
  name: wordpress-mysql
  labels:
    app: wordpress
spec:
  ports:
    - port: 3306
  selector:
    app: wordpress
    tier: mysql
  clusterIP: None

Os serviços sem cabeça são documentados aqui - https://kubernetes.io/docs/concepts/services-networking/service/#headless-servicesA definição de serviço define seletores, então suponho que a seguinte passagem se aplique:

Para serviços sem comando que definem seletores, o controlador de endpoints cria registros de endpoints na API e modifica a configuração de DNS para retornar registros (endereços) que apontam diretamente para os pods que apoiam o serviço

Eu segui o exemplo em um cluster K8s gerenciado de 3 nós no Azure:

C:\work\k8s\mysql-wp-demo> kubectl.exe get ep
NAME              ENDPOINTS          AGE
kubernetes        52.186.94.71:443   47h
wordpress         10.244.0.10:80     5h33m
wordpress-mysql   10.244.3.28:3306   5h33m
C:\work\k8s\mysql-wp-demo> kubectl.exe get pods -o wide
NAME                               READY   STATUS    RESTARTS   AGE     IP            NODE                                NOMINATED NODE   READINESS GATES
wordpress-584f8d8666-rlbf5         1/1     Running   0          5h33m   10.244.0.10   aks-nodepool1-30294001-vmss000001   <none>           <none>
wordpress-mysql-55c74969cd-4l8d4   1/1     Running   0          5h33m   10.244.3.28   aks-nodepool1-30294001-vmss000003   <none>           <none>
C:\work\k8s\mysql-wp-demo>

Tanto quanto eu entendo, não há diferença da perspectiva dos terminais.

Alguém pode me explicar - qual é o sentido dos serviços sem cabeça em geral e neste exemplo em particular?

Respostas

3 Matt Sep 17 2020 at 03:18

Um serviço regular tem um IP de serviço virtual que existe como regras iptables ou ipvs em cada nó. Uma nova conexão com esse IP de serviço é então roteada com DNAT para um dos endpoints do pod, para oferecer suporte a uma forma de balanceamento de carga em vários pods.

Um serviço sem comando (que não é um ExternalName) criará Aregistros DNS para qualquer endpoint com rótulos ou nomes correspondentes. As conexões irão diretamente para um único pod / endpoint sem atravessar as regras de serviço.

Um serviço com um tipo de ExternalNameé apenas um CNAMEregistro DNS no DNS do kubernetes. Por definição, eles são sem cabeça, pois são nomes de um IP externo ao cluster.

O exemplo de implantação / serviço myql vinculado está levando ao StatefulSet. Essa implantação é basicamente um único conjunto de estados de pod. Ao mover para um StatefulSet com vários pods, você desejará principalmente endereçar membros individuais do StatefulSet com um nome específico (consulte o comentário de mdaniel ).

Outro motivo para definir clusterIP: Noneé diminuir a carga no processamento do iptables, que fica mais lento conforme o número de serviços (ou seja, regras do iptables) aumenta. Aplicativos que não precisam de vários pods, não precisam do IP de serviço. Configurar um cluster para usar IPVS alivia um pouco o problema de desaceleração.