繁体   English   中英

容器内的 Docker Macvlan 网络无法连接到自己的主机

[英]Docker Macvlan network inside container is not reaching to its own host

我在 2 个 docker 主机之间设置了 Macvlan 网络,如下所示:

主机设置:HOST_1 ens192: 172.18.0.21

创建 macvlan 网桥接口

docker network  create  -d macvlan \
--subnet=172.18.0.0/22 \
--gateway=172.18.0.1 \
--ip-range=172.18.1.0/28 \
-o macvlan_mode=bridge \
-o parent=ens192 macvlan

创建 macvlan 接口 HOST_1

ip link add ens192.br link ens192 type macvlan mode bridge
ip addr add 172.18.1.0/28 dev ens192.br
ip link set dev ens192.br up

主机设置:HOST_2 ens192: 172.18.0.23

创建 macvlan 网桥接口

docker network  create  -d macvlan \
--subnet=172.18.0.0/22 \
--gateway=172.18.0.1 \
--ip-range=172.18.1.16/28 \
-o macvlan_mode=bridge \
-o parent=ens192 macvlan

在 HOST_2 中创建 macvlan 接口

ip link add ens192.br link ens192 type macvlan mode bridge
ip addr add 172.18.1.16/28 dev ens192.br
ip link set dev ens192.br up

容器设置

在两个主机上创建容器

HOST_1# docker run --net=macvlan -it --name macvlan_1 --rm alpine /bin/sh
HOST_2# docker run --net=macvlan -it --name macvlan_1 --rm alpine /bin/sh

HOST_1 中的 CONTAINER_1

24: eth0@if2: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue state UNKNOWN
    link/ether 02:42:ac:12:01:00 brd ff:ff:ff:ff:ff:ff
    inet 172.18.1.0/22 brd 172.18.3.255 scope global eth0
       valid_lft forever preferred_lft forever

HOST_2 中的 CONTAINER_2

21: eth0@if2: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue state UNKNOWN
    link/ether 02:42:ac:12:01:10 brd ff:ff:ff:ff:ff:ff
    inet 172.18.1.16/22 brd 172.18.3.255 scope global eth0
       valid_lft forever preferred_lft forever

CONTAINER_1 和 CONTAINER_2 中的路由表

Kernel IP routing table
Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
0.0.0.0         172.18.0.1      0.0.0.0         UG    0      0        0 eth0
172.18.0.0      0.0.0.0         255.255.252.0   U     0      0        0 eth0

场景

HOST_1 (172.18.0.21) <-> HOST_2 (172.18.0.23) = OK(反之亦然)

HOST_1 (172.18.0.21) -> CONTAINER_1 (172.18.1.0) and CONTAINER_2 (172.18.1.16) = OK

HOST_2 (172.18.0.23) -> CONTAINER_1 (172.18.1.0) and CONTAINER_2 (172.18.1.16) = OK

CONTAINER_1 (172.18.1.0) -> HOST_2 (172.18.0.23) = OK

CONTAINER_2 (172.18.1.16) -> HOST_1 (172.18.0.21) = OK

CONTAINER_1 (172.18.1.0) <-> CONTAINER_2 (172.18.1.16) = OK(反之亦然)

CONTAINER_1 (172.18.1.0) -> HOST_1 (172.18.0.21) = 失败

CONTAINER_2 (172.18.1.16) -> HOST_2 (172.18.0.23) = 失败

问题

我非常接近我想要实现的解决方案,除了这 1 个单一问题。 我怎样才能让容器连接到它自己的主机。 如果有解决方案,我想知道如何在 ESXi 虚拟化角度进行配置,如果有任何区别,也可以使用裸机配置

这是 macvlan 的定义行为,是设计使然。 请参阅Docker Macvlan 文档

  • 使用 macvlan 时,您无法 ping 或与默认命名空间 IP 地址通信。 例如,如果您创建一个容器并尝试 ping Docker 主机的 eth0,它将无法正常工作。 该流量由内核模块本身明确过滤,以提供额外的提供者隔离和安全性。

  • 可以将 macvlan 子接口添加到 Docker 主机,以允许 Docker 主机和容器之间的流量。 IP 地址需要在该子接口上设置并从父地址中删除。

这个问题“有点老”,但其他人可能会觉得它很有用。 USING DOCKER MACVLAN NETWORKS BY LARS KELLOGG-STEDMAN 的主机访问部分中描述了一种解决方法。 我可以确认 - 它正在工作。

主机访问 将容器连接到 macvlan 网络,您会发现虽然它可以毫无问题地联系本地网络上的其他系统,但容器将无法连接到您的主机(并且您的主机将无法连接到您的容器)。 这是 macvlan 接口的一个限制:没有网络交换机的特殊支持,您的主机无法将数据包发送到它自己的 macvlan 接口。

幸运的是,这个问题有一个解决方法:你可以在你的主机上创建另一个 macvlan 接口,并使用它与 macvlan 网络上的容器进行通信。

首先,我将通过使用 docker network create 的 --aux-address 选项从我们的网络范围中保留一个地址以供主机接口使用。 这使我们的最终命令行看起来像:

 docker network create -d macvlan -o parent=eno1 \\ --subnet 192.168.1.0/24 \\ --gateway 192.168.1.1 \\ --ip-range 192.168.1.192/27 \\ --aux-address 'host=192.168.1.223' \\ mynet

这将阻止 Docker 将该地址分配给容器。

接下来,我们在主机上创建一个新的 macvlan 接口。 你可以随心所欲地称呼它,但我称之为 mynet-shim:

 ip link add mynet-shim link eno1 type macvlan mode bridge

现在我们需要使用我们保留的地址配置接口并启动它:

 ip addr add 192.168.1.223/32 dev mynet-shim ip link set mynet-shim up

我们需要做的最后一件事是告诉我们的主机在与容器通信时使用该接口。 这相对容易,因为我们将容器限制在本地网络的特定 CIDR 子集中; 我们只需添加一条到该范围的路线,如下所示:

 ip route add 192.168.1.192/27 dev mynet-shim

有了该路由,您的主机在与 mynet 网络上的容器通信时将自动使用 mynet-shim 接口。

请注意,此处提供的接口和路由配置不是持久的——如果您重新启动主机,您将丢失。 如何使其持久化取决于分布。

在我的情况下,我向容器添加了一个网络。

所以CONTAINER_1 -> HOST_1可以通过不同的 IP ( 10.123.0.2 ) 访问。

CONTAINER_2HOST_2可以到达172.18.1.0

以下是docker-compose示例,希望这可以成为一种解决方法。

version: "3"

services:
  macvlan_1:
    image: alpine
    container: macvlan_1
    command: ....
    restart: always
    networks:
      macvlan:
        ipv4_address: 172.18.1.0
      internalbr:
        ipv4_address: 10.123.0.2

networks:
  macvlan:
    driver: macvlan
    driver_opts:
      parent: ens192
      macvlan_mode: bridge
    ipam:
      driver: default
      config:
        - subnet: 172.18.0.0/22
          gateway: 172.18.0.1
          ip_range: 172.18.1.0/28

  internalbr:
    driver: bridge
    ipam:
      config:
        - subnet: 10.123.0.0/24

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM