该篇文章系SDN实战团微信群(团主张宇峰@brocade)组织的线上技术分享整理而成,由九州云(99Cloud)培训经理梁博将他对于Docker网络使用体验和一些技术方面的理解进行了分享。
分享嘉宾
--------------------------------------------------------------------------------------------------
梁博,浙江九州云信息科技有限公司首席架构师兼培训业务负责人,从2012年开始OpenStack研究工作,加入九州云后联合创建了trystack.cn测试床项目,以及深入OpenStack SDN领域,多次参加各种云计算活动和培训工作,梁老师在九州云担任OpenStack奇侠之天命判官之前也曾在微软研发任职及多次跨界创业。
--------------------------------------------------------------------------------------------------
我今天和大家分享一下Docker的网络,主要是基于我的使用体验和对这里面的一些技术的理解,也顺便听取一下大家的建议。我是做培训的,大多数时候和理论的东西打交道, 顺便做一些实验,为了讲课的时候不那么虚。所以,要是问,在多大规模下会是什么样的,那我就只能说,我不知道了。
讲之前,问大家个问题,大家知道docker0是什么吗?实现docker的网络,有很多方式。
这张图, 是我们在用docker的时候,可以用的网络连接方式,可以看出,默认的docker对网络的管理,使用的linux bridge,这个bridge的名字就叫docker0。
容器里面有一个veth连接在这个bridge上,如果是single host,容器和容器之间的通信会通过docker0,在multi host上, 我们可以把物理的网卡bridge到docker0上,那么容器就可以实现跨主机的访问。我主要用docker来做我自己的工具(应用), 所以对网络的要求并不复杂,但是我也考虑过,如果在比较复杂的环境,例如你是做云的,或者你的应用灰常牛逼,需要几万个容器的,那么对网络的要求就会比较高,在这种场景下,我们就不能单单用docker0了。
我们从应用的角度来看待这个问题,如果我是做web application的,那么就涉及到web midlleware database or other backend的架构,他们并不在一个容器里面,甚至不在一台物理主机里面。那么我们在发布多种这样的应用的时候,就会需要编排,网络的管理。
例如backend通常是在private网络,而web server是在可以被外网访问到的网络里面,那么docker的生态里面,会有一些专有的工具来管理网络。这些都做过一些实验,真正敢说自己能在生产环境用的就只有docker + weave了。不过我个人认为,所谓的生产环境,就是被虐了很多遍的POC而已,都是慢慢演进来的。
特别是面对例如OpenStack,Docker这种新的东西的时候,可能群里大多比较关注SDN技术,所以今天就聊聊Docker + OVS吧。docker0比较简单,你装好docker就可以用了。但是ovs需要其他的配置。比如如果我们用k8s,可以使用ovs来封装数据包,也就是说用gre或者vxlan来打通所有的物理节点。好吧,概念是一样的,但是也不一样。
很多人都会比较,docker和openstack哪个好,我觉得本身他们不是相互取代的,而是共同配合来完成复杂的应用部署。单个应用无所谓你用什么,对吧。我说的概念是一样的,在网络层面,他们都是通过port连接到bridge上面,只不过ovs的bridge高级一点。但是有一点不一样,我们通常在跑虚拟化环境的时候,会心里有个数字,就是一台物理机上跑多少虚机。跑20个,50个或者100个,这个是根据应用,在部署之前心里就会知道个大概。但是docker管理的是容器,它没有虚拟机里面OS的那层开销或者说很小,所以,一台物理机跑1000个容器也是有可能的,估计群里有的朋友试过。这就对网络本身提出了很大的挑战
本来我家里的无线路由器只要和我的电脑打交道,结果这哥们带了一堆设备回来,现在连个手表都要IP地址,那么端口一下多了,网络就瓶颈了。那么在一台物理机跑很多容器的情况下,我们实际上不一定需要为每个容器都分配一个ip地址。docker可以让我们容器之间共享网络。也就是一个veth被N个容器来使用。
如果docker之下还有其他的cloud环境,例如AWS,GCE或者OpenStack的话,我们可以把docker的节点限定为一个应用,这个应用的stack,可以共用一个网络环境。我们可以docker run --net=xxx或者docker run --net=host来指定容器的网络环境,这样用来减轻ovs管理多个网络的鸭梨。这个是从单个host的视角来看的。
那么如果还是觉得这样比较麻烦。那么就把这个事情交给它上面的管理系统去做。比如说k8s,它把你的应用做成pod,然后通过service去发布,这个我不细说了。丢个图:
可以在一个pod里面共享一些基础资源,例如网络和存储,service的话,就是让多个pod来做fail over或者LB了。
使用OVS的话,就是:
所以,因为容器比较轻量级,而且对系统的依赖不强,所以到是比虚拟机更加灵活一点。我们做网络管理的时候,如果是跟虚拟机打交道,我们得考虑它的管理平台是什么,这就是OpenStack Neutron给我们带来的一些困扰。它很灵活,但是我们得遵守它的规则来玩。我们选择好了一个Cloud Platform,才对网络做针对的设计和部署。而Docker的话,我们可以先设计好网络,比如我们就是用ODL这些OF Controller来管理了一堆设备,然后把这些设备下连接的X86 Server里面的OVS打通,然后随便里面跑哪些业务,这些业务也可以很方便的去做数据路径的管理。甚至做好可视化。因为docker相对来说,还是比较透明的,不像Neutron里面的tenant network。
在Docker里面,不管使用bridge还是ovs,主要还是通过namespace在进程里面附加到网络上。docker0比较简单,就是通过L2/MAC地址学习来进行数据包的交换,其实就是在kernel里面做数据包转发。那么docker用了很多linux本身的东西来进行更上一层的管理。比如使用iptable,它为每个容器分配了一个172.xxxx的地址,然后把这段地址里面的转发都做了masquerade,所以,容器不需要做网络的配置,直接可以访问到外部网络。所以docker里面的ip地址的翻译完全是通过iptable中的SNAT,DNAT来实现。
你原来如果用的docker0,那么部署weave的话,可以直接来用。刚才说到docker本身的网络,那么就是基于这个基础上面, 我们可以做进一步的延伸,不能每次都手动的--net是吧。所以现在有很多docker的编排系统,例如k8s,messos这些。这些工具里面可以有多个网络管理的选择。特别提一下的是libnetwork,这个东西是docker搞出来的,所以直接集成到docker cli里面了。类似neutron一样,通过命令,直接来管理租户网络。除了这个,还有刚才提到的weave, flannel, socketplane等等。当然,你也可以把容器直接连到ovs上,让上面的controller来管理,这就是说docker的网络其实还是比较灵活的,部署的方案会比较多,我也没有一一试过,用的几本上就是k8s + flannel,要么就是在openstack上面让neutron去管理网络,docker作为计算节点,或者更近一步的,大师兄研究过,使用openstack的magnum来管理像k8s这样的编排工具。那会比较复杂,我比较喜欢weave是因为我的应用没那么复杂,所以docker0足够了。因为我也没钱去做一个公有云,让很多人来用。这点我倒是觉得daocloud做的挺好,因为管理应用,做CICD比较简单和方便。
说说用docker遇到的问题吧,docker目前遇到的网络问题真不是特别多,因为大家很多还是拿docker来做开发测试平台。
更多的是layered fs的问题。不过既然docker0更简单,它是不是应该性能更好更多的是layered fs的问题。不过既然docker0更简单,它是不是应该性能更好
如果我们使用的是docker run -P 8080:8080 ,会在iptable里面生成一条规则。从这个report的chart来看,它实际上延时比kvm的还高。
Report地址:http://domino.research.ibm.com/library/cyberdig.nsf/papers/0929052195DD819C85257D2300681E7B/$File/rc25482.pdf
这是IBM的一个报告,关心docker performance的朋友可以用来做一个参考,实际上,我现在试验性的把openstack里面的一些服务跑在容器里,就是用—net=host这种方式来跑的,这其实比较适合一个docker host跑一个app stack,在管理应用的时候尽量把app stack部署在一个host上。然后多部署几台主机用LB的方式来发布。如果用docker0的话,还可以让容器跑在privileged模式下。然后通过lso, lro来做offload。
今天就主要从网络的角度来分享一下docker的使用心得。接下来可以自由发挥。我能力有限,在线回答不了的话,可以线下讨论,我也可以顺着大家的问题,多做些研究,下次分享。
Q&A
--------------------------------------------------------------------------------------------------
朱坚
Q1:现在Docker一般是直接部署在物理server上还是虚拟机上?如果是在虚机上部署Docker是不是又更复杂一些了?
A1:在物理机和虚拟机部署上面, 区别不大。
诙谐童子
Q2:针对IBM的report,在实际做网络压力测试的时候, docker的docker0其时没有表现出它应该有的能力,这个能力是指capacity还是performance?
A2:Performance
Q3:就是说docker0使用的时候performance不是最佳的对么?
A3:也不能这么说,只是说,它没有我们认为的样子好。它会对网络的延时带来一点影响,从刚才那个report的chart来看,它实际上延时比kvm的还高。
HongLiang
Q4:测试报告70多us是跨物理机,还是单机内部?
A4:用的是2个机器,测试使用的是Mellanox ConnectX-2
肖何
Q5:如果使用docker的大使模式效果如何?通过几个docker共享其中一个docker veth连接到docker0做proxy转发?
A5:可以这么做,减少iptable的规则数量也对性能提升有一定的帮助。
Q6:关于跨主机的docker通信,有成熟的OVS上gre支持跨主机的通信,现在docker 1.8后引入SDN功能,通过控制器也能做到跨主机的vxlan互通了,这个有考虑吗?
A6:当然,ovs也是个不错的选择。特别是ovs 2.4增加了对docker网络的injection的能力。可以在运行时改变容器里的网络
Q7:顺着openstack我胡乱说一点,我觉得docker-server和OpenStack neutron-server好像有点接近,比如NAT/iptables这些,但在node agent,或者说分布路由上的思路上差异比较大
A7:docker更多是在本机做路由。但是也不局限于此。它本身也是可以被其他的L2方案来接管的
Q8:docker没有l2/l3 agent类似的plugin实现,它bri-int(veth)不能把tap流量map更复杂的转发组件(bri-tun/bri-ext)上,属于初级的聚合;而要做分布式路由,docker-server没有OF流表下发这套,上了规模后,东西向流量处理可能也会是瓶颈。
A8:可以用docker + ovs来解决,但是需要类似ODL这样的controller来管理,比如引流到某个设备
Q9:给docker 直接分ip这个想法如何?
A9:google就认为ip is cheap,尽量分ip给pod
Q10:dock支持ipv6不?
A10:docker 1.5开始支持IPV6
--------------------------------------------------------------------------------------------------
SDN实战团微信群由Brocade中国区CTO张宇峰领衔组织创立,携手SDN Lab及海内外SDN/NFV/云计算产学研生态系统相关领域实战技术牛,每周都会组织定向的技术及业界动态分享,欢迎感兴趣的同学加微信:eigenswing,进群参与,您有想听的话题可以给我们留言。