在 centos7
運行 docker
容器應用時,須要鏈接宿主機的 mysql
的 3306
端口,發現鏈接不上,docker
容器沒法訪問宿主機的 mysql
數據庫。可是,在容器內訪問外部網絡是能夠 ping
通的。mysql
在 centos7
上部署 docker
容器,其網絡模式採用的是 bridge
模式。
啓動 docker
時,docker
進程會建立一個名爲 docker0
的虛擬網橋,用於宿主機與容器之間的通訊。當啓動一個 docker
容器時,docker
容器將會附加到虛擬網橋上,容器內的報文經過 docker0
向外轉發。sql
若是 docker
容器訪問宿主機,那麼 docker0
網橋將報文直接轉發到本機,報文的源地址是 docker0
網段的地址。而若是 docker
容器訪問宿主機之外的機器,docker
的 SNAT
網橋會將報文的源地址轉換爲宿主機的地址,經過宿主機的網卡向外發送。docker
所以,當 docker
容器訪問宿主機時,若是宿主機服務端口會被防火牆攔截,那麼就沒法連通宿主機,出現 No route to host
的錯誤。數據庫
而訪問宿主機所在局域網內的其餘機器,因爲報文的源地址是宿主機 ip
,所以,不會被目的機器防火牆攔截,因此能夠訪問。centos
首先設置了 mysql
的配置文件,保證 mysql
能夠被任何 ip
訪問:安全
[mysqld] bind-address = 0.0.0.0
修改完配置文件重啓生效。
但爲了安全考慮,防火牆的 3306
端口仍然是不開放外網訪問的。 bash
容器訪問宿主機的地址使用 eth0
的地址,即宿主機內網 ip
地址。
運行 ipconfig
命令,查看網絡的虛擬網橋相關信息。 網絡
注意:宿主機會把容器 ip
地址段當成外網 ip
。(當前說明是 centos7
環境)測試
編輯防火牆文件 /etc/firewalld/zones/public.xml
,添加下面 docker0
地址段到配置:centos7
<rule family="ipv4"> <source address="172.18.0.0/16"/> <accept/> </rule>
重啓防火牆,docker
容器便可正常訪問宿主機端口。
service firewalld restart
🎨 若是有用到 docker-compose
命令,則會自動建立一個名爲 br-"docker network id"
的虛擬網橋。
🎨 此時一樣須要將虛擬網橋地址段配置到防火牆白名單,才能正常訪問,添加配置:
<rule family="ipv4"> <source address="172.20.0.0/16"/> <accept/> </rule>
在容器中測試宿主機端口是否能夠鏈接,可使用 wget 內網ip:端口
命令。
$ wget 172.17.25.162:3306 wget: can not connect to remote host (172.17.25.162): Host is unreachable #不能夠鏈接 $ wget 172.17.25.162:3306 wget: bad header line: 5.7.29-log #能夠鏈接