首页 文章

istio:使用grpc和http进入

提问于
浏览
4

我有一个服务监听两个端口;一个是http,另一个是grpc . 我想设置一个入口,可以使用相同的主机路由到这两个端口 .

如果使用http / 1.1,负载均衡器将重定向到http端口,如果使用h2,则重定向到grpc端口 .

有没有办法用istio做到这一点?

我做了一个问候世界,展示了我想要实现的目标:

apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: hello-world
  namespace: dev
spec:
  replicas: 1
  template:
    metadata:
      annotations:
        alpha.istio.io/sidecar: injected
        pod.beta.kubernetes.io/init-containers: '[{"args":["-p","15001","-u","1337","-i","172.20.0.0/16"],"image":"docker.io/istio/init:0.1","imagePullPolicy":"Always","name":"init","securityContext":{"capabilities":{"add":["NET_ADMIN"]}}}]'
      labels:
        app: hello-world
    spec:
      containers:
      - name: grpc-server
        image: aguilbau/hello-world-grpc:latest
        ports:
        - name: grpc
          containerPort: 50051
      - name: http-server
        image: nginx:1.7.9
        ports:
        - name: http
          containerPort: 80
      - name: istio-proxy
        args:
        - proxy
        - sidecar
        - -v
        - "2"
        env:
        - name: POD_NAME
          valueFrom:
            fieldRef:
              fieldPath: metadata.name
        - name: POD_NAMESPACE
          valueFrom:
            fieldRef:
              fieldPath: metadata.namespace
        - name: POD_IP
          valueFrom:
            fieldRef:
              fieldPath: status.podIP
        image: docker.io/istio/proxy:0.1
        imagePullPolicy: Always
        resources: {}
        securityContext:
          runAsUser: 1337
---
apiVersion: v1
kind: Service
metadata:
  name: hello-world
  namespace: dev
spec:
  ports:
  - name: grpc
    port: 50051
  - name: http
    port: 80
  selector:
    app: hello-world
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: hello-world-http
  namespace: dev
  annotations:
    kubernetes.io/ingress.class: "istio"
spec:
  rules:
  - host: hello-world
    http:
      paths:
      - backend:
          serviceName: hello-world
          servicePort: 80
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: hello-world-grpc
  namespace: dev
  annotations:
    kubernetes.io/ingress.class: "istio"
spec:
  rules:
  - host: hello-world
    http:
      paths:
      - backend:
          serviceName: hello-world
          servicePort: 50051
---

