共用方式為

在 Azure Kubernetes 服务中使用多个公共负载均衡器(预览版)

Azure Kubernetes 服务(AKS)通常为 LoadBalancer 群集中的所有服务预配一个标准负载均衡器(SLB)。 由于每个节点 NIC 限制为 300 个入站负载均衡规则8 个专用链接服务,因此大型群集或端口密集型工作负荷可以快速耗尽这些限制。

多 SLB 预览版通过允许在同一群集内创建多个 SLB 并跨这些 SLB 分片节点和服务,消除了这一瓶颈。 定义 负载均衡器配置,每个配置都绑定到主代理池和可选的命名空间、标签或节点选择器,AKS 会自动将节点和服务放置在相应的 SLB 上。 如果 outboundTypeloadBalancer,则出站 SNAT 行为保持不变。 出站流量仍会流经第一个 SLB。

使用此功能可以:

  • 无需添加群集即可突破 300 个入站规则的限制。
  • 通过将专用 SLB 绑定到其自身的代理池,隔离租户或工作负载流量。
  • 当接近每个 SLB 的限制时,将专用链接服务分布到多个 SLB 上。

先决条件

  • aks-preview 扩展 18.0.0b1 或更高版本。
  • 已注册订阅功能标志 Microsoft.ContainerService/MultipleStandardLoadBalancersPreview
  • Kubernetes 版本 1.28 或更高版本。
  • 使用--load-balancer-backend-pool-type nodeIP创建群集或使用az aks update更新现有群集。

安装 aks-preview Azure CLI 扩展

重要

AKS 预览功能可在自助服务和自愿选择的基础上启用。 预览版按“现状”和“视供应情况”提供,它们不包括在服务级别协议和有限保证范围内。 AKS 预览功能是由客户支持尽最大努力部分覆盖。 因此,这些功能并不适合用于生产。 有关详细信息,请参阅以下支持文章:

  • 使用 az extension add 命令安装 aks-preview 扩展。

    az extension add --name aks-preview
    
  • 使用 az extension update 命令更新到已发布的最新扩展版本。

    az extension update --name aks-preview
    

注册 MultipleStandardLoadBalancersPreview 功能标志

  1. 使用 MultipleStandardLoadBalancersPreview 命令注册 az feature register 功能标志。

    az feature register --namespace "Microsoft.ContainerService" --name "MultipleStandardLoadBalancersPreview"
    

    几分钟后,状态将显示为“已注册”

  2. 使用 az feature show 命令验证注册状态:

    az feature show --namespace "Microsoft.ContainerService" --name "MultipleStandardLoadBalancersPreview"
    
  3. 当状态反映为已注册时,使用 命令刷新 az provider register 资源提供程序的注册。

    az provider register --namespace Microsoft.ContainerService
    

AKS 如何选择负载均衡器(节点和服务放置)

AKS 使用多个输入来确定在何处放置节点并公开 LoadBalancer 服务。 这些参数在每个负载均衡器配置中定义,并影响每个资源的 SLB 选择。

输入类型 适用于 DESCRIPTION
主代理池
--primary-agent-pool-name
节点 必填。 此池中的所有节点始终会添加到 SLB 的后端池。 确保每个 SLB 至少有一个正常运行的节点。
节点选择器
--node-selector
节点 可选。 除主池外,还会将具有匹配标签的任何节点添加到 SLB。
服务命名空间选择器
--service-namespace-selector
服务业 可选。 只有位于具有匹配标签的命名空间中的服务才会考虑使用此 SLB。
服务标签选择器
--service-label-selector
服务业 可选。 只有具有匹配标签的服务才有资格使用此 SLB。
服务注释
service.beta.kubernetes.io/azure-load-balancer-configurations
服务业 可选。 将放置限制为一个或多个明确命名的 SLB 配置。 在没有它的情况下,任何匹配的配置都符合条件。

注释

选择器定义适用性。 批注(如果使用)将控制器限制为特定 SLB 子集。

AKS 如何使用这些输入

AKS 控制平面使用上述规则持续协调节点和服务状态:

节点位置

添加或更新节点时,AKS 会根据主池和节点选择器检查该节点符合哪些 SLB 的条件。

  • 如果多个 SLB 匹配,控制器将选取当前节点最少的 SLB。
  • 该节点会添加到该 SLB 的后端池。

服务部署

创建或更新 LoadBalancer 服务时:

  1. AKS 会查找命名空间和标签选择器与服务匹配的 SLB。
  2. 如果存在服务注解,则仅考虑那些命名的 SLB。
  3. 排除 allowServicePlacement=false 或会超出 Azure 限制(300 条规则或 8 个专用链接服务)的 SLB。
  4. 在有效选项中,选择了包含最少规则的 SLB。

externalTrafficPolicy (ETP) 行为

AKS 根据externalTrafficPolicy的值不同而以不同方式处理服务。

Mode 负载均衡器选择的工作原理 如何构建后端池成员列表 注释
群集 (默认值) 控制器遵循上述标准放置规则。 单个负载均衡规则针对所选 SLB 上的共享 kubernetes 后端池。 该 SLB kubernetes 池中的所有节点都是正常的目标。 健康探测器会自动删除没有匹配 Pod 的节点。 与当前单 SLB 群集中的行为相同。
本地 控制器仍使用基于选择器的算法来选取 SLB,但 为每个服务创建专用后端池 ,而不是使用共享池。 成员身份从服务的 EndpointSlice 对象同步,因此 只有那些实际托管就绪 Pod 的节点才会被添加。 运行状况探测继续使用 healthCheckNodePort 来移除运行不正常的节点。 保证客户端 IP 的保留,并避免通过缺少 Pod 的节点进行路由,即使节点在多个 SLB 中分片。

为何为本地 ETP 设置专用池?
在多 SLB 模式下,承载特定服务 Pod 的节点可能位于与面向客户端的 VIP 不同的 SLB 上。 共享后端池通常包含零个符合条件的节点,从而中断流量。 通过为每个服务分配专用池并从 EndpointSlice 同步,AKS 可确保服务的 SLB 始终指向正确的节点。

对配额的影响

  • 每个 ETP 本地服务将一个后端池和一个负载均衡规则添加到其 SLB。
  • 这些计算在 300 个规则限制之内,因此在拥有众多 ETP 本地服务时,请注意监控规则的使用情况。

对出站流量没有更改

aksOutboundBackendPooloutboundType 时,出站 SNAT 仍会流经第一个 SLB 的 loadBalancer,这一点与 ETP 设置无关。

可选:重新均衡

之后,你可以使用 az aks loadbalancer rebalance 手动重新平衡节点分布。

通过此设计,可以为基础结构和工作负载定义灵活的标签驱动路由,而 AKS 会自动处理放置,以保持平衡并避免配额问题。

添加第一个负载均衡器配置

添加一个名为 kubernetes 的配置,并将其绑定到一个始终至少有一个节点的 代理池。 删除每个配置会将群集切换回单 SLB 模式。

重要

若要启用多 SLB 模式,必须 添加一个负载均衡器配置,名称为 kubernetes,并将其附加到始终至少有一个就绪节点的 代理池。
此配置的存在用于切换多SLB支持;在服务选择中,它没有特殊优先级,并且被视为与任何其他负载均衡器配置相同。
如果删除每个负载均衡器配置,群集会自动回退到单 SLB 模式,这可能会短暂中断服务路由或 SNAT 流。

  1. 设置用于本教程的环境变量。 可以将所有占位符值替换为自己的值,但 DEFAULT_LB_NAME 必须保持为 kubernetes

    RESOURCE_GROUP="rg-aks-multislb"
    CLUSTER_NAME="aks-multi-slb"
    LOCATION="chinanorth3"
    DEFAULT_LB_NAME="kubernetes"
    PRIMARY_POOL="nodepool1"
    
  2. 使用 az group create 命令创建资源组。

    az group create --name $RESOURCE_GROUP --location $LOCATION
    
  3. 使用 az aks create 命令创建 AKS 群集。\

    az aks create --resource-group $RESOURCE_GROUP --name $CLUSTER_NAME \
      --load-balancer-backend-pool-type nodeIP \
      --node-count 3
    
  4. 使用 az aks loadbalancer add 命令添加默认负载均衡器。

    az aks loadbalancer add --resource-group $RESOURCE_GROUP --cluster-name $CLUSTER_NAME \
      --name $DEFAULT_LB_NAME \
      --primary-agent-pool-name $PRIMARY_POOL \
      --allow-service-placement true
    

添加其他负载均衡器

