在 Azure Kubernetes 服务 (AKS) 中使用双堆栈 Kubenet 网络
在使用 kubenet 网络和双堆栈 Azure 虚拟网络时,可以在双堆栈模式中部署 AKS 群集。 在此配置中,节点从 Azure 虚拟网络子网接收 IPv4 和 IPv6 地址。 Pod 接收从逻辑上不同的地址空间到节点的 Azure 虚拟网络子网的 IPv4 和 IPv6 地址。 然后配置网络地址转换 (NAT),以便 Pod 可以访问 Azure 虚拟网络上的资源。 流量的源 IP 地址是 NAT 到同一系列的节点主 IP 地址(从 IPv4 到 IPv4 和从 IPv6 到 IPv6)。
本文演示了如何将双堆栈网络与 AKS 群集一起使用。 有关网络选项和注意事项的详细信息,请参阅 Kubernetes 和 AKS 的网络概念。
- Azure 路由表的硬性限制是每个表 400 个路由。
- 双堆栈群集中的每个节点都需要两个路由(每个 IP 地址系列一个路由),因此双堆栈群集限制为 200 个节点。
- 在 Azure Linux 节点池中,服务对象仅支持用于
externalTrafficPolicy: Local
。 - Azure 虚拟网络和 Pod CIDR 需要双堆栈网络。
- 节点或 Pod IP 地址不支持单堆栈仅 IPv6。 可在 IPv4 或 IPv6 上预配服务。
- 双堆栈 kubenet 不支持以下功能:
- 配置 kubenet 网络的所有先决条件适用。
- AKS 双堆栈群集需要 Kubernetes v1.21.2 或更高版本。 推荐 v1.22.2 或更高版本。
- 如果使用 Azure 资源管理器模板,需要架构版本 2021-10-01。
Kubernetes v1.23 为 IPv4/IPv6 双堆栈群集(包括 Pod 和服务网络)提供稳定的上游支持。 节点和 Pod 始终获得 IPv4 和 IPv6 两种地址,而服务在每种地址系列上可以是双堆栈也可以是单堆栈。
AKS 为双堆栈网络配置所需的支持服务。 该配置包括:
- 双堆栈虚拟网络配置(如果使用托管虚拟网络)。
- IPv4 和 IPv6 节点和 Pod 地址。
- IPv4 和 IPv6 流量的出站规则。
- IPv4 和 IPv6 服务的负载均衡器设置。
备注
将 Dualstack 与用户定义的路由出站类型配合使用时,可以选择为 IPv6 设置默认路由,具体取决于是否需要 IPv6 流量访问 Internet。 如果没有为 IPv6 设置默认路由,创建群集时会显示警告,但不会阻止群集的创建。
提供了下列属性来支持双堆栈群集:
--ip-families
:采用要在群集上启用的 IP 系列列表,以逗号分隔。- 仅支持
ipv4
或ipv4,ipv6
。
- 仅支持
--pod-cidrs
:采用 CIDR 表示法 IP 范围的逗号分隔列表,从中分配 Pod IP。- 此列表中范围的计数和顺序必须与提供给
--ip-families
的值匹配。 - 如果未提供值,则使用默认值
10.244.0.0/16,fd12:3456:789a::/64
。
- 此列表中范围的计数和顺序必须与提供给
--service-cidrs
:采用 CIDR 表示法 IP 范围的逗号分隔列表,从中分配服务 IP。- 此列表中范围的计数和顺序必须与提供给
--ip-families
的值匹配。 - 如果未提供值,则使用默认值
10.0.0.0/16,fd12:3456:789a:1::/108
。 - 分配给
--service-cidrs
的 IPv6 子网不能大于 /108。
- 此列表中范围的计数和顺序必须与提供给
使用
az group create
命令为群集创建 Azure 资源组。az group create -l <region> -n <resourceGroupName>
使用
--ip-families
参数设置为ipv4,ipv6
的az aks create
命令创建双堆栈 AKS 群集。az aks create -l <region> -g <resourceGroupName> -n <clusterName> --ip-families ipv4,ipv6
创建群集后,使用
az aks get-credentials
命令获取群集管理员凭据。az aks get-credentials -g <resourceGroupName> -n <clusterName>
预配群集后,使用
kubectl get nodes
命令确认节点已预配双堆栈网络。kubectl get nodes -o=custom-columns="NAME:.metadata.name,ADDRESSES:.status.addresses[?(@.type=='InternalIP')].address,PODCIDRS:.spec.podCIDRs[*]"
kubectl get nodes
命令的输出显示节点具有来自 IPv4 和 IPv6 的地址和 Pod IP 分配空间。NAME ADDRESSES PODCIDRS aks-nodepool1-14508455-vmss000000 10.240.0.4,2001:1234:5678:9abc::4 10.244.0.0/24,fd12:3456:789a::/80 aks-nodepool1-14508455-vmss000001 10.240.0.5,2001:1234:5678:9abc::5 10.244.1.0/24,fd12:3456:789a:0:1::/80 aks-nodepool1-14508455-vmss000002 10.240.0.6,2001:1234:5678:9abc::6 10.244.2.0/24,fd12:3456:789a:0:2::/80
创建群集后,便可部署工作负载。 本文将指导你完成 NGINX Web 服务器的示例工作负载部署。
使用
kubectl create deployment nginx
命令创建 NGINX Web 服务器。kubectl create deployment nginx --image=nginx:latest --replicas=3
使用
kubectl get pods
命令查看 Pod 资源。kubectl get pods -o custom-columns="NAME:.metadata.name,IPs:.status.podIPs[*].ip,NODE:.spec.nodeName,READY:.status.conditions[?(@.type=='Ready')].status"
输出显示 Pod 同时具有 IPv4 地址和 IPv6 地址。 Pod 在获得 IP 地址前,不会显示 IP 地址。
NAME IPs NODE READY nginx-55649fd747-9cr7h 10.244.2.2,fd12:3456:789a:0:2::2 aks-nodepool1-14508455-vmss000002 True nginx-55649fd747-p5lr9 10.244.0.7,fd12:3456:789a::7 aks-nodepool1-14508455-vmss000000 True nginx-55649fd747-r2rqh 10.244.1.2,fd12:3456:789a:0:1::2 aks-nodepool1-14508455-vmss000001 True
重要
从 AKS v1.27 开始,你可以创建双堆栈 LoadBalancer 服务,该服务将预配 1 个 IPv4 公共 IP 和 1 个 IPv6 公共 IP。 但在旧版本中,只有服务的第一个 IP 地址将预配到负载均衡器,因此双堆栈服务只会获得第一个列出的 IP 系列的公共 IP。 要为单个部署提供双堆栈服务,请创建两个面向同一选择器的服务:一个针对 IPv4,一个针对 IPv6。
使用
kubectl expose deployment nginx
命令公开 NGINX 部署。kubectl expose deployment nginx --name=nginx --port=80 --type=LoadBalancer --overrides='{"spec":{"ipFamilyPolicy": "PreferDualStack", "ipFamilies": ["IPv4", "IPv6"]}}'
你会收到一个输出,显示服务已公开。
service/nginx exposed
公开部署并完全预配
LoadBalancer
服务后,使用kubectl get services
命令获取服务的 IP 地址。kubectl get services
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE nginx LoadBalancer 10.0.223.73 2603:1030:20c:9::22d,4.156.88.133 80:30664/TCP 2m11s
kubectl get services nginx -ojsonpath='{.spec.clusterIPs}'
["10.0.223.73","fd17:d93e:db1f:f771::54e"]
在支持 IPv6 的主机中通过命令行 Web 请求来验证功能。 Azure Cloud Shell 不支持 IPv6。
SERVICE_IP=$(kubectl get services nginx -o jsonpath='{.status.loadBalancer.ingress[1].ip}') curl -s "http://[${SERVICE_IP}]" | head -n5
<!DOCTYPE html> <html> <head> <title>Welcome to nginx!</title> <style>
使用
kubectl expose deployment nginx
命令公开 NGINX 部署。kubectl expose deployment nginx --name=nginx-ipv4 --port=80 --type=LoadBalancer' kubectl expose deployment nginx --name=nginx-ipv6 --port=80 --type=LoadBalancer --overrides='{"spec":{"ipFamilies": ["IPv6"]}}'
你会收到一个输出,显示服务已公开。
service/nginx-ipv4 exposed service/nginx-ipv6 exposed
公开部署并完全预配
LoadBalancer
服务后,使用kubectl get services
命令获取服务的 IP 地址。kubectl get services
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE nginx-ipv4 LoadBalancer 10.0.88.78 20.46.24.24 80:30652/TCP 97s nginx-ipv6 LoadBalancer fd12:3456:789a:1::981a 2603:1030:8:5::2d 80:32002/TCP 63s
在支持 IPv6 的主机中通过命令行 Web 请求来验证功能。 Azure Cloud Shell 不支持 IPv6。
SERVICE_IP=$(kubectl get services nginx-ipv6 -o jsonpath='{.status.loadBalancer.ingress[0].ip}') curl -s "http://[${SERVICE_IP}]" | head -n5
<!DOCTYPE html> <html> <head> <title>Welcome to nginx!</title> <style>