2 回答

  • 1

    如果将 grpc-serverhttp-server 容器移动到具有唯一标签的不同容器(即,服务的不同版本,可以这么说),然后在Ingress后面使用Istio路由规则,则可以执行类似的操作 . . 标头 Upgrade: h2 匹配的规则可以将流量发送到grpc版本,默认规则会将其余流量发送到http 1 .

  • 1

    我参加派对有点晚了,但对于那些在这篇文章中磕磕绊绊的人,我认为你可以毫不费力地做到这一点 . 我假设你已经在kubernetes集群上安装了istio,并且很高兴使用默认的istio-ingressgateway:

    apiVersion: extensions/v1beta1
    kind: Deployment
    metadata:
      name: hello-world
      namespace: dev
    spec:
      replicas: 1
      template:
        metadata:
          annotations:
            alpha.istio.io/sidecar: injected
            pod.beta.kubernetes.io/init-containers: '[{"args":["-p","15001","-u","1337","-i","172.20.0.0/16"],"image":"docker.io/istio/init:0.1","imagePullPolicy":"Always","name":"init","securityContext":{"capabilities":{"add":["NET_ADMIN"]}}}]'
          labels:
            app: hello-world
        spec:
          containers:
          - name: grpc-server
            image: aguilbau/hello-world-grpc:latest
            ports:
            - name: grpc
              containerPort: 50051
          - name: http-server
            image: nginx:1.7.9
            ports:
            - name: http
              containerPort: 80
          - name: istio-proxy
            args:
            - proxy
            - sidecar
            - -v
            - "2"
            env:
            - name: POD_NAME
              valueFrom:
                fieldRef:
                  fieldPath: metadata.name
            - name: POD_NAMESPACE
              valueFrom:
                fieldRef:
                  fieldPath: metadata.namespace
            - name: POD_IP
              valueFrom:
                fieldRef:
                  fieldPath: status.podIP
            image: docker.io/istio/proxy:0.1
            imagePullPolicy: Always
            resources: {}
            securityContext:
              runAsUser: 1337
    
    ---
    
    apiVersion: v1
    kind: Service
    metadata:
      name: hello-world
      namespace: dev
    spec:
      ports:
      - name: grpc
        port: 50051
      - name: http
        port: 80
      selector:
        app: hello-world
    
    ---
    
    apiVersion: networking.istio.io/v1alpha3
    kind: Gateway
    metadata:
      name: hello-world-istio-gate
      namespace: dev
    spec:
      selector:
        istio: ingressgateway
      servers:
      - port:
          number: 80
          name: http
          protocol: HTTP
        hosts:
        - "*"
      - port:
          number: 50051
          name: grpc
          protocol: GRPC
        hosts:
        - "*"
    
    ---
    
    apiVersion: networking.istio.io/v1alpha3
    kind: VirtualService
    metadata:
      name: hello-world-istio-vsvc
      namespace: dev
    spec:
      hosts:
      - "*"
      gateways:
      - hello-world-istio-gate
      http:
      - match:
        - port: 80
        route:
        - destination:
            host: hello-world
            port:
              number: 80
      tcp:
      - match:
        - port: 50051
        route:
        - destination:
            host: hello-world
            port:
              number: 50051
    

    上面的配置省略了你的两个Ingresses,而是包括:

    • 您的部署

    • 您的服务

    • istio网关

    • istio虚拟服务

    有一个重要的额外部分没有显示,我在前面谈到使用默认的ingressgateway时提到了它 . “hello-world-istio-gateway”中的以下行给出了一个线索:

    istio: ingressgateway
    

    这是指'istio-system'命名空间中的一个pod,它通常默认安装,名为'istio-ingressgateway' - 该pod由一个名为'istio-ingressgateway.' You will need to open up ports on the 'istio-ingressgateway' service. 的服务公开

    例如,我编辑了我的(默认)ingressgateway并为HTTP和GRPC添加了一个端口 . 结果如下(编辑长度)yaml代码:

    dampersand@kubetest1:~/k8s$ kubectl get service istio-ingressgateway -n istio-system -o yaml
    apiVersion: v1
    kind: Service
    metadata:
    
    <omitted for length>
    
      labels:
        app: istio-ingressgateway
        chart: gateways-1.0.3
        heritage: Tiller
        istio: ingressgateway
        release: istio
      name: istio-ingressgateway
      namespace: istio-system
    
      <omitted for length>
    
      ports:
      - name: http2
        nodePort: 31380
        port: 80
        protocol: TCP
        targetPort: 80
    
      <omitted for length>
    
      - name: grpc
        nodePort: 30000
        port: 50051
        protocol: TCP
        targetPort: 50051
      selector:
        app: istio-ingressgateway
        istio: ingressgateway
      type: NodePort
    

    进行上述更改(用于测试目的)的最简单方法是使用:

    kubectl edit svc -n istio-system istio-ingressgateway
    

    出于 生产环境 目的,最好编辑您的头盔图或istio.yaml文件或您最初用于设置ingressgateway的任何内容 .

    暂时不要注意,我的测试集群将istio-ingressgateway设置为NodePort,所以上面的yaml文件说的是我的集群是端口转发31380 - > 80和30000 - > 50051.你可能(可能)有istio-ingressgateway设置为LoadBalancer,它将是不同的...所以计划相应 .

    最后,以下博客文章是我在本文中概述的工具的一些非常优秀的背景阅读! https://blog.jayway.com/2018/10/22/understanding-istio-ingress-gateway-in-kubernetes/

相关问题