跨 VPC 网络创建内部负载均衡器


本页面介绍如何跨 VPC 网络在 Google Kubernetes Engine (GKE) 上创建内部直通式网络负载均衡器。在阅读本页面之前,您应该先熟悉以下概念:

准备工作

在开始之前,请确保您已执行以下任务:

  • 启用 Google Kubernetes Engine API。
  • 启用 Google Kubernetes Engine API
  • 如果您要使用 Google Cloud CLI 执行此任务,请安装初始化 gcloud CLI。 如果您之前安装了 gcloud CLI,请运行 gcloud components update 以获取最新版本。

使用 Private Service Connect 创建内部负载均衡器

作为服务提供方,您可以借助服务连接,通过 Private Service Connect 将服务提供给其他 VPC 网络中的服务使用方。您可以使用 ServiceAttachment 自定义资源创建、管理和删除服务连接。

要求和限制

  • 需要遵循 Private Service Connect 的限制。
  • 您可以在 GKE 1.21.4-gke.300 及更高版本中创建服务连接。
  • 您不能在多个服务连接配置中使用同一个子网。
  • 您必须创建使用内部直通式网络负载均衡器的 GKE 服务。
  • 您不能为 1.22.4-gke.100 之前的 GKE 版本指定其他项目(共享 VPC)中的子网。对于共享 VPC,请确保满足共享 VPC 的所有要求

创建 ServiceAttachment

  1. 创建子网。

    您必须为每个 ServiceAttachment 创建一个新子网

    gcloud beta compute networks subnets create SUBNET_NAME \
        --project PROJECT_ID \
        --network NETWORK_NAME \
        --region REGION \
        --range SUBNET_RANGE \
        --purpose PRIVATE_SERVICE_CONNECT
    

    替换以下内容:

    • SUBNET_NAME:新子网的名称。 在 GKE 1.22.4-gke.100 及更高版本中,您可以使用此字段的完全限定资源网址来指定其他项目中的子网。您可以使用 gcloud compute networks subnets describe 命令获取完全限定的资源网址。
    • PROJECT_ID:您的 Google Cloud 项目的 ID。
    • NETWORK_NAME:子网的 VPC 网络的名称。
    • REGION:新子网的区域。您必须使用您创建的服务所在的区域。
    • SUBNET_RANGE:要用于子网的 IP 地址范围。
  2. 部署工作负载。

    以下清单描述了一个运行示例 Web 应用容器映像的 Deployment。将清单保存为 my-deployment.yaml

    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: psc-ilb
    spec:
      replicas: 3
      selector:
        matchLabels:
          app: psc-ilb
      template:
        metadata:
          labels:
            app: psc-ilb
        spec:
          containers:
          - name: whereami
            image: us-docker.pkg.dev/google-samples/containers/gke/whereami:v1.2.19
            ports:
              - name: http
                containerPort: 8080
            readinessProbe:
              httpGet:
                path: /healthz
                port: 8080
                scheme: HTTP
              initialDelaySeconds: 5
              timeoutSeconds: 1
    
  3. 将清单应用到您的集群:

    kubectl apply -f my-deployment.yaml
    
  4. 创建一项服务。以下清单描述了一项在 TCP 端口 8080 上创建内部直通式网络负载均衡器的服务。将清单保存为 my-service.yaml

     apiVersion: v1
     kind: Service
     metadata:
       name: SERVICE_NAME
       annotations:
         networking.gke.io/load-balancer-type: "Internal"
     spec:
       type: LoadBalancer
       selector:
         app: psc-ilb
       ports:
       - port: 80
         targetPort: 8080
         protocol: TCP
    

    替换以下内容:

    • SERVICE_NAME:新服务的名称。
  5. 将清单应用到您的集群:

    kubectl apply -f my-service.yaml
    
  6. 创建 ServiceAttachment

    以下清单描述了向服务使用方公开您创建的服务的 ServiceAttachment。将清单保存为 my-psc.yaml

    apiVersion: networking.gke.io/v1
    kind: ServiceAttachment
    metadata:
     name: SERVICE_ATTACHMENT_NAME
     namespace: default
    spec:
     connectionPreference: ACCEPT_AUTOMATIC
     natSubnets:
     - SUBNET_NAME
     proxyProtocol: false
     resourceRef:
       kind: Service
       name: SERVICE_NAME
    

    替换以下内容:

    • SERVICE_ATTACHMENT_NAME:新服务连接的名称。
    • SUBNET_NAME:新子网的名称。在 GKE 1.22.4-gke.100 及更高版本中,您可以使用此字段的完全限定资源网址来指定其他项目中的子网。您可以使用 gcloud compute networks subnets describe 命令获取完全限定的资源网址。 对于共享 VPC 配置,请使用以下格式:projects/HOST_PROJECT_ID/regions/COMPUTE_REGION/subnetworks/SUBNET_NAME

    如需详细了解清单字段,请参阅服务连接字段

  7. 将清单应用到您的集群:

    kubectl apply -f my-psc.yaml
    
  8. 验证 Private Service Connect 控制器是否已创建服务连接:

    gcloud beta compute service-attachments list
    

    输出会显示具有自动生成的名称的服务连接:

    NAME        REGION       PRODUCER_FORWARDING_RULE          CONNECTION_PREFERENCE
    k8s1-sa-... REGION_NAME  a3fea439c870148bdba5e59c9ea9451a  ACCEPT_AUTOMATIC
    

查看 ServiceAttachment

您可以使用以下命令查看 ServiceAttachment 的详细信息:

