用户需求
StatefulSets场景下,单个Pod之间能有固定标识跨集群通信
描述:3个集群中起3个实例组成一个完整的服务。实例间能有固定标识互相独立通信
用户需求描述中说明单集群可能会扩展Pod,如下图中ZZZC机房起2个Pod,SHBT、BJPDC起1个Pod
ps:ZZZC、SHBT、BJPDC都是IDC
可实现方案(3种)
- 每一个Pod前挂一个VIP进行集群外访问,多个Pod起多个Stateful部署,我们容器对接了公司内部的负载均衡。或Ingress
- Pod支持固定IP。公司内部的PodIP在内网是互通的
- Headless Services支持多集群通信
方案2-固定PodIP
| 方案 | 实现 | 资料 |
|---|---|---|
| Calico | 预留ip pool资源 ipreservation 防止自动分配为Pod指定IP, By 添加 Annotation cni.projectcalico.org/ipAddrs": "["192.168.0.1"]" | Use a specific IP address with a pod |
| Cilium | 不支持 | can i pin the ip of the pod? Will cilium IPAM support specified ip address of pod? |
| Kubu-OVN | 使用annotation定义StatefulSet固定IP时需要注意以下几点: * IP必须在所属子网的CIDR内。 * 所使用的IP不能和已有的IP冲突。 * IP数量小于replicas数量时,多出的Pod将无法创建,需要根据StatefulSet的更新策略以及扩容规划调整 ovn.kubernetes.io/ip_pool中的IP数量。 | StatefulSet固定IP |
| hostIP, hostPort | 限制: * Pod不能随意漂移物理机。每次重新启动pod时,Kubernetes都可能将pod重新安排到其他节点上,因此应用程序的IP地址将更改。 * 相同端口的应用不能部署在同一物理机。当群集上运行的应用程序数量增加时,这可能会导致端口冲突。 结论:不建议使用,不好管理 | Configuration Best Practices |
| 阿里开源-OpenKruise | 原地升级(对应的是重建升级): 问题1:只允许修改限定的字段,如果尝试修改其他字段会被拒绝。 spec.template.metadata.* spec.template.spec.containers[x].image spec.template.metadata.labels/annotations 并且 container 中有配置 env from 更新以下字段会导致IP变化: spec.template.spec.containers[x].env spec.template.spec.containers[x].resources 问题2:Pod所在物理机故障,Pod重建至其他物理机,IP会发生变化 结论:支持以上前提下,能获得PodIP与物理机一样的生命周期 | github.com/openkruise/… Advanced StatefulSet 原地升级 |
| 阿里Terway(状态:公测中) | Terway拥有更为灵活的IPAM(容器地址分配)策略。无需按节点分配地址段,随用随分配,地址无浪费。支持为Pod配置固定IP及独立虚拟交换机、安全组。 仅支持:StatefulSet | 为Pod配置固定IP及独立虚拟交换机、安全组 |
| 京东云 | 非开源-提供思路 历史原因,集团内很多基础运维业务包括日志、监控、访问策略控制、服务发现等都是以IP作为实例唯一标识 通过对Enhanced Statefulset Controller 、 Scheduler、CNI这几个模块扩展实现 对scheduler做的扩展主要是解决Pod资源预留问题。正常流程中当绑定静态IP的Pod删除后,Pod所占用的资源也会被释放,如果有其他新调度的Pod到这个节点上就会占用当前节点的资源。这时如果绑定静态IP的Pod在此节点重建可能就会因为资源不足而失败。 节点故障会创建同规格节点进行迁移 结论:非开源、定制化开发 | 支持Pod 绑定静态 IP ,基于K8s的自定义控制器—Enhanced Statefulset |
| kubernetes | 原生不支持 | Static IP for pod |
方案3-Headless Services多集群通信
| 方案 | 进度 | 资料 |
|---|---|---|
| kubernetes | 停滞2年了 | Multi-Cluster Services API |
| Linkerd | 迭代中,8.8k Star | linkerd2 |
| istio | 不支持 | Headless services issues in multi-cluster multi-network Make headless services work across multi-network gateways |
Linkerd 实现原理
新增了很多组件与概念来实现
多集群通信使用Service与Gateway交互:
Headless Service Stateful通信:
west、east集群, west集群启动Headless Service :
nginx-svc
同时每一个Pod都含有DNS name:
pod-0
pod-1
east集群会Copy west集群中的Headless Service和Pod DNS name 到自身集群中并为每个Pod 添加IP,同时命名为(添加west集群后缀进行区分)
nginx-svc-west
pod-0-west
pod-1-west
在east集群中访问pod-0-west时,linkerd2-proxy会拦截将它指向gateway,proxy将请求转发回west集群