GKE Ingress:公网 HTTPS 与后端健康

验证:未记录
适用版本
未记录
验证范围
尚未登记验证记录。

本页为 GKE 托管 gce Ingress,使用 classic external ALB。

推荐做法#

  • 通过 Kubernetes 清单管理 Ingress / Service / BackendConfig,避免 Console 手改控制器资源。
  • Pod 使用 Zonal NEG;readiness 与 LB health check 分别配置并验证。
  • 保留静态 IP,确认 DNS 后绑定证书;删除入口时保持集群运行直到云资源回收。

常用操作#

替换为实际资源;本段不依赖 lab.env。

NAMESPACE='REPLACE_NAMESPACE'
INGRESS='REPLACE_INGRESS'

kubectl config current-context
kubectl -n "$NAMESPACE" describe ingress "$INGRESS"
kubectl -n "$NAMESPACE" get services,endpointslices,pods
kubectl -n "$NAMESPACE" get events --sort-by=.metadata.creationTimestamp

容易踩的坑#

  • ADDRESS 出现不证明后端健康;502/503 查 NEG、health check、selector、端口与 firewall。

GKE Zonal NEG 与 Cloud Run Serverless NEG 的健康检查规则不同。 本页 GKE 后端需要 health check;不要因 Cloud Run 不配置 VM health check,就省略 GKE 的检查和 firewall。

资源关系 · HTTPS 配置

配置说明与完整示例(按需展开)

前置:Autopilot 入门或 Standard 集群,先读 GKE 网络。本篇是可复制的独立 hello 实验,使用 GKE 托管 Ingress 控制器;只做本地清单与文档验证,未执行云端部署。

本篇使用哪一种入口#

Ingress是描述 HTTP(S) 域名与路径路由的 Kubernetes 对象;Ingress controller 读取这些对象,创建和维护实际负载均衡资源。GKE 自带托管控制器,不需要为本例安装 ingress-nginx 或 Envoy Gateway。

本例使用 kubernetes.io/ingress.class: gce 创建 classic external Application Load Balancer。这是 GKE 托管 Ingress 的外部模式,与 Cloud Run ALB 实验手工创建的全局 EXTERNAL_MANAGED 模式不同。若需要其他 ALB 模式或 Gateway API,另按 GKE GatewayClass 的支持情况设计,不能把通用 Envoy Gateway 清单当作 GKE 托管 Gateway。GKE Ingress 官方说明

公网用户
  → ALB 公网 IP:80 / 域名:443
  → GKE 控制器创建的 URL map、Backend service
  → Zonal NEG(Pod IP:80)
  → nginx Pod

Ingress 清单引用 Kubernetes Service;在本例 NEG 模式下,实际负载均衡数据流直接到 Pod endpoint,不必先绕到 Service ClusterIP 或 NodePort。

1. 核对集群与执行位置#

kubectl 在能连接控制面的机器执行: DNS-based endpoint 可从获授权且网络可达的本机使用;仅内部 IP 的 Standard 示例在私网管理机上执行。gcloud 创建公网地址只需相应云 API 权限,不要求连到 Kubernetes 内部 endpoint。

PROJECT_ID=REPLACE_PROJECT_ID
CLUSTER=REPLACE_CLUSTER
REGION=REPLACE_REGION

gcloud config set project "$PROJECT_ID"
gcloud container clusters describe "$CLUSTER" \
  --project="$PROJECT_ID" --region="$REGION" \
  --format='yaml(name,location,network,ipAllocationPolicy,addonsConfig.httpLoadBalancing)'
kubectl config current-context
kubectl get nodes

确认 kubectl context 与目标集群一致;若不一致,按 集群访问重新获取凭据。本例要求 VPC-native 网络、HttpLoadBalancing add-on 未被禁用;Autopilot 空集群可等业务 Pod 触发节点供应。Shared VPC 还需核对服务项目的控制器权限及宿主项目防火墙管理权限。

2. 准备应用、Service 与健康检查#

