Flannel 是 CoreOS 针对 Kubernetes 设计的一个Overlay Network工具。相比于其他 CNI 模型,Flannel 只专注于网络通信没有提供 Network Policy 功能,是目前最为精简的一款CNI工具。

当前Flannel 支持的后端包括:

  • UDP:一种自定义的,基于UDP转发三层报文的隧道协议

  • VXLAN:基于UDP转发二层报文的隧道协议

  • host-gw:基于路由方案工作

  • 基于云服务的后端:AWS 、[AliVPC](AliCloud VPC Backend for Flannel) 、GCE

  • IPIP:IPIP也是Linux的原生隧道方案之一,相比VXLAN功能更加精简,但是只支持IPv4单播流量

  • IPSec:是一种对IP协议进行加密和认证隧道协议

上述后端中,VXLAN和Host-gw是最常用的,UDP用于一些老旧内核环境的场景,IPIP和IPSec均是0.10版本之后提供的功能。

Flannel 基于每个节点的flanneld客户端和一个中心存储工作,基本原理是:为每个主机分配一个subnet,多个subnet组成大的容器网络。

  • 节点对Subnet 的租期时间是24小时,节点每隔一小时会刷新他的租期

  • 当flanneld重启时,会根据节点名称从etcd上获取上次的Subnet信息,并且重用这个网段的IP资源

  • 用户可以通过手工的方式,控制etcd上节点信息的超期时间,从而实现固定的IP配置

  • Flannel 是不提供主机名dns能力的

Docker + Flannel

Flannel 可以应用在原生Docker的跨主机通信中,用户只要部署一个etcd服务,Flannel 就可以为docker提供跨主机容器网络。

PS:Flannel 只支持 ETCD V2版本的API

在ETCD 的/coreos.com/network/config写入Flannel的配置信息。所有配置项参考官网

PS:不同Backend有各自独立的配置项(参考

1
2
3
4
5
6
7
{
    "Network":"10.33.1.0/16",
    "SubnetLen":24,
    "Backend": {
        "Type":"udp"
    }
}

在ETCD上写入配置文件后,启动flanneld 进程

1
flanneld --etcd-endpoints=http://172.24.33.77:2379

flanneld 启动后会在 /run/flannel/subnet.env 中保存该节点的子网信息,如下:

1
2
3
4
FLANNEL_NETWORK=10.33.0.0/16
FLANNEL_SUBNET=10.33.15.1/24
FLANNEL_MTU=1472
FLANNEL_IPMASQ=false

设定docker进程的启动参数,编辑/usr/lib/systemd/system/docker.service

1
2
EnvironmentFile=/run/flannel/subnet.env
ExecStart=/usr/bin/dockerd -H fd:// --containerd=/run/containerd/containerd.sock --cluster-store=etcd://172.24.33.77:2379 --cluster-advertise=172.24.33.112:2375 --bip=${FLANNEL_SUBNET} --mtu=${FLANNEL_MTU}

K8S+Flannel

Flannel在Kubernetes上部署实在过于简单,不在赘述。简单记录一下不同模式的特点

  • Flannel的三种模式

    • UDP/VXLAN
    • Host-gw
  • 几种模式的区别

    • UDP和VXLAN的主要区别在于:
      • UDP 模式下flannel0是一个单纯的tun设备,UDP报文的封装在flanneld进程(用户态)中进行
      • VXLAN模式下flannel.1是一个vxlan设备,UDP报文的封装在内核中已经完成
    • host-gw模式
      • 不存在flannel.x设备,流量出口是宿主机的网卡
      • 基于二层网络来工作,将宿主机作为POD子网的网关,要求所有的物理机在一个二层子网
  • 所有模式下,POD的网络设备都是一个veth,一端在容器内(配置容器IP),另一端在宿主的网络空间的cni0网桥上