Kubernetes - Ingress / Service / LB.

时间:2017-01-09 18:47:57

标签: node.js kubernetes google-compute-engine google-kubernetes-engine gitlab-ci

我是K8新手,这是我第一次尝试掌握它。我正在尝试使用此deployment.yml设置基本的Nodejs Express API:

apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: api
spec:
  replicas: 1
  template:
    metadata:
      labels:
        app: api
    spec:
      containers:
      - image: registry.gitlab.com/<project>/<app>:<TAG>
        imagePullPolicy: Always
        name: api
        env:
        - name: PORT
          value: "8080"
        ports:
          - containerPort: 8080
            hostPort: 80
        livenessProbe:
          httpGet:
            path: /healthz
            port: 8080
          initialDelaySeconds: 30
          timeoutSeconds: 1
        readinessProbe:
          httpGet:
            path: /healthz
            port: 8080
          initialDelaySeconds: 30
          timeoutSeconds: 1
      imagePullSecrets:
        - name: registry.gitlab.com

通过gitlab-ci部署。这是有效的,我已经设置了一个服务来公开它:

apiVersion: v1
kind: Service
metadata:
  name: api-svc
  labels:
    app: api-svc
spec:
  ports:
  - port: 80
    targetPort: 80
    protocol: TCP
    name: http
  selector:
    app: api
  type: LoadBalancer

但我一直在寻找入口,为可能的多个服务提供单一入口点。我一直在阅读Kubernetes指南,我读完了这个Kubernetes Ingress Example,这是我创建的ingress.yml:

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: ingress
spec:
  backend:
    serviceName: api-svc
    servicePort: 80

但是当我访问从入口生成的外部IP地址时,这不起作用,我只有502个错误页面。

有人能指出我正确的方向,我做错了什么或我错过了什么?我看到在上面的示例链接中有一个nginx-rc.yml,我在部署时完全像在示例中那样创建但是仍然没有从端点获得任何内容。可以通过服务外部IP访问API ..

非常感谢

3 个答案:

答案 0 :(得分:1)

我再次调查过,并认为我弄明白了。

为了使Ingress能够在GCE上工作,您需要将后端服务das NodePort定义为不是ClusterIP或LoadBalancer。

此外,您需要确保/的http运行状况检查有效(您将看到Google L7 Loadbalancer在该网址上大量使用您的服务),然后就可以使用了。

答案 1 :(得分:1)

以为我会发布我的工作部署/服务/入口

因此,经过多次努力才能实现这一目标,以下是我过去的工作原理:

<强>部署

apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: backend-api-v2
spec:
  replicas: 2
  template:
    metadata:
      labels:
        app: backend-api-v2
    spec:
      containers:
      - image: registry.gitlab.com/<project>/<app>:<TAG>
        imagePullPolicy: Always
        name: backend-api-v2
        env:
        - name: PORT
          value: "8080"
        ports:
          - containerPort: 8080
        livenessProbe:
          httpGet:
            # Path to probe; should be cheap, but representative of typical behavior
            path: /healthz
            port: 8080
          initialDelaySeconds: 30
          timeoutSeconds: 5
        readinessProbe:
          httpGet:
            path: /healthz
            port: 8080
          initialDelaySeconds: 30
          timeoutSeconds: 5
      imagePullSecrets:
        - name: registry.gitlab.com

<强>服务

apiVersion: v1
kind: Service
metadata:
  name: api-svc-v2
  labels:
    app: api-svc-v2
spec:
  type: NodePort
  ports:
  - port: 80
    targetPort: 8080
    nodePort: 31810
    protocol: TCP
    name: http
  selector:
    app: backend-api-v2

<强>入口

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: app-ingress
spec:
  rules:
  - host: api.foo.com
    http:
      paths:
      - path: /v1/*
        backend:
          serviceName: api-svc
          servicePort: 80
      - path: /v2/*
        backend:
          serviceName: api-svc-v2
          servicePort: 80

@Tigraine指出的重要事项是服务正在使用type: NodePort而不是LoadBalancer,我还定义了一个nodePort,但我相信如果你把它留出来它会创建一个。

对于不符合规则的任何路由,它将使用default-http-backend这是GKE在kube-system命名空间中运行的默认容器。因此,如果我访问http://api.foo.com/bob,我会得到default backend - 404的默认回复。

希望这有帮助

答案 2 :(得分:0)

您似乎将服务暴露给端口80,但您的容器正在公开8080,因此对服务的任何请求都将失败。

另外,看一下示例入口资源(https://github.com/nginxinc/kubernetes-ingress/blob/master/examples/complete-example/cafe-ingress.yaml),您还需要定义入口控制器被命中时路由的主机/路径。 (即example.foo.com - &gt; api-svc)