En esta página se explica cómo configurar Service Steering para tus pods.
Para saber cómo funciona la dirección de servicios, consulta el artículo Cómo funciona la dirección de servicios.
Requisitos
- GKE 1.30 o una versión posterior.
Limitaciones
- Un
ServiceFunctionChain
puede tener como máximo una función de servicio. - Recomendamos usar un máximo de 100 nodos más 10 pares de
ServiceFunctionChain
yTrafficSelector
. - La función de dirección de servicios de GKE solo está disponible en los nodos que ejecutan la imagen de nodo de Container-Optimized OS.
- GKE Service Steering solo admite direcciones IP de salida y de destino.
- Service Steering no gestiona los conflictos que surgen cuando se aplican varios TrafficSelectors con longitudes de prefijo idénticas al mismo asunto. Para evitar conflictos, diseña de forma proactiva tus selectores de tráfico con intervalos de direcciones IP que no se solapen y con criterios de selección claramente definidos.
Implementar la dirección de servicios
La función de dirección de servicios de GKE te permite personalizar y controlar el flujo de tráfico de red en un clúster. En esta sección se muestra cómo implementar Service Steering mediante un ejemplo de puerta de enlace web.
Imagina que quieres crear una pasarela web que proteja el tráfico de los dispositivos cliente de los usuarios finales a Internet. Un terminador de VPN atrae el tráfico a la pasarela gestionada mediante un túnel seguro. El tráfico del usuario final se redirige al firewall y, a continuación, al proxy. El proxy realiza la traducción de direcciones de red de origen (SNAT) en el tráfico, enmascara la dirección de origen original y la envía a Internet.
Para implementar GKE Service Steering, haz lo siguiente:
- Crea una VPC con una MTU de 8896.
- Crea un clúster de GKE.
- Crea los pods y el servicio de la función de servicio.
- Crea el
ServiceFunctionChain
. - Crea el recurso
TrafficSelector
que hace referencia aServiceFunctionChain
.
Antes de empezar
Antes de empezar, asegúrate de que has realizado las siguientes tareas:
- Habilita la API de Google Kubernetes Engine. Habilitar la API de Google Kubernetes Engine
- Si quieres usar Google Cloud CLI para esta tarea, instálala y, a continuación, inicialízala. Si ya has instalado la gcloud CLI, obtén la versión más reciente ejecutando
gcloud components update
.
- Consulta los requisitos y las limitaciones.
Preparar una VPC
Prepara una VPC. La dirección de servicios usa la encapsulación para redirigir el tráfico a las funciones de servicio adecuadas. La encapsulación implica añadir encabezados adicionales a cada paquete, lo que aumenta el tamaño del paquete. Service Steering no requiere ninguna configuración especial en las VPCs. Al preparar la VPC, le recomendamos que, al decidir el tamaño de la MTU, tenga en cuenta la sobrecarga de encapsulación. Para obtener más información, consulta Red de VPC con una MTU especificada.
El siguiente comando define el tamaño de MTU en tu VPC:
gcloud compute networks create VPC_NETWORK_NAME --mtu=8896
Sustituye VPC_NETWORK_NAME
por el nombre de la red VPC que contiene la subred.
Crear un clúster de GKE
Para habilitar las funciones avanzadas de gestión de direcciones IP y de enrutamiento de red necesarias para implementar la dirección de servicios en GKE, crea un clúster de GKE con GKE Dataplane V2 habilitado de la siguiente manera:
gcloud container clusters create CLUSTER_NAME \
--network VPC_NAME \
--release-channel RELEASE_CHANNEL \
--cluster-version CLUSTER_VERSION \
--enable-dataplane-v2 \
--enable-ip-alias
Haz los cambios siguientes:
CLUSTER_NAME
: el nombre del clúster.VPC_NAME
: el nombre de la VPC con la que quieres asociar el clúster.RELEASE_CHANNEL
: el nombre del canal de lanzamiento.VERSION
: la versión de GKE, que debe ser la 1.30 o una posterior. También puedes usar la marca--release-channel
para seleccionar un canal de lanzamiento. El canal de lanzamiento debe tener una versión predeterminada 1.30 o posterior.
Crear ServiceFunction
Pods
Para establecer tu cadena de servicios, despliega el pod de terminación de VPN y los pods de función de servicio necesarios en tu clúster. Los pods encapsulan las aplicaciones en contenedores que realizan tus funciones de red.
El pod de terminación de VPN suele ser la primera función de servicio de la cadena, que termina el tráfico que entra en el clúster a través de la VPN. A continuación, dirige las demás funciones de servicio, como los cortafuegos y el balanceo de carga, para que se procesen antes de llegar al destino final.
En el siguiente archivo de configuración de ejemplo se definen los tres componentes esenciales para gestionar el tráfico de red en un clúster:
- Pod de VPN: establece un endpoint de red privada virtual (VPN) en tu clúster, lo que permite una comunicación segura y cifrada entre tu clúster y redes externas.
- Despliegue de firewall: despliega varias réplicas de un pod de firewall, que proporciona seguridad y balanceo de carga.
- DaemonSet de proxy: implementa un pod de proxy en cada nodo de tu clúster, lo que asegura que el tráfico de red se pueda procesar de forma local antes de reenviarse a otros servicios, como el cortafuegos.
Guarda el siguiente archivo de manifiesto de ejemplo como service_function.yaml
:
apiVersion: v1
kind: Pod
name: vpn
namespace: vpn
labels:
app: vpn
spec:
containers:
- name: vpn
image: openvpn
ports:
- containerPort: 51820
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: firewall
namespace: firewall
spec:
replicas: 3
selector:
matchLabels:
app: firewall
template:
metadata:
labels:
app: firewall
spec:
containers:
- name: firewall
image: firewall
---
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: proxy
namespace: proxy
spec:
selector:
matchLabels:
app: proxy
template:
metadata:
labels:
app: proxy
spec:
containers:
- name: proxy
image: proxy
Aplica el archivo de manifiesto:
kubectl apply -f service_function.yaml
Crear ServiceFunctionChains
Para definir una secuencia de funciones de red que debe seguir el tráfico, crea una canalización en la que cada función (como cortafuegos, proxy y balanceador de carga) realice su tarea específica antes de enviar el tráfico a la siguiente.
Guarda el siguiente archivo de manifiesto de ejemplo como ServiceFunctionChain.yaml
:
apiVersion: networking.gke.io/v1
kind: ServiceFunctionChain
metadata:
name: firewall
spec:
sessionAffinity:
clientIpNoDestination:
timeoutSeconds: 3600 # 1hr
serviceFunctions:
- name: firewall
namespace: firewall
podSelector:
matchLabels:
app: firewall
---
apiVersion: networking.gke.io/v1
kind: ServiceFunctionChain
metadata:
name: proxy
spec:
sessionAffinity:
clientIpNoDestination: {}
serviceFunctions:
- name: proxy
namespace: proxy
podSelector:
matchLabels:
app: proxy
Aplica el archivo de manifiesto:
kubectl apply -f ServiceFunctionChain.yaml
Las funciones de servicio se definen en línea en ServiceFunctionChain
mediante el campo serviceFunctions
. Una función de servicio es un selector de endpoints.
Crea el recurso TrafficSelector
.
Para definir dónde y qué tráfico se selecciona para la dirección de servicios, cree el recurso TrafficSelector
que haga referencia al ServiceFunctionChains
que quiera aplicar al tráfico elegido.
Guarda el siguiente archivo de manifiesto de ejemplo como TrafficSelector.yaml
:
apiVersion: networking.gke.io/v1
kind: TrafficSelector
metadata:
name: vpn-to-firewall
spec:
serviceFunctionChain: firewall
subject:
pods:
namespaceSelector:
matchLabels:
kubernetes.io/metadata.name: vpn
podSelector:
matchLabels:
app: vpn
egress:
to:
ipBlock:
cidr: 0.0.0.0/0
ports:
- allPorts:
protocol: UDP
- allPorts:
protocol: TCP
---
apiVersion: networking.gke.io/v1
kind: TrafficSelector
metadata:
name: firewall-to-proxy
spec:
serviceFunctionChain: proxy
subject:
pods:
namespaceSelector:
kubernetes.io/metadata.name: firewall
podSelector:
app: firewall
egress:
to:
ipBlock:
cidr: 0.0.0.0/0
ports:
- allPorts:
protocol: UDP
- allPorts:
protocol: TCP
Aplica el archivo de manifiesto:
kubectl apply -f TrafficSelector.yaml
Solucionar problemas de la función de dirección de servicios
En esta sección se explica cómo resolver problemas relacionados con GKE Service Steering.
El tráfico de red no fluye
Puedes tomar las medidas que se indican a continuación para depurar el problema:
Paso 1: Comprueba que servicePathId
esté configurado en ServiceFunctionChain
Verifica que servicePathId
esté configurado en ServiceFunctionChain
. A cada objeto ServiceFunctionChain
se le asigna un servicePathId
único, como se muestra en el siguiente ejemplo:
apiVersion: networking.gke.io/v1
kind: ServiceFunctionChain
metadata:
name: firewall
spec:
serviceFunctions:
- name: firewall
namespace: firewall
podSelector:
matchLabels:
app: firewal
status:
servicePathId: 1
Paso 2: Verifica que se haya creado un servicio de Kubernetes por cada función de servicio
Se crea automáticamente un servicio ClusterIP para cada función de servicio. Puedes ver la lista de servicios con kubectl
:
kubectl get svc -A -l networking.gke.io/managed-by=service-steering-controller.gke.io
Paso 3: Verifica que, en cada función de servicio, se cree una entrada de mapa bpf en cada nodo para almacenar la dirección IP del servicio
Por cada función de servicio, se crea una entrada de mapa bpf en cada nodo para almacenar la dirección IP del servicio.
Obtén el nombre del pod anetd
:
kubectl get pods -n kube-system -o wide -l k8s-app=cilium
Registra el nombre del pod, como anetd
.
Ejecuta el siguiente comando:
kubectl -n kube-system exec -it ANETD-POD-NAME -- cilium bpf sfcpath list
Sustituye ANETD-POD-NAME
por el nombre del anetd
Pod.
El resultado debería ser similar al siguiente:
PATH SERVICE FUNCTION ADDRESS
(1, 1) 10.4.10.124
Paso 4: Verifica que se hayan creado entradas de mapa bpf en el mapa sfcselect
En un nodo, si hay pods seleccionados por un TrafficSelector
, se crean entradas de mapa bpf en el mapa sfcselect
. En el siguiente ejemplo se muestra que el tráfico TCP/UDP de cualquier puerto del endpoint (pod) 3783 a la dirección IP de destino 10.0.2.12 se dirige a un ServiceFunctionChain
.
Ejecuta el siguiente comando:
kubectl -n kube-system exec -it ANETD-POD-NAME -- cilium bpf sfcselect list
Sustituye ANETD-POD-NAME
por el nombre real del pod anetd de tu clúster.
El resultado debería ser similar al siguiente:
SELECTOR PATH
3783, egress, 0/TCP, 10.0.2.12/32 /32 (1, 1)
3783, egress, 0/UDP, 10.0.2.12/32 /32 (1, 1)
Paso 5: Usa tcpdump en el puerto 7081 para capturar y analizar el tráfico de red
Service Steering usa la encapsulación Geneve en el puerto UDP 7081. Puedes usar tcpdump en los nodos correspondientes para analizar el flujo de tráfico y determinar dónde puede estar ocurriendo el problema.
Siguientes pasos
- Consulta Información sobre la compatibilidad con varias redes para pods.
- Consulta Información sobre la dirección de servicios.
- Consulte Configurar la compatibilidad con varias redes para pods.