Kubernetes设计了网络模型,但却将它的实现交给了网络插件,CNI网络插件最主要的功能就是实现POD资源能够跨宿主机进行通信。
常见的CNI网络插件:
- Flannel
- Calico
- Canal
- Contiv
- OpenContrail
- NSX-T
- Kube-router
在node中的pod不能互相通信前:
Kubelet—-pod—-apiserver—-scheduler—-controller-manager—apiserver—-VIP(10.4.7.10:7443)—-Node2中的kubelet—pod
1.集群架构
主机名 | 角色 | IP地址 |
---|---|---|
k8s-40.host.com | flannel | 192.168.10.40 |
k8s-50.host.com | flannel | 192.168.10.50 |
部署方法以k8s-40.host.com为例
1.1.下载软件,解压,做软链接
[root@k8s-40 ~]# cd /opt/src/
[root@k8s-40 src]# wget https://github.com/coreos/flannel/releases/download/v0.11.0/flannel-v0.11.0-linux-amd64.tar.gz
[root@k8s-40 src]# mkdir /opt/flannel-v0.11.0
[root@k8s-40 src]# tar xf flannel-v0.11.0-linux-amd64.tar.gz -C /opt/flannel-v0.11.0/
[root@k8s-40 src]# ln -s /opt/flannel-v0.11.0/ /opt/flannel
1.2.创建目录
[root@k8s-40 src]# cd /opt/flannel
[root@k8s-40 flannel]# mkdir /opt/flannel/cert
1.3.拷贝证书文件
到管理主机上传送证书
[root@k8s-60 certs]# scp ca.pem client.pem client-key.pem k8s-40:/opt/flannel/cert
[root@k8s-60 certs]# scp ca.pem client.pem client-key.pem k8s-50:/opt/flannel/cert
1.4.创建配置
[root@k8s-40 cert]# cd ..
[root@k8s-40 flannel]# vi subnet.env
FLANNEL_NETWORK=172.7.0.0/16
FLANNEL_SUBNET=172.7.40.1/24
FLANNEL_MTU=1500
FLANNEL_IPMASQ=false
1.5.创建启动脚本
[root@k8s-40 flannel]# vi flanneld.sh
#!/bin/sh
./flanneld \
--public-ip=192.168.10.40 \
--etcd-endpoints=https://192.168.10.30:2379,https://192.168.10.40:2379,https://192.168.10.50:2379 \
--etcd-keyfile=./cert/client-key.pem \
--etcd-certfile=./cert/client.pem \
--etcd-cafile=./cert/ca.pem \
--iface=ens33 \ # 注意本机网卡名
--subnet-file=./subnet.env \
--healthz-port=2401
注意:flannel集群各主机的启动脚本略有不同,部署其它脚本时注意修改
1.6.授权和创建日志目录
[root@k8s-40 flannel]# chmod +x flanneld.sh
[root@k8s-40 flannel]# mkdir -p /data/logs/flanneld
1.7.创建supervisor配置
[root@k8s-40 flannel]# vi /etc/supervisord.d/flannel.ini
[program:flanneld-10-40]
command=/opt/flannel/flanneld.sh ; the program (relative uses PATH, can take args)
numprocs=1 ; number of processes copies to start (def 1)
directory=/opt/flannel ; directory to cwd to before exec (def no cwd)
autostart=true ; start at supervisord start (default: true)
autorestart=true ; retstart at unexpected quit (default: true)
startsecs=30 ; number of secs prog must stay running (def. 1)
startretries=3 ; max # of serial start failures (default 3)
exitcodes=0,2 ; 'expected' exit codes for process (default 0,2)
stopsignal=QUIT ; signal used to kill process (default TERM)
stopwaitsecs=10 ; max num secs to wait b4 SIGKILL (default 10)
user=root ; setuid to this UNIX account to run the program
redirect_stderr=true ; redirect proc stderr to stdout (default false)
stdout_logfile=/data/logs/flanneld/flanneld.stdout.log ; stderr log path, NONE for none; default AUTO
stdout_logfile_maxbytes=64MB ; max # logfile bytes b4 rotation (default 50MB)
stdout_logfile_backups=4 ; # of stdout logfile backups (default 10)
stdout_capture_maxbytes=1MB ; number of bytes in 'capturemode' (default 0)
stdout_events_enabled=false ; emit events on stdout writes (default false)
1.8 操作etcd,增加host-gw
flannel是依赖etcd存储网络信息的
2.flannel host-gw模型(三选一)
# 在etcd集群任意一个节点执行就可以
[root@k8s-40 etcd]# ./etcdctl set /coreos.com/network/config '{"Network": "172.7.0.0/16", "Backend": {"Type": "host-gw"}}'
验证:
[root@k8s-40 etcd]# ./etcdctl get /coreos.com/network/config
{"Network": "172.7.0.0/16", "Backend": {"Type": "host-gw"}}
2.1.启动服务并检查
[root@k8s-21 flannel]# supervisorctl update
[root@k8s-21 flannel]# supervisorctl status
3.flannel vxlan模型(三选一)
1.supervisor stop flanneld-7-[21.22]
2.删除host-gw模型创建的路由
route del -net 172.7.21.0/24 gw 10.4.7.21 hdss7-22.host.com上
route del -net 172.7.22.0/24 gw 10.4.7.22 hdss7-21.host.com上
3.在etcd修改
./etcdctl get /coreos.com/network/config
./etcdctl rm /coreos.com/network/config # 先删除host-gw模式设置的
./etcdctl set /coreos.com/network/config '{"Network": "172.7.0.0/16", "Backend": {"Type": "VxLAN"}}'
4.supervisor start flanneld-7-[21.22]
4.flannel 直接路由模型(三选一)
'{"Network": "172.7.0.0/16", "Backend": {"Type": "VxLAN","Directrouting": true}}'
5.flannel之SNAT规则优化
5.1.优化iptables规则
5.1.1.安装iptables-services并设置开机启动
[root@k8s-21 ~]# yum install iptables-services -y
[root@k8s-21 ~]# systemctl start iptables
[root@k8s-21 ~]# systemctl enable iptables
5.1.2.优化各运算节点的SNAT规则
iptables-save | grep -i postrouting
[root@k8s-21 ~]# iptables -t nat -D POSTROUTING -s 172.7.21.0/24 ! -o docker0 -j MASQUERADE
[root@k8s-21 ~]# iptables -t nat -I POSTROUTING -s 172.7.21.0/24 ! -d 172.7.0.0/16 ! -o docker0 -j MASQUERADE
## 注意来源地址172.7.21.0/24,目的地址是除172.7.0.0/16和docker0网卡出网的 地址
## 即容器之间不用转换 真实ip
5.2.保存iptables规则
5.2.1.各运算节点保存iptables规则
service iptables save
如果不行,查看拒绝规则,再删掉
iptables-save | grep -i reject
iptables -t filter -D INPUT -j REJECT --reject-with icmp-host-prohibited
iptables -t filter -D FORWARD -j REJECT --reject-with icmp-host-prohibited
再保存
iptables-save > /etc/sysconfig/iptables
视频:https://www.bilibili.com/video/BV1PJ411h7Sw?p=33
生产经验
k8s集群中的一定要做SNAT规则优化,容器、Pod之间要互相看到真实ip
如果是小集群,不用安装flannel,也可以实现pod与pod通信,加路由和防火墙规则就行
需要172.7.40.0/24和172.7.50.0/24通信,则需要两条静态路由
node-40加172.7.50.0/24的静态路由
route add -net 172.7.50.0/24 gw 192.168.10.50 dev ens33
加了之后可以curl通:curl 172.7.50.2
再添加一条防火墙规则
iptables -t filter -I FORWARD -d 172.7.50.0/24 -j ACCEPT
node-50加172.7.40.0/24的静态路由
route add -net 172.7.40.0/24 gw 192.168.10.40 dev ens33
加了之后可以curl通:curl 172.7.40.2
再添加一条防火墙规则
iptables -t filter -I FORWARD -d 172.7.50.0/24 -j ACCEPT
flannel原理也是类似的,就是添加了路由
二层网络:网络中的服务器,指向同一个网关