美文网首页
Docker Bridge0

Docker Bridge0

作者: 云师兄 | 来源:发表于2018-06-09 13:35 被阅读426次

    首先我们使用下面命令查看网络信息:

    [vagrant@localhost ~]$ docker network ls
    NETWORK ID          NAME                DRIVER              SCOPE
    dce12ad15e67        bridge              bridge              local
    be63d9693f78        host                host                local
    d1c04eee03c8        none                null                local
    

    今天要讨论的就是Linux的bridge网络。
    之前我们使用ip a命令查看宿主机网络接口的时候,返回结果如下:

    1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
        link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
        inet 127.0.0.1/8 scope host lo
           valid_lft forever preferred_lft forever
        inet6 ::1/128 scope host
           valid_lft forever preferred_lft forever
    2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
        link/ether 52:54:00:5f:94:78 brd ff:ff:ff:ff:ff:ff
        inet 10.0.2.15/24 brd 10.0.2.255 scope global noprefixroute dynamic eth0
           valid_lft 76814sec preferred_lft 76814sec
        inet6 fe80::5054:ff:fe5f:9478/64 scope link
           valid_lft forever preferred_lft forever
    3: docker0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default
        link/ether 02:42:08:96:2b:f9 brd ff:ff:ff:ff:ff:ff
        inet 172.17.0.1/16 brd 172.17.255.255 scope global docker0
           valid_lft forever preferred_lft forever
        inet6 fe80::42:8ff:fe96:2bf9/64 scope link
           valid_lft forever preferred_lft forever
    59: vetha65affd@if58: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master docker0 state UP group default
        link/ether 5a:31:ef:f0:fb:64 brd ff:ff:ff:ff:ff:ff link-netnsid 1
        inet6 fe80::5831:efff:fef0:fb64/64 scope link
           valid_lft forever preferred_lft forever
    

    其中的veth开头的网络接口就是上一节介绍的veth-pair接口中的其中一个,而另外一个就是容器中的veth网络接口。如当前宿主机中已经启动的容器busybox1的网络接口信息如下:

    [vagrant@localhost ~]$ sudo docker exec aec1c356e72c ip a
    1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue qlen 1000
        link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
        inet 127.0.0.1/8 scope host lo
           valid_lft forever preferred_lft forever
    58: eth0@if59: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue
        link/ether 02:42:ac:11:00:03 brd ff:ff:ff:ff:ff:ff
        inet 172.17.0.3/16 brd 172.17.255.255 scope global eth0
           valid_lft forever preferred_lft forever
    

    其中的eth0端口就是容器与宿主主机中的veth接口组成一对的网络接口,这也是容器可以连接上互联网的原因。而实际上容器也是通过这对veth接口最终连接上了宿主机的docker0端口,为了验证这句话,这里使用brctl工具,这个工具要先安装一下:

    sudo yum install bridge-utils
    

    安装以后,执行brctl show命令:

    vagrant@localhost ~]$ brctl show
    bridge name bridge id       STP enabled interfaces
    docker0     8000.024208962bf9   no      vetha65affd
    

    上面输出表明宿主机docker0接口和宿主机的vetha65affd接口的关系。
    容器和互联网通信的网络如下:


    image.png

    由上图可知一个linux主机通过eth0接口连接互联网,容器显示连接到docker0,然后通过NAT(network address transtation,网络地址转换),最后通过eth0接口连接互联网。实际上两个容器通过veth-pair连接的过程中也是通过docker0关联的。

    深入

    之前我们执行sudo docker network ls来查看宿主机网络信息:
    [vagrant@localhost ~]$ sudo docker network ls
    NETWORK ID NAME DRIVER SCOPE
    dce12ad15e67 bridge bridge local
    be63d9693f78 host host local
    d1c04eee03c8 none null local
    当我们创建一个容器后,容器就会自动连接到bridge网络上。此外,我们可以使用命令,让容器不连接到bridge网络上,而是连接到我们自己创建的网络上,请看下面:

    1. 首先创建一个名为my-bridge网络
    sudo docker network create -d bridge my-bridge
    

    结果如下:

    [vagrant@localhost ~]$ docker network ls
    NETWORK ID          NAME                DRIVER              SCOPE
    dce12ad15e67        bridge              bridge              local
    be63d9693f78        host                host                local
    ec80468730b6        my-bridge           bridge              local
    d1c04eee03c8        none                null                local
    

    我们使用brctl show命令来查看bridge信息,除了docker0这个bridge信息外,还有一个我们新创建的bridge:my-bridge:

    [vagrant@localhost ~]$ brctl show
    bridge name bridge id       STP enabled interfaces
    br-ec80468730b6     8000.02420153f2be   no
    docker0     8000.024208962bf9   no      vetha65affd
    

    可以看出新创建的network此时还没有其他容器对其连接。

    1. 创建容器的时候连接到自己创建的bridge
      现在我们新创建一个容器,并将这个容器连接到my-bridge上,而不是默认的docker0上:
    docker run -d --name my-busybox --network my-bridge hub.c.163.com/library/busybox:latest /bin/sh -c "while true;do sleep 3600;done"
    

    此时:

    [vagrant@localhost ~]$ brctl show
    bridge name bridge id       STP enabled interfaces
    br-ec80468730b6     8000.02420153f2be   no      veth2f2686c
    docker0     8000.024208962bf9   no      vetha65affd
    

    可以看到此时我们新增的network已经有容器的veth网络端口连接上了。
    我们也可以使用:

    docker network inspect ec80468730b6
    

    命令来查看具体的网络信息,最后一个参数为network id,在返回的json串中有一段:

    "Containers": {
                "9189e44ffc8026c63216343126e43dbfec455a212beff342df64c70242c98c9d": {
                    "Name": "my-busybox",
                    "EndpointID": "1254c2f18629884fdbdcfa2d0cc9f790c1d2de679e9b90417de7e4d4b18873e6",
                    "MacAddress": "02:42:ac:12:00:02",
                    "IPv4Address": "172.18.0.2/16",
                    "IPv6Address": ""
                }
            },
    

    表示连接到这个network的容器信息,可以看到就是我们新创建的容器my-busybox。

    3.修改已运行的容器连接到其他的bridge:

    docker network connect my-bridge test1
    

    上述命令将正在运行的test1容器网络端口连接到my-bridge。修改连接后,再次执行:

    docker network inspect ec80468730b6
    

    结果中Containers部分多了个test1容器的信息。另外,原来test1容器连接的docker0这个bridge网络interface信息中还是保留了连接,即一个容器可以连接到多个bridge上。
    还需要注意的是当两个容器连接到了同一个bridge上,则两个容器之间就可以相互ping通。

    相关文章

      网友评论

          本文标题:Docker Bridge0

          本文链接:https://www.haomeiwen.com/subject/wfeteftx.html