作者:刘海峰,IT行业资深码农,从事.net/java/go语言开发十余年,长期关注springcloud/k8s/linux网络相关的技术,现为滴普科技容器产品首席架构师。
前言
上一章介绍完flannel的udp模式后,接着来介绍一下vxlan模式,因为很多生产的K8S都正在使用这个模式,所以将会介绍得详细些。
在前面的章节中,我们介绍过配置linux vxlan完成跨主机的容器通信,flannel的vxlan模式大概完成的事情就是把那个章节中手工完成的事情自动化了,想了解的童鞋可以看回那一章:
vxlan模式下的flannel比udp模式少了一个组件,少的是那个用c语言写的打开tun设备的守护进程flanneld,因为vxlan模式下通信的全程都由linux内核完成,所以剩下二进制的flannel文件和以k8s的daemonset的方式运行的kube-flannel这两个组件了,下面将详细介绍这两个组件以及他们如何与k8s配合完成容器网络的编织。
二进制flannel文件
二进制flannel文件存放在每个节点的/opt/cni/bin目录下,这个目录下还有cni官方默认提供的其它插件,这些cni插件分为三类:
- ipam,负责地址分配,主要有:host-local、dhcp、static
- main,负责主机和容器网络的编织,主要有:bridge、ptp、ipvlan、macvlan、host-device、
- meta,其它,主要有:flannel、bandwidth、firewall、portmap、tuning、sbr
这些文件是我们在安装kubeadm和kubelet时自动安装的,如果发现这个目录为空,也可以用下面的命令手动安装:
yum install kubernetes-cni -y
这个flannel文件不做具体的网络编织的工作,而是生成其它cni插件需要的配置文件,然后调用其它的cni插件(通常是bridge和host-local),完成主机内容器到主机的网络互通,事实上这个flannel文件的源码已经不在flannel项目上了,因为这个flannel文件已经是cni的默认组件之一了,所以它的源码在cni的plugins中,地址如下:
https://github.com/containernetworking/plugins/tree/master/plugins/meta/flannel
kubelet创建一个Pod时,首先会创建一个pause容器,然后用pause容器的网络命名空间文件路径为入参(类似:/var/run/docker/netns/xxxx,前面的文章讲过这个路径如何获取及使用),加上其它一些参数,调用/etc/cni/net.d/目录下的配置文件指定的cni插件,这个配置文件是kube-flannel启动时复制进去的,内容如下:
cat /etc/cni/net.d/10-flannel.conflist
{
"name": "cbr0",
"cniVersion": "0.3.1",
"plugins": [
{
"type": "flannel",
"delegate": {
"hairpinMode": true,
"isDefaultGateway": true
}
},
{
"type": "portmap",
"capabilities": {
"portMappings": true
}
}
]
}
这个文件中指定的cni插件叫flannel,于是就调用了/opt/cni/bin/flannel文件,这个文件先会读取/run/flannel/subnet.env文件,这个文件也是kube-flannel启动时写入的,里面主要包含当前节点的子网信息,内容如下:
cat /run/flannel/subnet.env
FLANNEL_NETWORK=10.244.0.0/16
FLANNEL_SUBNET<