无法访问 Kubernetes 负载均衡器

Kubenetes Load Balancer is not accessible

我正在尝试在 AWS EKS 集群中托管以下 (deployment frontend) Kubernetes 部署,在部署部署并创建服务和入口后,一切都已成功部署和创建,但是当我尝试从外部访问 Load Balancer DNS 时,无法访问此 LoadBalancer。 有人能指出原因吗?

**下面的代码 (deployment-2048) 正在运行并且负载均衡器可以访问,但在(部署前端)** 的情况下不能访问。

apiVersion: apps/v1
kind: Deployment
metadata:
  annotations:
    deployment.kubernetes.io/revision: "1"
  creationTimestamp: "2021-03-09T14:08:45Z"
  generation: 2
  name: frontend
  namespace: default
  resourceVersion: "2864"
  uid: a7682f3b-dffa-498f-be47-b231cce0720a
spec:
  minReadySeconds: 20
  progressDeadlineSeconds: 600
  replicas: 4
  revisionHistoryLimit: 10
  selector:
    matchLabels:
      name: webapp
  strategy:
    rollingUpdate:
      maxSurge: 25%
      maxUnavailable: 25%
    type: RollingUpdate
  template:
    metadata:
      creationTimestamp: null
      labels:
        name: webapp
    spec:
      containers:
      - image: kodekloud/webapp-color:v2
        imagePullPolicy: IfNotPresent
        name: simple-webapp
        ports:
        - containerPort: 80
          protocol: TCP
        resources: {}
        terminationMessagePath: /dev/termination-log
        terminationMessagePolicy: File
      dnsPolicy: ClusterFirst
      restartPolicy: Always
      schedulerName: default-scheduler
      securityContext: {}
      terminationGracePeriodSeconds: 30
status:
  availableReplicas: 4
  observedGeneration: 2
  readyReplicas: 4
  replicas: 4
  updatedReplicas: 4

---
apiVersion: v1
kind: Service
metadata:
  namespace: default
  name: service-1
spec:
  ports:
    - port: 80
      targetPort: 80
      protocol: TCP
  type: LoadBalancer
  selector:
    name: webapp
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  namespace: default
  name: ingress-1
  annotations:
    kubernetes.io/ingress.class: alb
    alb.ingress.kubernetes.io/scheme: internet-facing
    alb.ingress.kubernetes.io/target-type: ip
spec:
  rules:
    - http:
        paths:
          - path: /*
            backend:
              serviceName: service-1
              servicePort: 80

---
apiVersion: v1
kind: Namespace
metadata:
  name: game-2048
---
apiVersion: apps/v1
kind: Deployment
metadata:
  namespace: game-2048
  name: deployment-2048
spec:
  selector:
    matchLabels:
      app.kubernetes.io/name: app-2048
  replicas: 5
  template:
    metadata:
      labels:
        app.kubernetes.io/name: app-2048
    spec:
      containers:
      - image: alexwhen/docker-2048
        imagePullPolicy: Always
        name: app-2048
        ports:
        - containerPort: 80
---
apiVersion: v1
kind: Service
metadata:
  namespace: game-2048
  name: service-2048
spec:
  ports:
    - port: 80
      targetPort: 80
      protocol: TCP
  type: LoadBalancer
  selector:
    app.kubernetes.io/name: app-2048
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  namespace: game-2048
  name: ingress-2048
  annotations:
    kubernetes.io/ingress.class: alb
    alb.ingress.kubernetes.io/scheme: internet-facing
    alb.ingress.kubernetes.io/target-type: ip
spec:
  rules:
    - http:
        paths:
          - path: /*
            backend:
              serviceName: service-2048
              servicePort: 80

容器端口设置为 8080,服务目标端口为 80

在您的原始问题中(没有编辑和其他信息),在 frontend 部署中您有 port 个值配置错误。

  • Port 在集群内的指定端口上公开 Kubernetes 服务。集群中的其他 pods 可以通过指定端口与此服务器通信。
  • TargetPort 是服务将请求发送到的端口,您的 pod 将监听该端口。您在容器中的应用程序也需要侦听此端口。
  • ContainerPort 定义应用程序可以在容器内到达的端口。

简而言之,来自部署的 containerPort 必须与 Service 中的 targetPort 具有相同的值。

用户@herbertgoto 有一个好主意,但不幸的是没有具体说明应该做什么。当您将 containerPort8080 更改为 80 它应该可以工作,但我猜想在所有资源中重新填充此更改存在问题(重新创建入口资源,重新部署 pod)。

第一个故障排除步骤应该是检查您的容器是否在正确的端口上侦听。这就是为什么我要求 $ netstat 输出。

有用的检查命令是使用 $ kubectl get ep 检查服务端点。

备注

如果你将在服务中跳过 targetPort 而只有 port,Kubernetes 会根据 port.

自动分配 targetPort

When i kept only containerPort and TargetPort to 8080. and the others to 80. Why it worked like this.

服务的默认端口端口是80。所以当你用80端口创建service时,你不需要指定任何额外的东西。当你将service中的port设置为8080时,你还需要指定它。

我已经创建了端口 8080 没有我的 GKE 集群的服务。

$ kubectl get svc
NAME         TYPE           CLUSTER-IP      EXTERNAL-IP     PORT(S)          AGE
kubernetes   ClusterIP      10.104.0.1      <none>          443/TCP          153m
my-nginx     LoadBalancer   10.104.14.137   34.91.230.207   8080:31311/TCP   9m39s
$ curl 34.91.230.207
curl: (7) Failed to connect to 34.91.230.207 port 80: Connection timed out
$ curl 34.91.230.207:8080
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
    body {
...

来自浏览器的响应:

只有外部IP 外部IP:8080 如您所见,当我不使用默认 80 端口时,我需要在浏览器和 curl 命令中指定端口 8080

结论:

部署 containerPort 和服务 targetPort 必须具有相同的值。当您使用 port 不同于 80 的服务时,您需要通过添加 :<portNubmer> 来指定它。这就是为什么在互联网的几乎所有指南中,您都可以看到服务 port 的值为 80.