Docker網路解決方案
阿新 • • 發佈:2019-02-13
原文地址:http://f.dataguru.cn/thread-576199-1-2.html
前言:前面的部分一直都是單機跑docker,但實際生產環境不可能只用一臺來跑。肯定會用到多臺,因為他們都是內部私有ip,那麼多臺主機之間的容器如何通訊?這個是個很頭疼的問題!目前主流幾種方法如下:
1、使用路由機制打通網路2、使用Open vSwitch(OVS)打通網路
3、使用flannel來打通網路
4、使用Quagga來實現自動學習路由
第一種:使用路由機制打通網路
使用Linux的路由來打通網路
優點:
- 常規路由技術
- 使用傳統網路技術
- 簡單
- 高效能
缺點:
- 與現有網路融為一體
- 靈活性低
現在有兩臺Docker例項:
file:///C:/Users/Don/Documents/My%20Knowledge/temp/d12921d0-891e-4a7f-9f37-4addd92a86fc_128_files/6325797f-dd7c-433e-aacc-dd447f7cbbaf.png
具體如圖,因為Docker預設的內部ip為172.17.42網段,所以必須要修改其中一臺的預設網段以免ip衝突。
#vim /etc/sysconfig/docker-network
DOCKER_NETWORK_OPTIONS= --bip=172.18.42.1/16 -H fd:// -H=unix:///var/run/docker.sock
#systemctl daemon-reload
#reboot
file:///C:/Users/Don/Documents/My%20Knowledge/temp/d12921d0-891e-4a7f-9f37-4addd92a86fc_128_files/96e55b20-d530-4526-ac7a-7763b2628350.png
ok。現在就可以開始操作了。
其實就是執行兩臺route add命令
docker 130上執行 route add -net 172.18.0.0/16 gw 192.168.18.128
docker 128上執行 route add -net 172.17.0.0/16 gw 192.168.18.130
ok,現在兩臺宿主機裡的容器就可以通訊了。
第二種:使用Open vSwitch(OVS)打通網路
是一種主流的虛擬化大二層技術
優點:
- 靈活
- 對現有物理網路沒要求
- 業界主流
缺點:
- 軟體封裝導致效能下降
- 複雜度相對較高
- 排錯難度高
流程圖如下:
file:///C:/Users/Don/Documents/My%20Knowledge/temp/d12921d0-891e-4a7f-9f37-4addd92a86fc_128_files/75f44505-cf9f-47bf-bc49-8fa40b8d3f03.png
file:///C:/Users/Don/Documents/My%20Knowledge/temp/d12921d0-891e-4a7f-9f37-4addd92a86fc_128_files/33f2ed6e-ad14-4839-87ac-ad43333d8c3d.png
首先安裝ovs的rpm包
# yum install openvswitch-2.4.0-1.x86_64.rpm #安裝軟體包
# /etc/init.d/openvswitch restart #重啟服務
# /etc/init.d/openvswitch status #檢視狀態
安裝網橋管理工具
#yum -y install bridge-utils
配置網路
ovs-vsctl add-br br0
ovs-vsctl add-port br0 gre1--set interface gre1 type=gre option:remote_ip=192.168.18.128
#新增br0到本地docker0,使得容器流量通過ovs流經tunnel
brctl addif docker0 br0
ip link set dev br0 up
ip link set dev docker0 up
iptables -t nat-F; iptables-F
ip route add 172.17.0.0/16 dev docker0
其餘節點同樣的配置,注意ip地址即可。
第三種:使用flannel來打通網路
新設計的Flannel,一種結合了路由機制與隧道技術
原理:每個主機配置一個ip段和子網個數。例如,可以配置一個覆蓋網路使用 10.100.0.0/16段,每個主機/24個子網。因此主機a可以接受10.100.5.0/24,主機B可以接受10.100.18.0/24的包。flannel使用etcd來維護分配的子網到實際的ip地址之間的對映。對於資料路徑,flannel 使用udp來封裝ip資料報,轉發到遠端主機。選擇UDP作為轉發協議是因為他能穿透防火牆。例如,AWS Classic無法轉發IPoIP or GRE 網路包,是因為它的安全組僅僅支援TCP/UDP/ICMP。
下圖解釋了資料報通過覆蓋網路轉發的路線:
file:///C:/Users/Don/Documents/My%20Knowledge/temp/d12921d0-891e-4a7f-9f37-4addd92a86fc_128_files/b0997f01-6d7f-4265-993d-f17bde472efc.jpg
部署也不是很複雜,僅需要etcd和flannel兩項支援即可。
etcd一般部署在單獨機器上,那麼flannel就部署在docker節點上,每個docker節點上都需部署。
1、部署etcd,假設地址為192.168.1.121
yum -y install etcd #安裝軟體包
vim /etc/etcd/etcd.conf #修改配置檔案
修改為如下:(預設只監聽本地迴環地址)
ETCD_LISTEN_CLIENT_URLS="http://0.0.0.0:2379"
systemctl restart etcd #重啟服務
etcdctl set /coreos.com/network/config '{ "Network": "10.1.0.0/16" }' #新增一條網路配置記錄,這個配置將用於flannel分配給每個Docker的虛擬IP地址段
2、部署flannel
tar zxf flannel-0.5.5-linux-amd64.tar.gz #解壓檔案
cp flannel-0.5.5/*/usr/bin/ #拷貝可執行檔案至系統變數path
使用systemd來管理flannel服務
vim /usr/lib/systemd/system/flanneld.service
[Unit]
Description=Flanneld overlay address etcd agent
After=network.target
Before=docker.service
[Service]
Type=notify
EnvironmentFile=/etc/sysconfig/flanneld
EnvironmentFile=-/etc/sysconfig/docker-network
ExecStart=/usr/bin/flanneld -etcd-endpoints=${FLANNEL_ETCD} $FLANNEL_OPTIONS
[Install]
RequiredBy=docker.service
WantedBy=multi-user.target
設定etcd地址
vim /etc/sysconfig/flanneld
FLANNEL_ETCD= "http://192.168.1.121:2379"
由於flannel將覆蓋docker0網橋,所以如果Docker服務已啟動,則停止Docker服務
編寫flannel啟動指令碼,並加入自啟動
vim /etc/init.d/start_flannel.sh
#!/bin/bash
systemctl stop docker #停止docker服務
systemctl restart flanneld #啟動flannel服務
mk-docker-opts.sh -i #生成環境變數
source /run/flannel/subnet.env #將環境變數生效
ifconfig docker0 ${FLANNEL_SUBNET} #設定docker0的網絡卡ip
systemctl start docker #啟動docker服務
ok,現在跨主機容器間已經可以通訊。
第四種:使用Quagga來實現自動學習路由
其實這種方式是基於第一種方式的路由技術,只不過路由資訊不需要自己手動新增,而是自動學習。試想一下,如果有10臺docker,那麼每臺docker就需要手動寫9條路由資訊,是不是很慘?
Linux上安裝路由器的軟體名為Quagga,它可以配置很多種企業級的動態路由協議。我使用的是RIPV2和OSPF同時開啟,但安裝Quagga的方法和配置命令,太過於繁瑣。所以網上有大神將其Docker化了。
下載Quagga映象:
docker pull index.alauda.cn/georce/router
特別需要注意的是:docker0的網段不能一樣,所以需要修改docker的子網地址,參考第一種的設定辦法
執行映象:
docker run-itd --name=router--privileged--net=host index.alauda.cn/georce/router
執行 ip route 檢視下路由表,已有別的docker0的網段資訊。
file:///C:/Users/Don/Documents/My%20Knowledge/temp/d12921d0-891e-4a7f-9f37-4addd92a86fc_128_files/4ee4e27c-94ed-4b68-8cd3-838467346fe3.png
file:///C:/Users/Don/Documents/My%20Knowledge/temp/d12921d0-891e-4a7f-9f37-4addd92a86fc_128_files/cd3ce34f-621a-488b-818d-ff2c69e365f0.png