保存为 gke-ingress-app.yaml。只部署 nginx 欢迎页,不包含数据库或敏感业务。

apiVersion: v1
kind: Namespace
metadata:
  name: gke-ingress-lab
---
apiVersion: cloud.google.com/v1
kind: BackendConfig
metadata:
  name: web-backend
  namespace: gke-ingress-lab
spec:
  healthCheck:
    type: HTTP
    requestPath: /
    port: 80
---
apiVersion: v1
kind: Service
metadata:
  name: web
  namespace: gke-ingress-lab
  annotations:
    cloud.google.com/neg: '{"ingress": true}'
    cloud.google.com/backend-config: '{"ports": {"80": "web-backend"}}'
spec:
  type: ClusterIP
  selector:
    app: gke-web
  ports:
    - name: http
      port: 80
      targetPort: 80
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: web
  namespace: gke-ingress-lab
spec:
  replicas: 2
  selector:
    matchLabels:
      app: gke-web
  template:
    metadata:
      labels:
        app: gke-web
    spec:
      containers:
        - name: nginx
          image: nginx:stable
          ports:
            - containerPort: 80
          resources:
            requests:
              cpu: 250m
              memory: 512Mi
            limits:
              cpu: 500m
              memory: 512Mi
          readinessProbe:
            httpGet:
              path: /
              port: 80
            initialDelaySeconds: 3
            periodSeconds: 5
配置 作用与原因
replicas: 2 维护两个应用副本;不自动保证跨 Zone,需要时另配拓扑约束
selector: app: gke-web Service 通过标签发现 Deployment 创建的 Pod
port / targetPort Ingress 引用的 Service 端口 / 应用实际监听端口,本例都是 80
cloud.google.com/neg 明确启用容器原生负载均衡,控制器管理各 Zone 的 Pod endpoint 组
BackendConfig GKE 的扩展资源,用来配置云端 Backend service;本例明确指定 LB 健康检查路径与 Pod 端口
readinessProbe kubelet 检查 Pod 内应用是否就绪,与云端健康检查是两项检查

生产镜像应固定审核过的版本或 digest。本例 nginx:stable 只为合成页面实验。相比 Cloud Run 的 Serverless NEG,GKE 的 Pod NEG 使用实际 IP/端口,需要正确的云端健康检查。BackendConfig 配置

kubectl apply -f gke-ingress-app.yaml

继续创建 Ingress,再一起等待就绪。NEG readiness gate 会把负载均衡后端健康状态纳入 Pod Ready 判断;入口尚未建好时,不要只因 Pod 未完全 Ready 就反复重建。

3. 创建公网 IP 和 Ingress#

先保留一个全局静态公网地址,让后续证书和域名指向稳定入口:

gcloud compute addresses create gke-web-ip \
  --project="$PROJECT_ID" --global

保存为 gke-ingress.yaml:

apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: web
  namespace: gke-ingress-lab
  annotations:
    kubernetes.io/ingress.class: gce
    kubernetes.io/ingress.global-static-ip-name: gke-web-ip
spec:
  defaultBackend:
    service:
      name: web
      port:
        number: 80

gce 告诉 GKE 控制器创建外部入口;本控制器仍使用这个 annotation,不能仅替换成 spec.ingressClassName。defaultBackend 将请求交给 web Service 的 80 端口;后续按需添加 Host/path 规则。本例 Service 不用 LoadBalancer 类型,避免再创建一套 L4 入口。

kubectl apply -f gke-ingress.yaml
kubectl -n gke-ingress-lab get ingress web -w

等待 ADDRESS 出现后用 Ctrl+C 停止观察。控制器供应 LB 和健康检查可能需要数分钟,地址出现也不代表后端立刻健康。

4. 验证完整公网链路#

kubectl -n gke-ingress-lab rollout status deployment/web --timeout=900s
kubectl -n gke-ingress-lab get pods -o wide
kubectl -n gke-ingress-lab get endpointslices \
  -l kubernetes.io/service-name=web
