如何获取在 docker 中运行的服务的真实客户端 IP

Ale*_*rov 13 networking docker

我的场景:我想让我的基于 docker 的服务知道从网络调用它们的 IP(我的应用程序的要求。)

我在云 VPS、debian jessie 和 docker 1.12.2 上运行。

nc在详细模式下使用打开端口8080

docker run --rm -p "8080:8080" centos bash -c "yum install -y nc && nc -vv -kl -p 8080"
Run Code Online (Sandbox Code Playgroud)

说,VPS 有域example.com,从我的另一台机器,假设有dead:::::beef我调用的 IP

nc example.com 8080
Run Code Online (Sandbox Code Playgroud)

服务器说:

Ncat: Version 6.40 ( http://nmap.org/ncat )
Ncat: Listening on :::8080
Ncat: Listening on 0.0.0.0:8080
Ncat: Connection from 172.17.0.1.
Ncat: Connection from 172.17.0.1:49799.
Run Code Online (Sandbox Code Playgroud)

172.17.0.1位于服务器的本地网络上,当然与我的客户端无关。实际上:

docker0   Link encap:Ethernet  HWaddr ....
          inet addr:172.17.0.1  Bcast:0.0.0.0  Mask:255.255.0.0
Run Code Online (Sandbox Code Playgroud)

如果我以主机网络模式启动容器

docker run --rm --net=host -p "8080:8080" centos bash -c "yum install -y nc && nc -vv -kl -p 8080"
Run Code Online (Sandbox Code Playgroud)

并再次呼叫我的服务器

nc example.com 8080
Run Code Online (Sandbox Code Playgroud)

我得到了预期的结果:

Ncat: Connection from dead:::::beef.
Ncat: Connection from dead:::::beef:55650.
Run Code Online (Sandbox Code Playgroud)

我的问题是:

  • 为什么docker在不处于主机网络模式时“屏蔽”ips?我认为 docker daemon 进程可能是打开端口、接收连接,然后使用其自己的内部虚拟网络接口连接将其中继到容器进程的进程。nc因此在容器中运行只能看到调用来自 docker 守护进程的 IP。
  • (如何)我可以让我的 docker 服务知道外部 IP 调用它而不将其全部置于主机模式吗?

Les*_*ter 11

根据文档,默认驱动程序(即当您未--net=host在 中指定时docker run,是bridge网络驱动程序。

这不是关于 docker '屏蔽' IP 地址,而是关于如何bridgedhost网络模式变化。

就 Docker 而言,桥接网络使用软件桥接器,允许连接到同一桥接网络的容器进行通信,同时提供与未连接到该桥接网络的容器的隔离。Docker 网桥驱动程序会自动在宿主机中安装规则,以便不同网桥网络上的容器无法直接相互通信。

Docker 创建了一个隔离网络,以便桥接网络中的每个容器都可以进行通信,在您的情况下,它是docker0. 因此,默认情况下,您的 docker 主机上的容器在此网络内进行通信。

正如您现在可能已经发现的那样,yes172.17.0.1docker0网络上的默认路由,但这并不充当将数据包转发到目的地的路由器,因此您将其视为来自 netcat 输出的源。

事实上,您可以通过ss -tulnp在 docker 主机上运行来验证这一点。您应该会看到侦听端口 8080 的进程是 docker。

另一方面,使用主机网络驱动程序意味着容器和主机之间没有隔离。您可以通过ss -tulnp在 docker 主机上运行来验证这一点;您应该看到在套接字上而不是在 docker 上侦听的进程(在您的情况下,您应该看到nc)。

  • 我现在才意识到我已经回复了一个 2 年前未回复的帖子。即使 OP 不再需要答案,希望有人仍然会发现这很有用。 (3认同)
  • 这正是我们允许并鼓励回答旧问题的原因。1600人来到这里,没有找到答案。现在未来的人会。 (2认同)