【问题标题】:How to use Istio Virtual Service in-between front and back services如何在前后端服务之间使用 Istio 虚拟服务
【发布时间】:2020-06-05 14:34:55
【问题描述】:

我对 Istio 完全陌生,而且推介看起来非常令人兴奋。但是,我不能让它工作,这可能意味着我没有正确使用它。 我的目标是在 2 个服务之间实现会话关联,这就是我最初最终使用 Istio 的原因。但是,我做了一个非常基本的测试,它似乎不起作用: 我有一个 Kubernetes 演示应用程序,它作为前端服务、有状态服务和无状态服务。在浏览器中,我使用 K8s 服务名称作为 url:http://api-statefulhttp://api-stateless,访问在有状态或无状态服务上调度请求的前端服务。

我想声明一个虚拟服务来拦截从前端服务发送到有状态服务的请求。我没有将它声明为网关,因为我理解网关在 K8s 集群的外部边界。 我在带有 Istio 1.6 的 Windows 上使用 Docker。

我在下面复制了我的 yaml 文件。我想做的基本测试:将 api-stateful 的流量重新路由到 api-stateless,以验证是否考虑了虚拟服务。它不起作用。你看出什么问题了吗?是虚拟服务的错误使用吗?我的 Kiali 控制台在设置中没有检测到任何问题。

####################################################################
######################### STATEFUL BACKEND #########################
# Deployment for pocbackend containers, listening on port 3000
apiVersion: apps/v1
kind: Deployment
metadata:
  name: stateful-deployment
spec:
  replicas: 3
  selector:
    matchLabels:
      app: stateful-backend
      tier: backend
  template:
    metadata:
      labels:
        app: stateful-backend
        tier: backend
    spec:
       containers:
       - name: pocbackend
         image: pocbackend:2.0
         ports:
           - name: http
             containerPort: 3000
---
# Service for Stateful containers, listening on port 3000
apiVersion: v1
kind: Service
metadata:
  name: api-stateful
spec:
  selector:
    app: stateful-backend
    tier: backend
  ports:
  - protocol: TCP
    port: 3002
    targetPort: http
---
#####################################################################
######################### STATELESS BACKEND #########################
# Deployment for pocbackend containers, listening on port 3000
apiVersion: apps/v1
kind: Deployment
metadata:
  name: stateless-backend
spec:
  replicas: 3
  selector:
    matchLabels:
      app: stateless-backend
      tier: backend
  template:
    metadata:
      labels:
        app: stateless-backend
        tier: backend
    spec:
      containers:
      - name: pocbackend
        image: pocbackend:2.0        
        ports:
           - name: http
             containerPort: 3000
 ---
# Service for Stateless containers, listening on port 3000
apiVersion: v1
kind: Service
 metadata:
  name: api-stateless
spec:
  selector:
    app: stateless-backend
    tier: backend
  ports:
  - protocol: TCP
    port: 3001
    targetPort: http
---
#############################################################
######################### FRONT END #########################
# deployment of the container pocfrontend listening to port 3500
apiVersion: apps/v1
kind: Deployment
metadata:
  name: front-deployment
spec:
  replicas: 2
  selector:
    matchLabels:
      app: frontend
      tier: frontend
  template:
    metadata:
      labels:
        app: frontend
        tier: frontend
    spec:
      containers:
      - name: pocfrontend
        image: pocfrontend:2.0               
        ports:
           - name: http
             containerPort: 3500      
---
# Service exposing frontend on node port 85
apiVersion: v1
kind: Service
metadata:
  name: frontend-service
spec:
  type: NodePort
  selector:
    app: frontend
    tier: frontend
  ports:
  - protocol: TCP
    port: 3500
    targetPort: http
    nodePort: 30000
---
##############################################################
############ ISTIO PROXY FOR API-STATEFUL SERVIC E############
##############################################################
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
  name: api-stateful-proxy
spec:
  hosts:
  - api-stateful
  http: 
  - route:
      - destination:
          host: api-stateless

【问题讨论】:

  • 使用此虚拟服务,您将请求发送到有状态服务,它将路由到无状态服务。另外,不起作用是什么意思?
  • 无状态和有状态服务现在返回一个计数器值,没什么特别的。每次 pod 收到请求时,它都会在有状态或无状态文件夹中生成日志(我从示例中删除了卷挂载以保持简短)。尽管我的虚拟服务,当我向有状态服务发送请求时,它是接收请求的有状态服务,而不是无状态服务:所以看起来虚拟服务没有正确执行路由或被绕过.我只是在通过虚拟服务测试路由。
  • 你的意思是我需要定位 api-stateful-proxy?这与文档不一致,而且虚拟服务的“主机”部分应该指定请求目标的主机。
  • 你是对的。那是错误的。
  • 您是否尝试过使用粘性会话配置添加DesinationRule?在 istio 文档中可以在 this 页面上找到它。

标签: kubernetes proxy istio


【解决方案1】:

如 cmets 中所述,这可以使用带有粘性会话配置的 DestinationRule 修复。

可以在 istio documentation 中找到示例:

LoadBalancerSettings

适用于特定目标的负载平衡策略。详情请参阅 Envoy 的负载均衡 documentation

例如,以下规则对流向评级服务的所有流量使用循环负载平衡策略。

apiVersion: networking.istio.io/v1alpha3
kind: DestinationRule
metadata:
  name: bookinfo-ratings
spec:
  host: ratings.prod.svc.cluster.local
  trafficPolicy:
    loadBalancer:
      simple: ROUND_ROBIN

以下示例使用 User cookie 作为哈希键,为基于评级服务散列的负载平衡器设置粘性会话。

 apiVersion: networking.istio.io/v1alpha3
 kind: DestinationRule
 metadata:
   name: bookinfo-ratings
 spec:
   host: ratings.prod.svc.cluster.local
   trafficPolicy:
     loadBalancer:
       consistentHash:
         httpCookie:
           name: user
           ttl: 0s

【讨论】:

  • 谢谢,我同意,我终于做到了。我对 VirtualService 很好奇,我从来没有想过它是如何工作的,这就是为什么我让帖子打开但没有得到答复的原因。无论如何,你是完全正确的,它的工作原理,谢谢!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2019-07-19
  • 2021-09-21
  • 1970-01-01
  • 2021-06-09
  • 1970-01-01
  • 1970-01-01
  • 2020-09-07
相关资源
最近更新 更多