kubectl -n gke-ingress-lab describe ingress web
export GKE_LB_IP=$(gcloud compute addresses describe gke-web-ip \
  --project="$PROJECT_ID" --global --format='value(address)')
curl --fail "http://$GKE_LB_IP/"

预期公网请求返回 nginx 欢迎页;这与 port-forward 测试不同,实际经过 ALB 和 NEG。控制台 Network services → Load balancing 可查看 GKE 创建的资源和后端健康状态;Ingress 注解、事件及 Service 的 cloud.google.com/neg-status 能帮助定位生成资源。

GKE 通常自动管理相应健康检查和 GFE 来源防火墙规则。Shared VPC、组织防火墙或 NetworkPolicy 可能另行阻断路径;遇到 502/503 先查后端健康、Service selector、应用监听和策略。不要把 Cloud Run 的“无需 VM 健康检查”套用到这里。

5. 添加域名与 HTTPS#

先将自有主机名,例如 web.example.com,的 DNS A 记录指向 GKE_LB_IP。确认没有把同一域名的 AAAA 记录留在错误入口。保存以下文件为 gke-managed-certificate.yaml,将示例域名替换为你控制的真实域名:

apiVersion: networking.gke.io/v1
kind: ManagedCertificate
metadata:
  name: web-cert
  namespace: gke-ingress-lab
spec:
  domains:
    - web.example.com

ManagedCertificate 是 GKE 用于申请并管理 Google-managed certificate的资源。本例不需要把私钥放进 Kubernetes Secret;它也不是前面 Certificate Manager certificate map 的同一种资源。

在 gke-ingress.yaml 的 annotations 中增加:

networking.gke.io/managed-certificates: web-cert

保留已有 class 和静态 IP 注解,再应用:

kubectl apply -f gke-managed-certificate.yaml
kubectl apply -f gke-ingress.yaml
kubectl -n gke-ingress-lab describe managedcertificate web-cert

等证书状态 Active,再以真实域名访问 https://web.example.com/。证书签发可能明显慢于 Pod 启动;检查 DNS、CAA、Ingress 绑定和事件。这里仍保留 HTTP,创建 HTTPS 不会自动将 HTTP 重定向到 HTTPS;需要跳转时另按 FrontendConfig 配置。Google-managed certificate、入口配置

6. 配置应该改在哪里#

路由、TLS、健康检查等修改分别写入 Ingress、ManagedCertificate、BackendConfig 和 Service 清单。不要在 Google Cloud 控制台手工改 GKE 生成的 Backend service 或 URL map,否则控制器可能覆盖修改。若需要全手工控制,使用独立 NEG 架构并自行承担资源生命周期管理。

本例公网 IP + gce 外部入口不需要 Proxy-only subnet。内部 Ingress 的 gce-internal 使用不同网络条件,需要代理 subnet,不能只改一个注解就假定其他配置都适用。

7. 清理#

先删除 Ingress,让控制器清理其管理的入口,再删除实验 namespace 和专用静态 IP。保持集群运行直到控制器完成清理,不要先删集群再等它回收资源。

kubectl -n gke-ingress-lab delete ingress web
kubectl -n gke-ingress-lab get ingress

在 Load balancing 控制台确认本 Ingress 的 forwarding rules、target proxies、URL map、backend services 等已被回收。删除 Kubernetes 对象的返回值不保证所有云端异步清理已完成。然后执行:

kubectl delete namespace gke-ingress-lab
gcloud compute addresses delete gke-web-ip \
  --project="$PROJECT_ID" --global

若 IP 仍被使用,查清该实例生成的引用并等待/处理控制器事件,不强制删除其他服务资源。确认本例 NEG 与证书已回收,删除本次专用 DNS 记录。仅删除实验 namespace,不删除其他业务或共享网络。Ingress 排障

搜索文档

输入关键词,搜索所有文档。

↑ ↓ 选择 · Enter 打开 · Esc 关闭