通过指定不同的主池以及可选的命名空间、标签或节点选择器来创建特定于租户的配置。

  1. 团队 1 将在单独的节点池中运行自己的工作负荷。 分配标签 tenant=team1 ,以便可以使用选择器计划工作负荷:

    TEAM1_POOL="team1pool"
    TEAM1_LB_NAME="team1-lb"
    
  2. 使用 az aks nodepool add 命令为团队 1 创建第二个节点池。

    az aks nodepool add --resource-group $RESOURCE_GROUP --cluster-name $CLUSTER_NAME \
      --name $TEAM1_POOL \
      --labels tenant=team1 \
      --node-count 2
    
  3. 使用 az aks loadbalancer add 命令为团队 1 创建负载均衡器。

    az aks loadbalancer add --resource-group $RESOURCE_GROUP --cluster-name $CLUSTER_NAME \
      --name $TEAM1_LB_NAME \
      --primary-agent-pool-name $TEAM1_POOL \
      --service-namespace-selector "tenant=team1" \
      --node-selector "tenant=team1"
    
  4. 标记目标命名空间(例如, team1-apps)以使用 az aks command invoke 命令匹配选择器。

    az aks command invoke \
      --resource-group $RESOURCE_GROUP \
      --name $CLUSTER_NAME \
      --command "
    kubectl create namespace team1-apps --dry-run=client -o yaml | kubectl apply -f -
    kubectl label namespace team1-apps tenant=team1 --overwrite
    "
    
  5. 现在可以列出群集中的负载均衡器,以便使用 az aks loadbalancer list 命令查看多个配置。

    az aks loadbalancer list --resource-group $RESOURCE_GROUP --cluster-name $CLUSTER_NAME --output table
    

    示例输出:

    AllowServicePlacement    ETag     Name        PrimaryAgentPoolName    ProvisioningState    ResourceGroup
    -----------------------  -------  ----------  ----------------------  -------------------  ---------------
    True                     <ETAG>   kubernetes  nodepool1               Succeeded            rg-aks-multislb
    True                     <ETAG>   team1-lb    team1pool               Succeeded            rg-aks-multislb
    

将服务部署到特定负载均衡器

使用逗号分隔的配置名称列表添加批注 service.beta.kubernetes.io/azure-load-balancer-configurations。 如果省略批注,控制器会自动选择。

az aks command invoke \
  --resource-group $RESOURCE_GROUP \
  --name $CLUSTER_NAME \
  --command "
cat <<EOF | kubectl apply -f -
apiVersion: v1
kind: Service
metadata:
  name: lb-svc-1
  namespace: team1-apps
  labels:
    app: nginx-test
  annotations:
    service.beta.kubernetes.io/azure-load-balancer-configurations: \"team1-lb\"
spec:
  selector:
    app: nginx-test
  ports:
  - name: port1
    port: 80
    targetPort: 80
    protocol: TCP
  type: LoadBalancer
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx-test
  namespace: team1-apps
  labels:
    app: nginx
spec:
  replicas: 1
  selector:
    matchLabels:
      app: nginx-test
  template:
    metadata:
      labels:
        app: nginx-test
    spec:
      containers:
      - image: nginx
        imagePullPolicy: Always
        name: nginx
        ports:
        - containerPort: 80
          protocol: TCP
        resources:
          limits:
            cpu: \"150m\"
            memory: \"300Mi\"
EOF
"

重新平衡节点(可选)

如果缩放后规则数量变得不平衡,可以使用 az aks loadbalancer rebalance 命令运行再平衡操作。 此命令会中断活动流,因此应在维护时段内执行调度。

az aks loadbalancer rebalance --resource-group $RESOURCE_GROUP --cluster-name $CLUSTER_NAME

监视和故障排除

  • 监视控制器事件(kubectl get events …)以确认服务已协调。
  • 如果外部连接被阻止,请打开节点 shell 并 curl 服务 VIP 以确认 kube-proxy 路由。

限制和已知问题

限度 详细信息
出站 SNAT 始终使用第一个 SLB;出站流不会分片。
后端池类型 创建或更新现有群集以使用 nodeIP 后端池。
自动缩放程序归零 主代理池无法扩展到 0 个节点。
ETP local 规则增长 每个 ETP local 服务都使用其自己的规则和后端池,因此规则数量的增长速度可能比 cluster 模式更快。
再平衡中断 从后端池中移除节点会中断活动连接。 规划维护时段。
配置重新加载时间 运行 az aks loadbalancer后,更改可能不会立即生效。 AKS操作很快完成,但云控制器管理器可能需要更长的时间才能应用更新。 等待 EnsuredLoadBalancer 事件以确保更改已生效。

清理资源

完成操作后,使用 az group delete 命令删除资源组以移除群集和负载均衡器。

az group delete --name $RESOURCE_GROUP --yes --no-wait

后续步骤

多个 SLB 功能有助于在网络层缩放和隔离工作负荷,同时通过 Azure 托管的配置保持简单性。 有关详细信息,请参阅以下资源: