k8s的网络接口cni及灵雀云的实践

author author     2022-10-01     604

关键词:

K8S的网络接口CNI及灵雀云的实践

K8S的网络模型


我们从底层网络来看,分为三个层面。首先是Pod之间的多个容器的网络互通。我们知道,K8S的Pod可以由多个容器组成,这个层面网络互通是比较简单的,因为所有的容器都是共享一个网卡,可以直接通信。


第二个,一台虚拟机上多个容器之间的网络是如何通信的。这块儿其实也比较好解决,例如Docker会搭一个网桥,让上面所有的东西、网卡接到网桥上,他们之间的网络就可以互通。Docker默认服务会创建一个Docker0的网桥,其它主流的像Calico、Flannel的模式也是类似的。这种方式的实现也是现在的主流。


第三种是比较难的,Docker一开始就没有做好,是跨主机的Pod之间的网络通信。对于K8S来说,这个网卡如何分配其实K8S是没有定义的。不同Pod跨主机网络之间如何通信、如何打通网络,K8S不管,是交给第三方实现的。在这块,是有很多工作可以做的。

技术分享图片

容器网络设计给运维人员带来的困惑


现在我们再想一些问题,容器网络设计会给传统运维工作带来怎样的困惑?


传统运维工作强调对IP要有很强的管控。容器时代,Pod需不需要有固定的IP?Pod重启之后,IP是否不变?其实K8S没有规定,而且从大部分主流的实现来看,容器IP是可以变的。既然容器的IP是会变的,就会带来一个很直接的问题,我想访问这个服务怎么访问?之前两位同事讲过很多,我不做很细的介绍。


这个大致的原理是,尽管底层Pod IP不断变化,但是我会给你提供固定的域名或者DNS的方式,或者固定的Cluster IP的方式等等。不管Pod方式如何变,总会给你固定的方式,通过固定的方式可以访问到一直变化的IP,这些方式都是通过Kube-proxy、iptables、Kube-dns实现。

技术分享图片

我们实际测的时候发现,K8S的服务发现功能比较少,随着访问量越来越大,会发现它的性能有很多问题,还有稳定性也有很严重的问题,而且它的稳定性缺陷是它从设计当初就很难避免。我们正在改进这些设计缺陷问题。


为此很多人就会问,说你的容器IP是一直变的,怎么管?但容器就是这样的,容器生命周期很短,不断创建、不断消失,IP肯定不断变。容器的好处是,你可以在这台机器上挂,在另外一台机器也可以。但运维人员首先觉得IP这样飘不好。对于运维来说,网络方面是很重要的资源,要对IP进行强管控,服务来回飘,会让他的安全感下降很多。


运维服务有很多基于IP的东西,有流量和突发的监控,如果你服务的IP一直变化,通过这个IP它很难用到这个服务,相当于IP的监控就没有意义,因为根本不知道IP流量上去了是哪个服务的,很难对应到这个事。

   

还有是对于IP安全策略没有办法做。如果以前IP是固定的,iptables或者网络底层防火墙,这样的东西都是很好做的,可以很好的进行服务之间的安全访问限制。如果IP都是变的,这个事情就变得没有办法做了。


第四是定位分析和数据处理问题。我们见到,有的客户把网络正常在跑的所有流量镜像一份,每天对复制的流量进行分析,看你有没有违规操作或者有什么恶意攻击,或者哪些行为不正常,这样他们通过IP再定位服务。如果IP是变的,相当于把他们很多能做的事情去掉了。


还有一些特殊的软件,他们的license是根据网卡来的,就是说他的license是根据网卡的IP加上Mac计算出来的。这种情况下相当于IP变了,license失效,软件跑不起来。


还有你的IP不断变化,实际中也有问题,有很多服务和软件就是基于IP部署的,基于IP相互发现的,最典型的是Etcd这样的。如果你是用K8S或者其他的容器,IP是变的,这个东西怎么填都是很难的事情。


K8S有它的解决方案,Headless Server和 Stateful Set可以做这个事情。但是这个事情在我看来有两个问题,它引入两个不好理解的概念,如果大家对K8S比较关心,第一次看,我觉得你看好半天才能明白它干什么,它为什么这么设计。它的核心理想是你的Pod IP是变的,然后给Pod一个顺序,给每个Pod一个标志符,etcd1、2、3,给他们三个人每个人用k8s Service+域名,你在里面不用填IP,填对应的三个域名就可以。但域名有cash缓存的问题,底层Pod IP失效,域名的缓存没有失效就会造成研判时间的不一致,我觉得靠Service做这件事情也是有问题的,并不能完美的解决这个问题。  


 为什么Docker、K8S都没有做固定IP的事情?


刚才说了IP不固定的影响,做容器之前大家可能没有想这个事,可能从一开始就认为IP是不固定的,我们想一下如果IP是固定的有什么影响,其实好像还可以用,并且可能变得更简单。比如Cluster IP或者DNS它们的映射由于IP是固定的可能变得更简单了。如果容器的IP固定,运维传统的基于IP的监控也可以做了,因为对他们来说没有影响,和原来是一样的,对他们的接受程度也会更高一点。


我们很多服务发现的方式,可能之前通过K8S的Sevrice来进行服务发现,既然IP固定,我们可以跳过,直接用IP服务发现就可以,没有必要让你的运维理解很复杂的概念。大家会问什么是Cluster IP,什么是Pod,这些还是有理解成本,如果提供原生的方式也是不错的。


可能想到一个问题,既然固定IP还是有好处的,为什么Docker还是K8S都没有做这个事情呢?我觉得一开始Docker没有想好这个事情怎么做。最开始Docker就是一个单机的工具,没有想做得很复杂,最早Docker的网络和存储都是很弱的,它根本没有往这方面想。


还有一点,在我理解就是理念之争。到底服务应该做成有状态的还是无状态的?有Docker之后大家认为容器应该是跑无状态的东西,而不是有状态的东西,但是网络这块是有状态的。我们之前说有状态想到的是存储,认为存储才是有状态的服务,其实网络也是状态的一部分。大家可以想一下,如果Pod里面的服务访问外面,给外部留下的信息是某个IP访问我,所以对外的状态对你来说,IP其实也是你的一个状态,所以说网络其实也是状态的一部分,如果要做有状态这个事情就变得很难。


但是能不能做呢?可以做,我们做了一些尝试,做的方式是我们自定义CNI插件。


如何自定义CNI插件?


CNI,这个概念大家平时听的少一点。它的全称是Container Network Interface,它注重给你的容器提供一套标准的网络的接口。现在包括K8S等都是通过CNI这种方式实现的。CNI 是 CNCF 的一个项目,如果你对比其它项目,CNI应该是里面最简单的。如果你对这个项目有兴趣,从这里开始是比较好的,可能几百行或者上千行的代码就到头了。一个是CNI的标准,包括CNI接口和库,怎么快速实现CNI,还有CNI提供的网络插件。


介绍一下Kubernetes和CNI之间是如何交互的,给大家讲完之后,大家可以比较容易上手,自己实现自己的网络。

技术分享图片

这是Kubernetes的基本参数,大家可以看到。红色的标起来的是两个选项。CNI在我看来是有点奇怪的实现。一般的时候一个程序和另一个程序交互,大概是HTTP REST或者是RPC或者TCP的通信,但是CNI和Kubernetes的交互方式是通过二进制文件的方式,它会调用二进制文件传一个参数来做这样的事情。第二张是CNI实现的组件,他们都是以二进制的形式放在目录下面。左下角是CNI的配置,是最简单的,参数很少,还有一些其他比较复杂的。其实比较重要的是type和IPAM。


大概讲一下它交互的流程,是通过创建Pod和销毁Pod两个事件来触发的。创建Pod的时候,它会去调CNI,它会根据这个文件会先调用macvlan,创建一个网卡,然后再分配IP,都是调里面的DHCP和macvlan二进制文件。创建网卡,构建IP,把这个网卡放到Pod network namespace,相当于完成Pod网卡的创建。还有,Pod删除的时候,可能调用二进制文件释放掉,然后删除网卡,完成网卡的销毁。大概的交互比较简单,就这两个,实现的时候也是实现这两个方法就可以。

技术分享图片

最下面是main函数,其实有一个库,可以方便实现,照着这个写就可以,需要实现的是下面的函数就可以。函数其它的都不太用着重关注,都是做错误处理。最主要关注上面的,它是在NetNSpath里面创建的一块link,删除的时候再把这块网卡删除,这是最简单的设备创建。如果大家对网络比较熟,或者对自己的网络有特殊的要求或者定制化的需求,其实在里面实现自己的逻辑就可以,整体来说它的逻辑还是比较简单的。而且还有一个功能是多个命令是可以串联的,比如我刚才举的例子,macvlan和DHCP是串联的,macvlan先创建网卡,然后再调DHCP,分配IP,他们之间有一个result的返回,通过result进行数据结构的传输。我们看一下result就可以知道网络还可以做什么别的事情。

技术分享图片

这是官方定义的API标准,其实我们也是可以在里面扩充的。上面是interfaces,Kubernetes这个网络做得实在太简单,包括容器中的很多东西都是太简单了,可能一个pod里面有一个网卡设一个IP就完了。其实一个pod里面有多个网卡的需求,一个数据流,一个控制流,这种是可以做的。在它的interfaces里面可以看到有内置的网卡和mac地址,因为我们碰到有些客户,你的mac是可信域才可以做安全策略,这需要你要自定义的mac。再往下,网卡是不是有多个IP,而不是常用的网络,一个容器的一个IP。再往下可以定义这个容器的路由表,包括路由的顺序等等都是可以定义的。再往下是DNS server,容器里面的DNS都可以自定义,容器通信网络这块有很多可以做的事情,如果大家想做这方面,我觉得机会还是很大的。现在的网络说实在的,尽管实现很多,但是都还是蛮弱的。


容器网络方面已经有一些第三方实现,比较知名的有flannel、calico、weave……。下面两项其实是它官方已经实现的,看起来分两大类:一是网卡生成的方式,比如bridge、ipvlan、macvlan、loopback、ptp、vlan。第二大块是IPAM。我不知道大家是否理解IPAM,IPAM的意思是IP该怎么分配。官方实现的有两种,一种是DHCP,一种是host-local。


灵雀云如何通过IPAM做到精确管控IP?


回到之前说的我们要做固定IP,大家可以很容易联想IPAM这块做一些东西,因为这个IPAM是针对IP的,如果要做的话,先看一下现有的两种有没有问题,或者现有的两种怎么实现。DHCP大家比较熟悉,就是自动分配IP,它的问题是没有办法精细管控IP。因为当需要通过主机发再发DHCP的广播再获得IP,相当于容器IP和宿主机的IP混在一起,很难精确分配到某个Pod使某个IP,因为你不知道这些信息。这在实际生产环境用得很少。因为IP管控要求很严格,不可能自己计算IP,我们家里的wifi或者办公才会用到,企业级业务碰到的机会都很少。

host-local,每台机器上都有这个文件,这个文件上规定每台机器能生成一些IP。可以看一下配置文件的格式。其实这两个参数比较重要,一个是rangeStart和rangeEnd,就是每台机器分配的范围是多少。这种分配方式有一个很严重的问题, Calico 和 Flannel都有,就是每台机器都是固定的,这给每台机器划分了一个网关,相当于你Pod是在机器上的,因为IP是很不灵活,很难实现IP的漂移。而且分配IP比较困难,新增机器要重新定义,这台机器用多少IP,要考虑IP段的释放,很不灵活,显然没有办法实现固定IP的事情。


为什么这个事情感觉这么难?我觉得也是K8S设计理念的问题,我们可以看到K8S管了很多东西,管了Pod、configmap、Service等,你会发现它没有管你的IP。理论上来说,IP对你的服务或者对你的集群来说是很重要的资源,但是K8S里面IP不是它的一等应用,甚至你根本没有一个跟容器相关的资源在开发里面找到,所以使得你的IPAM变得很难。你要么通过K8S完全无关的东西来实现,要么通过锁死的方式实现,这其实都是因为你没有把IP资源看得特别重,你只是当做可以随机分配的,所以它设置的理念就是你的IP我不关心,该是什么就是什么,所以导致这样的结果。


最后讲一下我们做的,我们把IP当做很重要的资源,进行单独的管理。我们会专门实现IPAM的组件,实现网段的添加、删除,可以在K8S管理网段,给某个业务或者某几个用户分配一个网关,然后对IP进行网关设置,路由设置,和DNS设置。有了网段之后,有IP的添加删除,会有很重要的资源,该用哪些IP,哪些IP是可以用的,都是可以用管理员指定的,而不是像K8S随机划一个网段,还有权限、配额,之后就可以顺利创建服务了。


技术分享图片

现在创建K8S的Deploy的时候需要申明用哪几个IP。如果IP信息传输到IPAM的组件,这个IPAM就是一个数据库,这个数据库就会显示哪些IP可以使用,哪些应该被哪个服务使用,把这个记录下来。在K8S启动Pod,CNI里面再实现一套逻辑,把IPAM的逻辑实现了,那套做的东西会进入IPAM的数据库里面找,如果用就占用这个,别人不能再用,就可以实现每个POD有自己的IP,这个IP是你之前想要的。如果在删除的时候,CNI会把IP释放掉,说明这个IP不会再被这个服务使用,别的服务可以使用这个IP。我们如果想创建etcd的服务,就不用再写一个东西,你只要做你想要的IP就可以,很大的简化你的工作量,而且实现我之前说的传统的运维,IP的监控、管理的东西。

本文出自 “13481808” 博客,请务必保留此出处http://13491808.blog.51cto.com/13481808/1983816

灵雀云acp斩获“2022金边奖-最佳云原生边缘云平台”

...算社区主办的全球边缘计算大会·上海站成功召开,灵雀云凭借出色的全栈云原生技术实力、专业的高品质服务以及在边缘云场景的丰富落地实践,斩获“2022金边奖-最佳云原生边缘云平台”奖项。“十四五”规划中明确... 查看详情

从零开始入门k8s|理解cni和cni插件

...键词“入门”,即可下载从零入门K8s系列文章PPT。导读:网络架构是K8s中较为复杂的方面之一。K8s网络模型本身对某些特定的网络功能有着一定的要求,因此,业界已经有了不少的网络方案来满足特定的环境和要求。CNI意为容器... 查看详情

jenkins官方社区携手灵雀云成功举办jenkinsmeetup

10月27日,由Jenkins官方社区和灵雀云主办的Jenkins插件开发Meetup在北京中科曙光大厦成功举办。这是Hacktoberfest(即HackOctoberFestival,十月“黑客”庆典)黑客马拉松活动的一部分。 灵雀云DevOps高级研发工程师赵晓杰作为出品人... 查看详情

灵雀云acp成功通过金融信创生态实验室适配验证

近日,灵雀云全栈云原生开放平台ACP(以下简称灵雀云ACP)成功通过了金融信创生态实验室适配验证,在金融科技领域的技术实力和专业水平得到了权威认可。近日,灵雀云全栈云原生开放平台ACP(以下简称灵雀云ACP)成功通过... 查看详情

浅谈k8s网络模型cni协议

...来,是为了更好的提供开放、扩展、规范等能力。K8s网络模型采用CNI(ContainerNetworkInterface,容器网络接口)协议,只要提供一个标准的接口,就能为同样满足该协议的所有容器平台提供网络功能。CNI是CoreOS提出的一种容... 查看详情

工业互联网新引擎——灵雀云×英特尔5g融合边缘云解决方案

