我是Docker的新手,并且有关于Docker容器网络的一些基本问题以寻求帮助,我阅读了有关Docker的网络配置的文章:https://docs.docker.com/articles/networking/
有一部分介绍了如何使用iptables使docker容器与外部通信,实际上我可以理解这一部分:
1从容器到外部,路由后链上有一个伪装规则,与SNAT相同
Chain POSTROUTING (policy ACCEPT)
target prot opt source destination
MASQUERADE all -- 172.17.0.0/16 !172.17.0.0/16
2从外部访问容器内部的服务,在预路由链中有一个DNAT规则,然后主机将其转发到docker0,容器最终将接收到数据包
Chain DOCKER (2 references)
target prot opt source destination
DNAT tcp -- 0.0.0.0/0 0.0.0.0/0 tcp dpt:49153 to:172.17.0.2:80
但是实际上,当我停止iptables服务时, docker 的网络仍然可以正常工作,我使用“iptables -L”和“iptables -t nat -L”进行检查,并且内核中没有规则,这是我的设置(假设10.170.28.0/24是外部网络,而172.17.0.0/16是docker容器的内部网络):
首先,iptables服务被关闭,fiter和nat表为空,如下所示:
iptables -t nat -L
Chain PREROUTING (policy ACCEPT)
target prot opt source destination
Chain POSTROUTING (policy ACCEPT)
target prot opt source destination
Chain OUTPUT (policy ACCEPT)
target prot opt source
iptables -L
Chain INPUT (policy ACCEPT)
target prot opt source destination
Chain FORWARD (policy ACCEPT)
target prot opt source destination
Chain OUTPUT (policy ACCEPT)
target prot opt source destination
这是主机中的路由表(主机ip为10.170.28.8):
route
Kernel IP routing table
Destination Gateway Genmask Flags Metric Ref Use Iface
10.170.28.0 * 255.255.255.192 U 0 0 0 eth0
192.168.0.0 * 255.255.255.0 U 0 0 0 br-data
link-local * 255.255.0.0 U 1002 0 0 eth0
link-local * 255.255.0.0 U 1003 0 0 eth1
link-local * 255.255.0.0 U 1040 0 0 br-data
172.17.0.0 * 255.255.0.0 U 0 0 0 docker0
default 10.170.28.1 0.0.0.0 UG 0 0 0 eth0
确实,上表中有规则将目标为172.17.0.0/16的数据包转发到桥接docker0,但在此之前,DNAT是谁将10.170.28.8转换为172.17.0.2(容器IP)的?从容器(172.17.0.0/16)到外部(10.170.28.0/24)的流量在没有SNAT或伪装的情况下如何工作?
最佳答案
首先,“停止” iptables是不可能的,它只是重置规则。如您的帖子所示,* filterINPUT链的策略为ALLOW。
Docker默认运行TCP转发代理,捕获所有转发端口的流量(通过ss -lnp | grep 49153
验证)。
在我的机器上进行的测试表明,无法进行出站连接:
如果省略2.,则ping会按预期工作。
$ docker --version
Docker version 18.09.2-ce, build 62479626f2
更多细节:
关于networking - 为什么当我关闭iptables时docker容器仍然可以与外部通信,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29629620/