Kubernetes 不健康的 Ingress 后端。

41
我按照负载均衡器教程:https://cloud.google.com/container-engine/docs/tutorials/http-balancer 进行了操作,当我使用 Nginx 镜像时一切正常,但是当我尝试使用自己的应用程序镜像时,后端变得不健康了。
我的应用程序在 / 上进行重定向(返回 302),但我在 Pod 定义中添加了一个 livenessProbe
    livenessProbe:
      httpGet:
        path: /ping
        port: 4001
        httpHeaders:
          - name: X-health-check
            value: kubernetes-healthcheck
          - name: X-Forwarded-Proto
            value: https
          - name: Host
            value: foo.bar.com

我的入口看起来像:

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: foo
spec:
  backend:
    serviceName: foo
    servicePort: 80
  rules:
  - host: foo.bar.com

服务配置为:

kind: Service
apiVersion: v1
metadata:
  name: foo
spec:
  type: NodePort
  selector:
    app: foo
  ports:
    - port: 80 
      targetPort: 4001

ingress describe ing 中,后端的健康状况如下:

backends:       {"k8s-be-32180--5117658971cfc555":"UNHEALTHY"}

并且进入规则看起来像:

Rules:
  Host  Path    Backends
  ----  ----    --------
  * *   foo:80 (10.0.0.7:4001,10.0.1.6:4001)
任何指针都将不胜感激,我已经试图解决这个问题几个小时了,但没有成功。 更新 我已经将readinessProbe添加到我的部署中,但似乎仍然会命中/,并且入口仍然不健康。我的探针如下:
    readinessProbe:
      httpGet:
        path: /ping
        port: 4001
        httpHeaders:
          - name: X-health-check
            value: kubernetes-healthcheck
          - name: X-Forwarded-Proto
            value: https
          - name: Host
            value: foo.com

我把我的服务改成了:

kind: Service
apiVersion: v1
metadata:
  name: foo
spec:
  type: NodePort
  selector:
    app: foo
  ports:
    - port: 4001
      targetPort: 4001

更新2

在我从readinessProbe中移除自定义头部后,它开始工作了!非常感谢。

6个回答

61
你需要添加一个 readinessProbe(只需复制你的 livenessProbe)。
GCE L7 Ingress Docs中有解释。

健康检查

目前,所有服务后端必须满足以下任一要求才能通过从 GCE 负载均衡器发送到它的 HTTP 健康检查:1. 在 '/' 上响应 200。内容无关紧要。2. 将任意 URL 公开为支持 Service 的 pod 的 readiness 探针。

此外,请确保 readinessProbe 指向与您公开给 Ingress 的端口相同的端口。在您的情况下,这很好,因为您只有一个端口,如果添加另一个端口,可能会遇到问题。

我遇到了同样的问题,你的答案以及这里的答案:https://dev59.com/wVgQ5IYBdhLWcg3wUSO3#42971328 帮助我解决了这个问题。 - GrandVizier
我曾经遇到过同样的问题,你的答案以及这篇文章:https://medium.com/google-cloud/kubernetes-liveness-checks-4e73c631661f 对我非常有帮助。 - shalitha senanayaka

12

我认为值得注意的是,文档中存在一个相当重要的限制:

更改Pod的就绪探针不会影响创建后的Ingress。

添加了我的就绪探针后,我基本上删除了我的Ingress (kubectl delete ingress <name>),然后再次应用了我的yaml文件来重新创建它,在短时间内一切都正常运行。


在GKE上,我没有删除Ingress,而是删除并重新添加了特定的主机规则。效果非常好。 - Akash Agarwal

6

我曾经遇到了同样的问题。跟随Tex的提示,但仍然看到了那个信息。后来发现我需要等待几分钟才能进入验证服务健康状况的阶段。如果有人正在经历相同的情况,并且已经完成了所有步骤,例如readinessProbelinvenessProbe,只需确保您的ingress指向的是一个 NodePort 服务,并等待几分钟直到黄色警告图标变为绿色。另外,请检查 StackDriver 上的日志以更好地了解发生了什么。


4

我也遇到了完全相同的问题,这是在更新我的Ingress readinessProbe后发生的。

我可以看到Ingress状态标记为某些后端服务处于未知状态,状态以黄色显示。 我等待了超过30分钟,但更改没有反映。

超过24小时后,更改得以反映,状态变为绿色。 我没有找到官方文档来解决此问题,但似乎这是GCP Ingress资源中的一个错误。


4
如果您不想更改您的 pod spec,或者依赖于 GKE 自动拉取 readinessProbe 的魔力,您还可以像这样配置 BackendConfig 来明确地配置健康检查。
如果您想要为 readinessProbe 使用脚本,但它不受 GKE ingress 健康检查支持,那么这也很有用。
请注意,BackendConfig 需要在 Service 定义中明确引用。
---
apiVersion: v1
kind: Service
metadata:
  name: my-service
  namespace: my-namespace
  annotations:
    cloud.google.com/neg: '{"ingress":true}'
    # This points GKE Ingress to the BackendConfig below
    cloud.google.com/backend-config: '{"default": "my-backendconfig"}'
spec:
  type: ClusterIP
  ports:
    - name: health
      port: 1234
      protocol: TCP
      targetPort: 1234
    - name: http
      ...
  selector:
    ...
---
apiVersion: cloud.google.com/v1
kind: BackendConfig
metadata:
  name: my-backendconfig
  namespace: my-namespace
spec:
  healthCheck:
    checkIntervalSec: 15
    port: 1234
    type: HTTP
    requestPath: /healthz

1

所有这些答案都对我很有帮助。

此外,http探测需要返回200状态。可笑的是,我的返回了301状态。因此,我只需添加一个简单的“ping”端点,一切就恢复正常/健康了。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接