kubectl describe serviceattachment SERVICE_ATTACHMENT_NAME

输出类似于以下内容:

 kubectl describe serviceattachment foo-sa
Name:        <sa-name>
Namespace:    default
Labels:       <none>
Annotations:  <none>
API Version:  networking.gke.io/v1beta1
Kind:         ServiceAttachment
Metadata:
  ...
Status:
  Forwarding Rule URL:      https://www.googleapis.com/compute/beta/projects/<project>/regions/<region>/forwardingRules/<fr-name>
  Last Modified Timestamp:  2021-07-08T01:32:39Z
  Service Attachment URL:   https://www.googleapis.com/compute/beta/projects/<projects>/regions/<region>/serviceAttachments/<gce-service-attachment-name>
Events:                     <none>

使用 ServiceAttachment

如需使用其他项目中的服务,请执行以下步骤:

  1. 获取 ServiceAttachment 的网址:

    kubectl get serviceattachment SERVICE_ATTACHMENT_NAME -o=jsonpath="{.status.serviceAttachmentURL}"
    

    输出内容类似如下:

      serviceAttachmentURL: https://www.googleapis.com/compute/alpha/projects/<project>/region/<region>/serviceAttachments/k8s1-...my-sa
    
  2. 使用 ServiceAttachment 的网址创建 Private Service Connect 端点

  3. 从使用方项目中的虚拟机使用 curl 命令,验证您可以连接到在提供方项目中部署的 Service:

    curl PSC_IP_ADDRESS
    

    PSC_IP_ADDRESS 替换为使用方项目中转发规则的 IP 地址。

    输出类似于以下内容:

    {
      "cluster_name":"cluster",
      "host_header":"10.128.15.200",
      "node_name":"gke-psc-default-pool-be9b6e0e-dvxg.c.gke_project.internal",
      "pod_name":"foo-7bf648dcfd-l5jf8",
      "pod_name_emoji":"👚",
      "project_id":"gke_project",
      "timestamp":"2021-06-29T21:32:03",
      "zone":"ZONE_NAME"
    }
    

更新 ServiceAttachment

您可以按照以下步骤更新 ServiceAttachment

  1. 修改 my-psc.yaml 中的 ServiceAttachment 清单:

    apiVersion: networking.gke.io/v1
    kind: ServiceAttachment
    metadata:
      name: my-sa
      namespace: default
    spec:
      connectionPreference: ACCEPT_AUTOMATIC
      natSubnets:
      - my-nat-subnet
      proxyProtocol: false
      resourceRef:
        kind: Service
        name: ilb-service
    
  2. 将清单应用到您的集群:

    kubectl apply -f my-psc.yaml
    

删除 ServiceAttachment

您无法删除连接到服务连接的内部直通式网络负载均衡器。您必须单独删除服务连接和 GKE Service。

  1. 删除服务连接:

    kubectl delete serviceattachment SERVICE_ATTACHMENT_NAME --wait=false
    

    此命令将服务连接标记为删除,但资源仍然存在。您也可以通过省略 --wait 标志来等待删除完成。

  2. 删除 Service:

    kubectl delete svc SERVICE_NAME
    
  3. 删除子网:

    gcloud compute networks subnets delete SUBNET_NAME
    

ServiceAttachment 字段数

ServiceAttachment 具有以下字段:

  • connectionPreference:用于确定客户如何连接到服务的连接偏好设置。您可以使用 ACCEPT_AUTOMATIC 自动项目审批,也可以使用 ACCEPT_MANUAL 明确进行项目审批。如需了解详情,请参阅使用 Private Service Connect 发布服务
  • natSubnets:用于服务连接的子网资源名称列表。
  • proxyProtocol:如果设置为 true,则请求中提供使用方来源 IP 和 Private Service Connect 连接 ID。这是可选字段,如果未提供,则默认为 false。
  • consumerAllowList:允许连接到 ServiceAttachment 的使用方项目列表。仅当 connectionPreferenceACCEPT_MANUAL 时才能使用此字段。如需详细了解此字段,请参阅使用 Private Service Connect 发布服务
    • project:使用方项目的项目 ID 或编号。
    • connectionLimit:使用方项目的连接限制。此字段是可选字段。
    • forceSendFields:要发送以包含在 API 请求中的字段名称。此字段是可选字段。
    • nullFields:要包含在具有 null 值的 API 请求中的字段名称。此字段是可选字段。
  • consumerRejectList:不允许连接到 ServiceAttachment 的使用方项目 ID 或编号列表。仅当 connectionPreferenceACCEPT_MANUAL 时才能使用此字段。如需详细了解此字段,请参阅使用 Private Service Connect 发布服务
  • resourceRef:对 Kubernetes 资源的引用。

    • kind:Kubernetes 资源类型。您必须使用 Service
    • name:Kubernetes 资源的名称,该资源必须与内部直通式网络负载均衡器位于同一命名空间中。

问题排查

您可以使用以下命令查看错误消息:

kubectl get events -n NAMESPACE

NAMESPACE 替换为内部直通式网络负载均衡器的命名空间。

如果您尝试删除服务连接正在使用的内部直通式网络负载均衡器,则会出现如下所示的错误消息。您必须先删除 ServiceAttachment,然后才能删除内部直通式网络负载均衡器。

Error syncing load balancer: failed to ensure load balancer: googleapi:
Error 400: The forwarding_rule resource '<fwd-rule-URL>' is already being used
by '<svc-attachment-URL>', resourceInUseByAnotherResource.

后续步骤