我一直在寻找如何在GKE中使用Cookie相似性。并且我成功实现了它(由于这个问题:Problems configuring Ingress with cookie affinity),现在我可以看到我收到了GCLB Cookie,但是由于某种原因,请求没有返回到相同的pod副本
我使用以下内容创建了一个YAML:
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: my-bsc-deployment
spec:
selector:
matchLabels:
purpose: bsc-config-demo
replicas: 3
template:
metadata:
labels:
purpose: bsc-config-demo
spec:
containers:
- name: hello-app-container
image: gcr.io/google-samples/hello-app:1.0
---
apiVersion: cloud.google.com/v1beta1
kind: BackendConfig
metadata:
name: my-bsc-backendconfig
spec:
timeoutSec: 40
connectionDraining:
drainingTimeoutSec: 60
sessionAffinity:
affinityType: "GENERATED_COOKIE"
affinityCookieTtlSec: 50
---
apiVersion: v1
kind: Service
metadata:
name: my-bsc-service
labels:
purpose: bsc-config-demo
annotations:
beta.cloud.google.com/backend-config: '{"ports": {"80":"my-bsc-backendconfig"}}'
spec:
type: NodePort
selector:
purpose: bsc-config-demo
ports:
- port: 80
protocol: TCP
targetPort: 8080
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: my-bsc-ingress
spec:
backend:
serviceName: my-bsc-service
servicePort: 80
rules:
- http:
paths:
- path: /*
backend:
serviceName: my-bsc-service
servicePort: 80
---
什么可能导致此类问题?
答案 0 :(得分:2)
原因是来自GCP HTTP(S)负载均衡器documentation:
您必须创建一个防火墙规则,以允许来自 130.211.0.0/22和35.191.0.0/16到达您的实例。这些是负载均衡器用于连接到后端的IP地址范围 实例。
您的用户不是通过这些“代理”直接连接到后端,因此会发生会话亲缘关系,但不是您想要的。实际上,如果您使用的是GCLB,则应避免会话关联。
答案 1 :(得分:0)
我必须面对同样的问题,并且平衡流量的最后一层是kubeproxy
,此代理完全不支持会话亲缘关系。
要解决该问题,您必须使用其他入口控制器将kubeproxy
替换为支持会话亲缘关系的代理服务,在我的情况下,我使用Nginx。您有一些很好的示例,说明了如何在GitHub存储库here上实现它,基本用法here,还可以根据每个入口的需要使用注释来配置Nginx,完整的注释列表{{ 3}}。
答案 2 :(得分:0)
亲和力正在发挥作用,但并非您期望的那样。目前,GCP LB与后端(节点,而不是Pod)之间存在关联。流量到达您的节点后,该服务会将请求转发到Pod。由于服务没有亲缘关系,因此它基本上是随机选择一个Pod。有两种方法可以使这项工作。
使用container native load balancing using network endpoint groups。这将导致Pod充当负载均衡器的后端,因此cookie亲缘关系应该保持不变。
保持Ingress不变,使用spec.sessionAffinity
配置NodePort服务。在GKE上,仅支持clientIP
作为该字段的值。下一步是确保正确使用了客户端IP,请添加spec.externalTrafficPolicy: Local
字段。
或者,您可以使用Nginx入口,它不会像GCP入口那样引起2层负载平衡,因此亲和力更直接,但不受Google支持。