在 Azure Kubernetes 服务 (AKS) 中使用双栈网络

在使用双栈 Azure 虚拟网络时,可以在双栈模式下部署 AKS 群集。 在此配置中,节点从 Azure 虚拟网络子网接收 IPv4 和 IPv6 地址。 Pod 接收从逻辑上不同的地址空间到节点的 Azure 虚拟网络子网的 IPv4 和 IPv6 地址。 然后配置网络地址转换(NAT),以便 Pod 可以访问 Azure 虚拟网络上的资源。 流量的源 IP 地址是 NAT 到同一系列的节点主 IP 地址(从 IPv4 到 IPv4 和从 IPv6 到 IPv6)。

本文演示了如何将双堆栈网络与 AKS 群集一起使用。 有关网络选项和注意事项的详细信息,请参阅 Kubernetes 和 AKS 的网络概念

重要

2025 年 11 月 30 日开始,Azure Kubernetes 服务(AKS)不再支持或提供 Azure Linux 2.0 安全更新。 Azure Linux 2.0 节点映像在 202512.06.0 版中冻结。 从 2026 年 3 月 31 日开始,将删除节点映像,并且无法缩放节点池。 通过将 节点池升级到 受支持的 Kubernetes 版本或迁移到 osSku AzureLinux3,迁移到受支持的 Azure Linux 版本。 有关详细信息,请参阅 停用 GitHub 问题和Azure 更新停用公告。 若要随时了解公告和更新,请关注AKS 发行说明

局限性

  • 在 Azure Linux 节点池中,IPv6 服务需要 externalTrafficPolicy: Local
  • Azure 虚拟网络和 Pod CIDR 需要双栈网络。
    • 节点或 Pod IP 地址不支持单栈的仅 IPv6 网络。 可在 IPv4 或 IPv6 上预配服务。
  • Azure CNI Overlay 不支持在双堆栈网络中使用 Azure 或 Calico 网络策略。 若要使用网络策略,请使用由 Cilium 提供支持的 CNI Azure。
  • 标准 NAT 网关仅支持 IPv4。 对于双堆栈出口,请使用 StandardV2 NAT 网关。 由 AKS 管理的 managedNATGatewayV2 出站类型目前处于预览阶段。
  • 虚拟节点加载项不支持在双栈网络中使用。

先决条件

本文使用的是 Azure CNI Overlay。 还可以在运行 Kubernetes 1.29 或更高版本的 Linux 群集上部署由 Cilium 提供支持的 Azure CNI 双堆栈群集。

Kubernetes 中的双栈网络概述

Kubernetes v1.23 为 IPv4/IPv6 双栈群集(包括 Pod 和服务网络)提供稳定的上游支持。 节点和 Pod 始终获得 IPv4 和 IPv6 两种地址,而服务在每种地址系列上可以是双栈也可以是单栈。

AKS 为双栈网络配置所需的支持服务。 该配置包括:

  • 如果使用托管虚拟网络,请使用双堆栈虚拟网络配置。
  • IPv4 和 IPv6 节点和 Pod 地址。
  • IPv4 和 IPv6 流量的出站规则。
  • IPv4 和 IPv6 服务的负载均衡器设置。

注释

将双堆栈网络与用户定义的路由的 出站类型 结合使用时,可以选择为 IPv6 设置默认路由,具体取决于是否需要 IPv6 流量才能访问 Internet。 如果没有 IPv6 的默认路由,则会在创建群集时显示警告,但不会阻止群集创建。

双堆栈群集参数

以下参数支持双堆栈群集:

Parameter 接受的值 默认值 限制条件
--ip-families ipv4ipv4,ipv6 未指定 提供以逗号分隔的 IP 系列列表,以便在群集上启用。
--pod-cidrs 逗号分隔的 CIDR 范围 10.244.0.0/16,fd12:3456:789a::/64 范围的数量和顺序必须与 --ip-families 匹配。
--service-cidrs 逗号分隔的 CIDR 范围 10.0.0.0/16,fd12:3456:789a:1::/108 范围的数量和顺序必须与 --ip-families 匹配。 IPv6 子网不能大于 /108

部署双栈 AKS 群集

  1. 使用 az group create 命令为群集创建 Azure 资源组。

    az group create --location <region> --name <resourceGroupName>
    
  2. 使用 az aks create 参数设置为 --ip-familiesipv4,ipv6 命令创建双堆栈 AKS 群集。

    az aks create \
        --location <region> \
        --resource-group <resourceGroupName> \
        --name <clusterName> \
        --network-plugin azure \
        --network-plugin-mode overlay \
        --ip-families ipv4,ipv6 \
        --generate-ssh-keys
    
  3. 创建群集后,使用 az aks get-credentials 命令获取群集凭据。

    az aks get-credentials --resource-group <resourceGroupName> --name <clusterName>
    

检查节点来查看两个 IP 系列

集群预配完成后,使用 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 服务器,以验证双堆栈 Pod IP 分配。

部署 NGINX Web 服务器

  1. 通过运行 kubectl create deployment nginx 命令创建 NGINX Web 服务器。

    kubectl create deployment nginx --image=nginx:latest --replicas=3
    
  2. 通过运行 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
    

通过 LoadBalancer 类型服务公开工作负载

重要

Azure 负载均衡器将运行状况探测从链接本地地址发送到 IPv6 目标。 在 Azure Linux 节点池中,使用 externalTrafficPolicy: Cluster IPv6 服务的流量会失败。 以下示例在 IPv6 服务上设置 externalTrafficPolicy: Localkube-proxy 以便响应节点上的探测。

  1. 使用 LoadBalancer 命令,通过单独的 IPv4 和 IPv6 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":{"externalTrafficPolicy":"Local","ipFamilies":["IPv6"]}}'
    

    你会看到表明这些服务已暴露的输出结果。

    service/nginx-ipv4 exposed
    service/nginx-ipv6 exposed
    
  2. 公开部署并完全预配 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
    
  3. 使用分配的 IPv6 地址和配置的 IPv6 路由验证 Linux VM 或本地计算机的功能。

    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>