...主办的“装备制造龙头企业数字化转型研讨会“上,灵雀云解决方案架构师赵昕受邀参会,并进行了“工业互联网云原生平台的价值及建设规划“技术分享,同时在会上解读了灵雀云ACP5G专网边缘云(集成Intel®Smar... 查看详情

非全研究生计算机网络-k8s网络插件(cni)性能分析

由于计算机网络课程需要,看了一些k8s网络机制,随翻译了一篇论文,说实话有点空洞。作者:YoungkiParkSchoolofElectronicEngineeringSoongsilUniversitySeoul,KoreaHyunsikYangSchoolofElectronicEngineeringSoongsilUniversitySeoul,KoreaYounghanKimSchoo... 查看详情

gartner发布服务器虚拟化市场指南灵雀云作为唯一本土容器厂商入选

容器化、云原生已经成为数据中心未来的主要发展方向近日,国际知名权威分析机构Gartner发布了《服务器虚拟化市场指南》。报告显示云服务商和开源社区正在给服务器虚拟化领域带来新一轮的创新,容器和虚拟机融合以及基... 查看详情

kubernetes CNI(容器网络接口)

】kubernetesCNI(容器网络接口)【英文标题】:kubernetesCNI(containernetworkinginterface)【发布时间】:2019-04-1708:40:30【问题描述】:我是kubernetes世界的新手,有人可以指定/告诉/重定向到:什么是KubernetesCNI?为什么使用它?它的用例是... 查看详情

带有 Weave CNI 插件的 AWS EKS K8s 集群不能有自定义指标 [关闭]

...AWSVPCCNI最大Pod数量节点限制(MaxPods=实例类型支持的最大网络接口数)*(每个接口的IPv4地址)-即t3. 查看详情

k8s各种网络方案-每天5分钟玩转docker容器技术(170)

网络模型有了,如何实现呢?为了保证网络方案的标准化、扩展性和灵活性,Kubernetes采用了ContainerNetworkingInterface(CNI)规范。CNI是由CoreOS提出的容器网络规范,它使用了插件(Plugin)模型创建容器的网络栈。CNI的优点是支持多... 查看详情

k8s各种网络方案-每天5分钟玩转docker容器技术(170)

网络模型有了,如何实现呢?为了保证网络方案的标准化、扩展性和灵活性,Kubernetes采用了ContainerNetworkingInterface(CNI)规范。CNI是由CoreOS提出的容器网络规范,它使用了插件(Plugin)模型创建容器的网络栈。CNI的优点是支持多... 查看详情

非全研究生计算机网络-k8s网络插件(cni)性能分析

由于计算机网络课程需要,看了一些k8s网络机制,随翻译了一篇论文,说实话有点空洞。作者:YoungkiParkSchoolofElectronicEngineeringSoongsilUniversitySeoul,KoreaHyunsikYangSchoolofElectronicEngineeringSoongsilUniversityS 查看详情

k8s中使用cni代替静态路由表有啥好处

...通过在每个节点上添加具有适当规则的静态路由表,容器网络也可以正常工作。例如,给定三个具有三个不同dockerbridge子网的节点:node-1(192.168.0 查看详情

k8s网络之设计与实现

 k8s网络主题系列:一、k8s网络之设计与实现二、k8s网络之Flannel网络三、k8s网络之Calico网络 K8s网络设计与实现是在学习k8s网络过程中总结的内容。在学习k8s网络各种插件之前我觉得有必要先搞清楚其设计思路是怎样的,... 查看详情

1.k8s部署(安装docker/kubeadm/kubelet,部署kubernetesmaster,加入kubernetesnode,部署容器网络(cni),测试kubernetes集)(代码片段

...belet和kubectl3.部署KubernetesMaster4.加入KubernetesNode5.部署容器网络(C 查看详情

1.k8s部署(安装docker/kubeadm/kubelet,部署kubernetesmaster,加入kubernetesnode,部署容器网络(cni),测试kubernetes集)(代码片段

...belet和kubectl3.部署KubernetesMaster4.加入KubernetesNode5.部署容器网络(C 查看详情

魅族容器云平台自动化运维实践

...魅族容器云的实践过程,分别是基本介绍、k8s集群、容器网络、外部访问4/7层负载均衡、监控/告警/日志、业务发布/镜像/多机房。1、基本介绍魅族云平台的定位是私有云平台,主要是用于支撑在线业务,用以替换传统的虚拟化... 查看详情