简体   繁体   中英

Kubernetes: Route incoming traffic to specific Pod

I want to deploy many Pods in Google Kubernetes Engine and then establish a TCP connection to each specific Pod by Subdomain like pod-name-or-label.mydomain.com or path routing like protocol://mydomain.com:7878/pod-name-or-label.

I have looked in different directions like Istio or nginx-ingress, but that seems to me to be too complicated.

Is not there a simple solution for that?

For Istio , You can use VirtualService to control the routing rules to the target subset with defining by DestinationRules .

The DestinationRule will route to the target Pods by the specified label pods.

The request flow will like to:

+--------------------+
|                    |
|    Istio Gateway   |
|                    |
|                    |
+---------+----------+
          |traffic incoming
          |
+---------v----------+
|                    |
|   VirtualService   |
|                    |
|                    |
+---------+----------+
          |route to subset by the routing rules
          v

+--------------------+
|                    |
|  DestinationRules  |
|                    |
|                    |
+---------+----------+
          |route traffic to target pods
          v

+--------------------+
|                    |
|                    |
|       Pods         |
|                    |
+--------------------+

so as @ericstaples said you should create different Deployments with different pod labels to achieve separating traffic to the target pods , Example:

  1. create a deployment with pod label: t1
  2. create a subset in DestinationRule : select t1 label pod as subset s1
  3. control your traffic in VirtualService that route to s1 subset
  4. s1 route to the target pods

also for expose Gateway , you can use ClusterIP or NodePort like ** Kubernetes** other service did, see more of Istio Traffic .

There are some references maybe it's helpful:

https://istio.io/docs/concepts/traffic-management/

https://istio.io/docs/tasks/traffic-management/request-routing/

This question is bit old, but in current Kubernetes versions you can do it easly using Nginx Ingress .

If you want to reach your application from outside the cluster you need to expose it using Services . Easiest way is to use Service with selectors when you put the same selector in Deployment/Pod and Service . Example below:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: test1
spec:
  replicas: 1
  selector:
    matchLabels:
      key: test1
  template:
    metadata:
      labels:
        key: test1
    spec:
      containers:
      - name: hello1
        image: gcr.io/google-samples/hello-app:1.0
        imagePullPolicy: IfNotPresent
        ports:
        - containerPort: 8080
---
apiVersion: v1
kind: Service
metadata:
  name: test1
spec:
  selector:
    key: test1
  ports:
    - port: 80
      targetPort: 8080

Path routing will be configured in Ingress . As on the example below:

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: ingress
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /
spec:
  rules:
  - host: my.pod.svc 
    http:
      paths:
      - path: /pod
        backend:
          serviceName: my-pod
          servicePort: 80
  - host: nginx.test.svc
    http:
      paths:
      - path: /abc
        backend:
          serviceName: nginx1
          servicePort: 80

For more details you can check this thread .

Now i have that solution with istio installed on the cluster:

apiVersion: networking.istio.io/v1alpha3
kind: Gateway
metadata:
  name: echo-gateway
spec:
  selector:
    istio: ingressgateway # use istio default controller
  servers:
  - port:
      number: 80
      name: http
      protocol: HTTP
    hosts:
    - "dev.sample.com"

With that gateway i can apply that Deployment, Service, VirtualService

apiVersion: apps/v1
kind: Deployment
metadata:
  name: my-echo-1000-deployment
  labels:
    echoservice: echo-1000
spec:
  replicas: 1
  selector:
    matchLabels:
      echoservice: echo-1000
  template:
    metadata:
      labels:
        echoservice: echo-1000
    spec:
      containers:
      - image: gcr.io/google-containers/echoserver:1.10
        imagePullPolicy: IfNotPresent
        name: my-echo-run-container
        ports:
        - containerPort: 8080
          protocol: TCP

---

apiVersion: v1
kind: Service
metadata:
  name: my-echo-1000-service
  labels:
    echoservice: echo-1000
spec:
  ports:
  - port: 8080
    name: http
  selector:
    echoservice: echo-1000

---

apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
  name: my-echo-1000-vservice
spec:
  hosts:
  - "dev.sample.com"
  gateways:
  - echo-gateway
  http:
  - match:
    - uri:
        exact: /echo-1000
    route:
    - destination:
        host: my-echo-1000-service
        port:
          number: 8080

Get the LoadbalancerIP from istio-ingressgateway and make an entry in /etc/hosts for dev.sample.com

Now i can get the echoserver in specific Pod with http://dev.sample.com/echo-1000

Is that a good solution or is there a better one?

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM