Centos 7 firewallD 如何配置允许docker容器自由访问主机的网络端口?

ada*_*dev 47 firewall centos docker firewalld

我在 CentOS 7 上安装了 docker 并且我正在运行 firewallD。

从我的容器内部,转到主机(默认 172.17.42.1)

开启防火墙

container# nc -v  172.17.42.1  4243
nc: connect to 172.17.42.1 port 4243 (tcp) failed: No route to host
Run Code Online (Sandbox Code Playgroud)

防火墙关闭

container# nc -v  172.17.42.1  4243
Connection to 172.17.42.1 4243 port [tcp/*] succeeded!
Run Code Online (Sandbox Code Playgroud)

我已经阅读了 firewalld 上的文档,但我并不完全理解它们。有没有办法简单地允许 docker 容器中的所有内容(我猜在 docker0 适配器上)不受限制地访问主机?

小智 51

也许比之前的答案更好;

firewall-cmd --permanent --zone=trusted --change-interface=docker0
firewall-cmd --permanent --zone=trusted --add-port=4243/tcp
firewall-cmd --reload
Run Code Online (Sandbox Code Playgroud)

  • 我相信 `add-port` 是多余的。如果 `docker0` 被标记为受信任,则无论如何都会让该端口通过。 (13认同)
  • @MattHughes 它在没有`add-port` 的情况下对我有用。您还需要**重启docker**。 (7认同)
  • 这导致了`创建默认“桥接”网络时出错:无法对 NAT 链进行编程:ZONE_CONFLICT:'docker0' 已经绑定到一个区域` 对我来说,即使在完全重启之后 (2认同)
  • @Jay如果您有更好的答案,请将其写为新答案,而不是编辑现有答案。如果社区同意您的观点,您将以点赞的形式获得奖励。您可以在答案中明确添加对要改进的答案的引用,以指出现有答案可能存在的问题。 (2认同)

ada*_*dev 13

这些命令起到了作用:

firewall-cmd --permanent --zone=trusted --add-interface=docker0
firewall-cmd --permanent --zone=trusted --add-port=4243/tcp
Run Code Online (Sandbox Code Playgroud)


Kev*_*ane 6

公认的解决方案适用于某些人而不适用于其他人的原因之一在于 firewalld 的设计问题。Firewalld 只处理任何连接的第一个匹配区域。它还在基于接口的区域之前处理基于 IP 地址的区域。只要您的任何区域恰好包含 docker 正在使用的 IP 地址,受信任区域中的 ACCEPT 规则将永远不会得到处理。

要验证这一点,您可以查看生成的 iptables 规则,除非您使用的是 nbt 后端:

iptables -vnL | less
Run Code Online (Sandbox Code Playgroud)

解决方案是使用 firewalld 直接规则而不是受信任区域。直接规则总是首先被处理。例如,对于端口 3306(即本地主机上的 mysqld),您需要以下规则:

/bin/firewall-cmd --direct --permanent --add-rule ipv4 filter INPUT 10 -p tcp --dport 3306 -i docker0 -j ACCEPT
Run Code Online (Sandbox Code Playgroud)

如果您在没有 --permanent 开关的情况下重复相同的命令,firewalld 会为您即时进行更改,您不需要重新启动 docker。

第二个原因是,根据 docker 的版本和您配置的网络,流量实际上可能不会流经 docker0 接口,而是通过单独的桥接接口。您可以使用命令查看该界面

ip address show
Run Code Online (Sandbox Code Playgroud)

您将不得不使用此桥接接口重复上面的直接规则语句。

您还可以在 docker 中指定自己的网络。这篇文章描述了这个过程:https : //serverfault.com/questions/885470/how-to-configure-firewall-on-user-defined-docker-bridge

简短版本是您在 docker 文件中指定网络部分,如下所示:

version: '3'
  .
  .
  .
networks:
  mynetwork:
    driver_opts:
      com.docker.network.bridge.name: mynetwork_name
Run Code Online (Sandbox Code Playgroud)

您也可以在命令行上执行此操作。


小智 6

我也有这个问题;这对我有用:

firewall-cmd --zone=public --add-masquerade --permanent
Run Code Online (Sandbox Code Playgroud)

来自:https : //serverfault.com/questions/987686/no-network-connectivity-to-from-docker-ce-container-on-centos-8