七.部署flannel網絡
kubernetes支持基於vxlan方式的flannel與weave網絡,基於BGP路由的Calico網絡,本節采用flannel網絡。
Flannel網絡采用etcd等kv存儲做集中控制,在每個host生成1個subnet,每個host上的subnet通過vxlan方式打通。
1. 創建flannel TLS證書與私鑰
etcd集群啟用了雙向TLS認證,需要為flannel網絡指定與etcd集群通信的CA與秘鑰。
1)創建flannel證書簽名請求
[root@kubenode1 ~]# mkdir -p /etc/kubernetes/flannel [root@kubenode1 ~]# cd /etc/kubernetes/flannel/ [root@kubenode1 flannel]# touch flanneld-csr.json # hosts字段留空 [root@kubenode1 flannel]# vim flanneld-csr.json { "CN": "flanneld", "hosts": [], "key": { "algo": "rsa", "size": 2048 }, "names": [ { "C": "CN", "ST": "ChengDu", "L": "ChengDu", "O": "k8s", "OU": "cloudteam" } ] }
2)生成flannel證書與私鑰
[root@kubenode1 flannel]# cfssl gencert -ca=/etc/kubernetes/ssl/ca.pem \ -ca-key=/etc/kubernetes/ssl/ca-key.pem \ -config=/etc/kubernetes/ssl/ca-config.json \ -profile=kubernetes flanneld-csr.json | cfssljson -bare flanneld

# 分發flanneld.pem,flanneld-key.pem [root@kubenode1 flannel]# scp flanneld.pem flanneld-key.pem root@172.30.200.22:/etc/kubernetes/flannel/ [root@kubenode1 flannel]# scp flanneld.pem flanneld-key.pem root@172.30.200.23:/etc/kubernetes/flannel/
2. 在etcd寫入集群Pod網段信息
# 在etcd集群(1個節點操作即可)寫入”key-value”,即Pod網段信息,”key”指”${FLANNEL_ETCD_PREFIX}/config”; # etcdctl采用的是etcd v2 api; # 注意其中使用的環境變量,${CLUSTER_CIDR}需要與kube-controller-manager的參數--cluster-cidr一致; [root@kubenode1 flannel]# etcdctl --endpoints=${ETCD_ENDPOINTS} \ --ca-file=/etc/kubernetes/ssl/ca.pem \ --cert-file=/etc/kubernetes/flannel/flanneld.pem \ --key-file=/etc/kubernetes/flannel/flanneld-key.pem \ set ${FLANNEL_ETCD_PREFIX}/config '{"Network":"'${CLUSTER_CIDR}'", "SubnetLen": 24, "Backend": {"Type": "vxlan"}}'

3. 下載部署flannel
[root@kubenode1 ~]# cd /usr/local/src/ [root@kubenode1 src]# wget https://github.com/coreos/flannel/releases/download/v0.10.0/flannel-v0.10.0-linux-amd64.tar.gz [root@kubenode1 src]# mkdir -p /usr/local/flannel [root@kubenode1 src]# tar -zxvf flannel-v0.10.0-linux-amd64.tar.gz [root@kubenode1 src]# cd /usr/local/flannel/
4. 配置flanneld的systemd unit文件
[root@kubenode1 src]# cd /usr/local/flannel/ [root@kubenode1 flannel]# touch /usr/lib/systemd/system/flanneld.service # EnvironmentFile:這里將flanneld的啟動參數放在unit文件之外,修改后不用重載; # ExecStart:啟動文件位置,並帶上指定參數的變量; # ExecStartPost:啟動后需要執行的操作,這里利用mk-docker-opts.sh腳本將分配到flanneld的Pod subnet信息寫入到/run/flannel/docker文件中,docker服務啟動時調用/run/flannel/docker文件中的參數設置docker0網橋; # RequiredBy:docker.service依賴與flanneld服務; # flanneld使用系統默認路由所在接口封裝vxlan與其他節點通信,多網口時可使用--iface選項指定通信接口 [root@kubenode1 flannel]# vim /usr/lib/systemd/system/flanneld.service [Unit] Description=Flanneld overlay address etcd agent Documentation=https://github.com/coreos After=network.target After=network-online.target Wants=network-online.target After=etcd.service Before=docker.service [Service] Type=notify EnvironmentFile=/usr/local/flannel/flanneld.conf ExecStart=/usr/local/flannel/flanneld $FLANNELD_ARGS ExecStartPost=/usr/local/flannel/mk-docker-opts.sh -k DOCKER_NETWORK_OPTIONS -d /run/flannel/docker Restart=on-failure [Install] WantedBy=multi-user.target RequiredBy=docker.service # 啟動參數文件,“-etcd-prefix”指定flannel網絡配置存儲路徑,注意與寫入etcd集群的“k-v”路徑對應 [root@kubenode1 flannel]# touch /usr/local/flannel/flanneld.conf [root@kubenode1 flannel]# vim /usr/local/flannel/flanneld.conf FLANNELD_ARGS="-etcd-cafile=/etc/kubernetes/ssl/ca.pem \ -etcd-certfile=/etc/kubernetes/flannel/flanneld.pem \ -etcd-keyfile=/etc/kubernetes/flannel/flanneld-key.pem \ -etcd-endpoints=https://172.30.200.21:2379,https://172.30.200.22:2379,https://172.30.200.23:2379 \ -etcd-prefix=/kubernetes/network"
5. 修改docker的systemd unit文件
# 增加EnvironmentFile項:指定啟動參數位置,注意與flanneld設定的文件對應; # 修改ExecStart項:unix為開放本地客戶端調用dockerd接口,ip地址為開放遠端客戶端調用dockerd接口,指定參數注意與flanneld設定的參數名對應 [root@kubenode1 flannel]# vim /usr/lib/systemd/system/docker.service [Unit] Description=Docker Application Container Engine Documentation=https://docs.docker.com After=network.target [Service] Type=notify EnvironmentFile=-/run/flannel/docker ExecStart=/usr/bin/dockerd -H unix:///var/run/docker.sock -H 0.0.0.0:2375 $DOCKER_NETWORK_OPTIONS ExecReload=/bin/kill -s HUP $MAINPID LimitNOFILE=infinity LimitNPROC=infinity LimitCORE=infinity TimeoutStartSec=0 Delegate=yes KillMode=process [Install] WantedBy=multi-user.target # docker啟動參數文件,創建相應的目錄與文件即可,不用編輯; # mk-docker-opts.sh會利用從etcd分配到的信息編輯此文件 [root@kubenode1 flannel]# mkdir -p /run/flannel [root@kubenode1 flannel]# touch /run/flannel/docker
6. 啟動flanneld
# docker服務應該在flanneld服務之后啟動 [root@kubenode1 flannel]# systemctl daemon-reload [root@kubenode1 flannel]# systemctl enable flanneld [root@kubenode1 flannel]# systemctl stop docker [root@kubenode1 flannel]# systemctl start flanneld [root@kubenode1 flannel]# systemctl start docker
7. 驗證
1)網口
# docker0已從etcd獲取Pod網段內1個24位subnet的地址,取代默認的172.17.0.0/16的地址; # 對外(除跨主機的容器通信),采用默認的bridge網絡,以nat的形式與外部通信; # 同時生成一個flannel.1網口,跨主機的通信即通過flannel.1做vxlan的封裝發出; # flannel為每台主機分配獨立的24位subnet,flannel.1將這些subnet連接起來,相互之間可路由; # flannel 沒有提供隔離 [root@kubenode1 ~]# ip address show

2)路由
# 在其余節點啟動flanneld服務后,相關路由會被推送到各host主機; # 以下是kubenode1到kubenode2&kubenode3的路由,通過flannel.1做封裝 [root@kubenode1 ~]# ip route

3)查看etcd分配到各flanneld的Pod網段信息
# 集群Pod網段,即寫入etcd的Pod網段信息 [root@kubenode1 ~]# etcdctl \ --endpoints=${ETCD_ENDPOINTS} \ --ca-file=/etc/kubernetes/ssl/ca.pem \ --cert-file=/etc/kubernetes/flannel/flanneld.pem \ --key-file=/etc/kubernetes/flannel/flanneld-key.pem \ get ${FLANNEL_ETCD_PREFIX}/config

# 已分配的Pod subnet列表 [root@kubenode1 ~]# etcdctl \ --endpoints=${ETCD_ENDPOINTS} \ --ca-file=/etc/kubernetes/ssl/ca.pem \ --cert-file=/etc/kubernetes/flannel/flanneld.pem \ --key-file=/etc/kubernetes/flannel/flanneld-key.pem \ ls ${FLANNEL_ETCD_PREFIX}/subnets

# 某Pod subnet對應的flanneld進程監聽的ip與網絡參數; # 任選1個Pod subnet列表,如10.254.3.0/24,可查詢到其所在host節點與vtep mac地址 [root@kubenode1 ~]# etcdctl \ --endpoints=${ETCD_ENDPOINTS} \ --ca-file=/etc/kubernetes/ssl/ca.pem \ --cert-file=/etc/kubernetes/flannel/flanneld.pem \ --key-file=/etc/kubernetes/flannel/flanneld-key.pem \ get ${FLANNEL_ETCD_PREFIX}/subnets/10.254.3.0-24

4)ping測試
# iptables input鏈最后一條規則“-A INPUT -j REJECT --reject-with icmp-host-prohibited”,即不滿足input已定義放行的規則,到鏈的最后則拒絕訪問,同時返回"icmp-host-prohibited"消息;而flannel.1之間是通過udp封裝的vxlan通信,input鏈默認未放行udp,導致docker0之間的ping包會被丟棄;
# 不能重啟iptables,docker服務啟動,或Pod subnet有變更時會向iptables添加規則,重啟會使相關規則丟失;
# 同時可以將/etc/sysconfig/iptables中下面兩條規則注釋掉
[root@kubenode1 ~]# iptables -D INPUT -j REJECT --reject-with icmp-host-prohibited
[root@kubenode1 ~]# iptables -D FORWARD -j REJECT --reject-with icmp-host-prohibited
# ping測試
[root@kubenode1 ~]# ping 10.254.3.1
[root@kubenode1 ~]# ping 10.254.71.1

