Docker - 无主机路由

时间:2016-10-24 09:10:50

标签: docker

当我尝试连接到我的容器内的端口到另一个容器时,我不成功并获取,

root@ac1590a59fe5:/opt/f5massupgrade# curl -v https://172.17.0.1:6379
* Rebuilt URL to: https://172.17.0.1:6379/
* Hostname was NOT found in DNS cache
*   Trying 172.17.0.1...
* connect to 172.17.0.1 port 6379 failed: No route to host
* Failed to connect to 172.17.0.1 port 6379: No route to host
* Closing connection 0

从泊坞主机我成功

[root@docker-host ~]# curl -v https://172.17.0.1:6379/0
* About to connect() to 172.17.0.1 port 6379 (#0)
*   Trying 172.17.0.1...
* Connected to 172.17.0.1 (172.17.0.1) port 6379 (#0)
* Initializing NSS with certpath: sql:/etc/pki/nssdb
*   CAfile: /etc/pki/tls/certs/ca-bundle.crt
  CApath: none

如果我检查 iptables ,我可以看到问题,

[root@docker-host ~]#  iptables -S INPUT
-P INPUT ACCEPT
-A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
-A INPUT -p icmp -j ACCEPT
-A INPUT -i lo -j ACCEPT
-A INPUT -i docker0 -j ACCEPT
-A INPUT -p tcp -m state --state NEW -m tcp --dport 22 -j ACCEPT
-A INPUT -j REJECT --reject-with icmp-host-prohibited

所以我添加以下内容并且一切正常,

iptables -I INPUT 4 -i docker0 -j ACCEPT

我在这里错过了什么吗?

[root@docker-host ~]# docker version
Client:
 Version:         1.9.1
 API version:     1.21
 Package version: docker-common-1.9.1-40.el7.centos.x86_64
 Go version:      go1.4.2
 Git commit:      ab77bde/1.9.1
 Built:
 OS/Arch:         linux/amd64

Server:
 Version:         1.9.1
 API version:     1.21
 Package version: docker-common-1.9.1-40.el7.centos.x86_64
 Go version:      go1.4.2
 Git commit:      ab77bde/1.9.1
 Built:
 OS/Arch:         linux/amd64

谢谢,

8 个答案:

答案 0 :(得分:22)

如果仍然有人在CentOS 8或任何使用Firewalld的系统上仍然遇到此问题

尝试对firewalld进行以下设置

# Allows container to container communication, the solution to the problem
firewall-cmd --zone=public --add-masquerade --permanent

# standard http & https stuff
firewall-cmd --zone=public --add-port=80/tcp --permanent
firewall-cmd --zone=public --add-port=443/tcp --permanent
# + any other port you may need

# reload the firewall
firewall-cmd --reload

如果无法立即使用docker服务,您可能还需要重新启动,因为我已经阅读了许多指南,因此无需将docker0接口添加到受信任区域

我一直在为Docker容器设置Traefik反向代理,我从Traefik日志中仅收到502个响应,并且到我的容器没有路由错误。起初我以为这是我的Traefik设置,但事实证明它是@al的防火墙限制。提到。它为我指明了正确的方向,我从https://serverfault.com/questions/987686/no-network-connectivity-to-from-docker-ce-container-on-centos-8那里得到了答案

答案 1 :(得分:7)

以下自定义内核可调参数解决了Docker容器之间的“主机没有路由”的问题:

sysctl net.bridge.bridge-nf-call-iptables=0
sysctl net.bridge.bridge-nf-call-arptables=0
sysctl net.bridge.bridge-nf-call-ip6tables=0

这些控制是否将通过网桥的数据包​​发送到iptables进行处理。

请注意,如果将其添加到sysctl.conf中,根据Linux发行版的不同,它可能不会在重新启动期间作为已知错误自动应用。

答案 2 :(得分:7)

这些在Fedora 32上为我工作

$ sudo firewall-cmd --zone=public --add-masquerade --permanent
$ sudo firewall-cmd --reload
$ sudo systemctl restart docker

答案 3 :(得分:4)

我们在运行firewalld的RHEL盒上遇到了此问题。防火墙阻止容器托管主机访问(icmp流量除外)。

我们需要配置防火墙,以允许从Docker容器到主机的通信。在我们的示例中,容器位于子网172.27.0.0/16上的桥接网络中(通过docker network lsdocker inspect <network-name>确定)。 firewalld的防火墙规则可以通过以下方式更新:

firewall-cmd --permanent --zone=public --add-rich-rule='rule family=ipv4 source address=172.27.0.0/16 accept'
firewall-cmd --reload

这是解决问题的useful reference

答案 4 :(得分:1)

尝试使用标志--net设置为host来运行容器。

docker run --net host image 

答案 5 :(得分:0)

对我来说,问题是MAC地址冲突...不知道怎么回事...

答案 6 :(得分:0)

知道这是一个老问题,但是我只是遇到了这个问题,因此能够借助该线程解决它。

多亏了Samuel,我检查了我网络中的容器是否有冲突的MAC地址。就是这种情况,也是问题的原因。

现在,冲突的原因是我的撰写文件中使用了多个网络。我使用了由每个docker-compose创建的默认网络,并加入了现有网络。

码头工人选择MAC地址的方式是从02:42:ac:12:00:00开始,然后为每个后续容器使用下一个地址。显然,这是针对每个网络单独完成的。 Docker根据使用撰写创建的默认网络选择我的容器的MAC地址。生成的MAC在组合网络上是唯一的,但已在它加入的现有网络中使用。

here已描述了此问题,最近通过引入网络优先级解决了该问题。

答案 7 :(得分:0)

由于docker将创建两个网络,因此我希望打开所有相关IP。

# open all IPs starts with "172" so that all the containers may communicate each other
sudo firewall-cmd --permanent --zone=public --add-rich-rule='rule family=ipv4 source address=172.0.0.0/8 accept'
# make our container able to visit the network outside
sudo firewall-cmd --permanent --zone=public --add-masquerade
# apply the change
sudo firewall-cmd --reload

您可以访问/etc/firewalld/zones/public.xml以获取最终结果。

这是我的例子:

<?xml version="1.0" encoding="utf-8"?>
<zone>
  <short>Public</short>
  <description>For use in public areas. You do not trust the other computers on networks to not harm your computer. Only selected incoming connections are accepted.</description>
  <service name="ssh"/>
  <service name="dhcpv6-client"/>
  <masquerade/>
  <rule family="ipv4">
    <source address="172.0.0.0/8"/>
    <accept/>
  </rule>
</zone>

希望有帮助。