本节介绍自定义bridge network的自定义网络。

1.前言2.创建自定义网络2.1 创建网络2.2 指定网段创建网络3.创建容器3.1 指定网络创建容器3.2 指定IP创建容器4.通信4.1 不同bridge之间是网络隔离的4.2 不同bridge上的容器如何通信4.3 原理5.小结

1.前言

  前两节,我们创建的容器默认使用了bridge network,网桥docker0,网段是172.17.0.0/16。那能不能自己定义网络、网段呢?

2.创建自定义网络

  Docker提供三种user-defined网络驱动:bridge、overlay和macvlan。本章只介绍bridge方式。
  创建之前,查看当前网络,可以发现docker安装时创建了bridge、host、none三个网络。

[root@docker1 ~]# docker network ls
NETWORK ID          NAME                DRIVER              SCOPE
c1bb643c9c5a        bridge              bridge              local
59364623cee2        host                host                local
fb704391fb47        none                null                local

2.1 创建网络

  执行docker network create --driver=bridge mynet1

  • docker网络  多了mynet1,驱动为bridge
[root@docker1 ~]# docker network ls
NETWORK ID          NAME                DRIVER              SCOPE
c1bb643c9c5a        bridge              bridge              local
59364623cee2        host                host                local
50ffccecba76        mynet1              bridge              local
fb704391fb47        none                null                local
  • 网桥  新增了一个网桥
[root@docker1 ~]# brctl show
bridge name     bridge id        STP enabled  interfaces
br-50ffccecba76    8000.0242c34e7ef4   no      
docker0         8000.0242a8646c32   no       veth535a8bb
                             veth895fec0
  • 路由表  新增了目的地址为172.18.0.0/16的路由表
[root@docker1 ~]# route -n
Kernel IP routing table
Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
0.0.0.0         192.168.0.1     0.0.0.0         UG    100    0        0 enp0s3
172.17.0.0      0.0.0.0         255.255.0.0     U     0      0        0 docker0
172.18.0.0      0.0.0.0         255.255.0.0     U     0      0        0 br-50ffccecba76
192.168.0.0     0.0.0.0         255.255.255.0   U     100    0        0 enp0s3
  • docker network inspect命令查看网络详情
    可以发现其网段是由docker指定的,为172.18.0.0/16
[root@docker1 ~]# docker network inspect mynet1
[
    {
        "Name": "mynet1",
        "Id": "50ffccecba76af9de29d457743e6859d34b6a70b61f364a66ec15813425b1454",
        "Created": "2020-04-19T21:57:34.490552328+08:00",
        "Scope": "local",
        "Driver": "bridge",
        "EnableIPv6": false,
        "IPAM": {
            "Driver": "default",
            "Options": {},
            "Config": [
                {
                    "Subnet": "172.18.0.0/16",
                    "Gateway": "172.18.0.1"
                }
            ]
        },
        ......

2.2 指定网段创建网络

  执行命令docker network create --driver=bridge --subnet=172.21.21.0/24 --gateway=172.21.21.1 mynet2
  创建完,路由表、网桥等发生类似的变化,且该网络的网段和网关是我们自己指定的。

3.创建容器

  分别用上面两个网络创建容器。

3.1 指定网络创建容器

  执行docker run -it -d --network=mynet1 --name=bbox_mynet1 busybox,进入容器,查看其IP

[root@docker1 ~]# docker exec -it bbox_mynet1 sh
/ # 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
12: eth0@if13: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue 
    link/ether 02:42:ac:12:00:02 brd ff:ff:ff:ff:ff:ff
    inet 172.18.0.2/16 brd 172.18.255.255 scope global eth0
       valid_lft forever preferred_lft forever

3.2 指定IP创建容器

  执行docker run -it -d --network=mynet2 --ip=172.21.21.65 --name=bbox_mynet2 busybox,进入容器,查看IP

[root@docker1 ~]# docker exec -it bbox_mynet2 sh
/ # 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
14: eth0@if15: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue 
    link/ether 02:42:ac:15:15:41 brd ff:ff:ff:ff:ff:ff
    inet 172.21.21.65/24 brd 172.21.21.255 scope global eth0
       valid_lft forever preferred_lft forever

  注意:只有自己定义网段的网络,才允许指定容器IP。

4.通信

  当前网络拓扑

4.1 不同bridge之间是网络隔离的

  同一个bridge上容器自然可以通信,我们不再测试。那不同bridge上呢?看样子应该不通,毕竟网段都不一样。但是等等,我们前面说过linux系统开启了ip_forward,它本身就是一个路由器,我们查看一下主机的路由表:

[root@docker1 ~]# route -n
Kernel IP routing table
Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
0.0.0.0         192.168.0.1     0.0.0.0         UG    100    0        0 enp0s3
172.17.0.0      0.0.0.0         255.255.0.0     U     0      0        0 docker0
172.18.0.0      0.0.0.0         255.255.0.0     U     0      0        0 br-50ffccecba76
172.21.21.0     0.0.0.0         255.255.255.0   U     0      0        0 br-757bb8fb1878
192.168.0.0     0.0.0.0         255.255.255.0   U     100    0        0 enp0s3

  从路由表来看,不同bridge的容器是可以通信的。测试一下,从bbox_mynet1 ping bbox1,发现不通。
  为什么呢?查看iptables,执行iptables -t filter -vnL

Chain DOCKER-ISOLATION-STAGE-1 (1 references)
 pkts bytes target     prot opt in     out     source               destination         
    0     0 DOCKER-ISOLATION-STAGE-2  all  --  br-757bb8fb1878 !br-757bb8fb1878  0.0.0.0/0            0.0.0.0/0           
    0     0 DOCKER-ISOLATION-STAGE-2  all  --  br-50ffccecba76 !br-50ffccecba76  0.0.0.0/0            0.0.0.0/0           
   33  6167 DOCKER-ISOLATION-STAGE-2  all  --  docker0 !docker0  0.0.0.0/0            0.0.0.0/0           
   76  9290 RETURN     all  --  *      *       0.0.0.0/0            0.0.0.0/0            Chain DOCKER-ISOLATION-STAGE-2 (3 references)
 pkts bytes target     prot opt in     out     source               destination         
    0     0 DROP       all  --  *      br-757bb8fb1878  0.0.0.0/0            0.0.0.0/0           
    0     0 DROP       all  --  *      br-50ffccecba76  0.0.0.0/0            0.0.0.0/0           
    0     0 DROP       all  --  *      docker0  0.0.0.0/0            0.0.0.0/0           
   33  6167 RETURN     all  --  *      *       0.0.0.0/0            0.0.0.0/0           

  这几条规则决定了不同bridge之间的流量被DROP了。
  可见Docker设计之初就规定了不同bridge之间不能通信。

4.2 不同bridge上的容器如何通信

  那如何让两个bridge上的容器通信呢?
  现在想让bbox_mynet1能访问bbox1,我在bbox_mynet1里加上一块连接docker0的网卡,如下图:

  执行命令将容器bbox_mynet1连接到网络bridge上docker network connect bridge bbox_mynet1
  (注意docker network connect docker0 bbox_mynet1是不行的,网络名称必须是docker network ls查出的NAME)
  查看容器bbox_mynet1的网卡,可以发现多了网卡eth1:

[root@docker1 ~]# docker exec -it bbox_mynet1 sh
/ # 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
12: eth0@if13: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue 
    link/ether 02:42:ac:12:00:02 brd ff:ff:ff:ff:ff:ff
    inet 172.18.0.2/16 brd 172.18.255.255 scope global eth0
       valid_lft forever preferred_lft forever
16: eth1@if17: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue 
    link/ether 02:42:ac:11:00:05 brd ff:ff:ff:ff:ff:ff
    inet 172.17.0.5/16 brd 172.17.255.255 scope global eth1
       valid_lft forever preferred_lft forever

  此时可以ping通bbox1

/ # ping 172.17.0.2
PING 172.17.0.2 (172.17.0.2): 56 data bytes
64 bytes from 172.17.0.2: seq=0 ttl=64 time=0.202 ms
64 bytes from 172.17.0.2: seq=1 ttl=64 time=0.101 ms

4.3 原理

  为什么通了呢?根据拓扑图,很好理解,查看bbox_mynet1的路由表,里面多了一条指向172.17.0.0/16的路由,并且出口为eth1,而eth1与docker0的接口是veth pair,流量自然走到了docker0上。

/ # route -n
Kernel IP routing table
Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
0.0.0.0         172.17.0.1      0.0.0.0         UG    0      0        0 eth1
172.17.0.0      0.0.0.0         255.255.0.0     U     0      0        0 eth1
172.18.0.0      0.0.0.0         255.255.0.0     U     0      0        0 eth0

5.小结

  • Docker支持用户自己创建网络,支持指定CIDR及网关
  • 在自定义CIDR的网络上创建容器,可以指定容器IP
  • 不同bridge的容器是隔离的,通过iptables Filter table实现
  • 想让不同bridge上的容器A访问容器B,需要给容器A添加一个网卡,该网卡连接到容器B所在的bridge上

 下一节,我们介绍None & Host网络。点击此处回到docker系列文章目录

 作者原创,转载请声明出处!


本人微信公众号同步更新云计算、容器、网络、编程等文章,欢迎参观!

Docker-Bridge Network 03 自定义网络的更多相关文章

  1. centos7下安装docker(12.2自定义网络)

    通常默认的情况下我们使用的是docker的bridge的网络,用户也可以根据自己的业务需要,创建user-defined docker 提供三种user-defined网络驱动:bridge,over ...

  2. Docker系列(28)- 自定义网络

    自定义网络 网络模式 bridge:桥接docker(默认,自己创建也可以使用bridge模式) none:不配置网络 host:和宿主机共享网络 container:容器网络联通!(用的少!局限性大 ...

  3. Docker | 自定义网络(网关、子网地址)

    了解 docker network 通过下面的命令来获取帮助 docker network --help Commands: connect Connect a container to a netw ...

  4. Docker 自定义网络

    1.创建自定义网络 docker network create -d bridge --subnet 172.25.0.0/16 network_name 2.redis docker 添加到网络 d ...

  5. Docker Network Configuration 高级网络配置

    Network Configuration TL;DR When Docker starts, it creates a virtual interface named docker0 on the ...

  6. Docker bridge、host、container other、overlay 网络模式

    docker run创建Docker容器时,可以用--net 选项指定容器的网络模式,Docker有以下5种网络模式: bridge模式:使用–net =bridge指定,默认设置: host模式:使 ...

  7. 网络-Docker 提供的几种原生网络和自定义网络(11)

    Docker 网络从覆盖范围可分为单个 host 上的容器网络和跨多个 host 的网络,本章重点讨论前一种 Docker 安装时会自动在 host 上创建三个网络,我们可用 docker netwo ...

  8. docker学习之network:初识网络配置

    起因 我的开发环境需要一个python代码运行环境.reids服务和mysql服务. 由于以前,我的开发环境是mac,而CI和线上运行环境是centos,偶尔会出项本地单元测试跑不过,而CI可以过.这 ...

  9. Docker的单主机容器网络

    作者:杨冬 欢迎转载,也请保留这段声明.谢谢! 出处: https://andyyoung01.github.io/ 或 http://andyyoung01.16mb.com/ 本篇文章主要探索Do ...

随机推荐

  1. if-else代码优化的八种方案

    前言 代码中如果if-else比较多,阅读起来比较困难,维护起来也比较困难,很容易出bug,接下来,本文将介绍优化if-else代码的八种方案. 优化方案一:提前return,去除不必要的else 如 ...

  2. MySQl数据类型和条件限制

    数据库的增删改查已经介绍完毕,今天从表的详细操作开始讲解 表操作 今日内容 1.数据类型 建表的时候,字段都有对应的数据类型 整型 浮点型 字符类型(char与varchar) 日期类型 枚举与集合 ...

  3. Spring优雅整合Redis缓存

    “小明,多系统的session共享,怎么处理?”“Redis缓存啊!” “小明,我想实现一个简单的消息队列?”“Redis缓存啊!” “小明,分布式锁这玩意有什么方案?”“Redis缓存啊!” “小明 ...

  4. [贪心,dp] Educational Codeforces Round 71 (Rated for Div. 2) C. Gas Pipeline (1207C)

    题目:http://codeforces.com/contest/1207/problem/C   C. Gas Pipeline time limit per test 2 seconds memo ...

  5. 封装WebSocket(建立链接、主动关闭)

    一.前言 近期项目里需做一个在线聊天功能,就想要在对话的时候建立socket链接.又因为聊天只是其中一个部分,在它外面还有一些全局的消息通知需要接收,因此也需要建立socket链接.在该项目里不仅一处 ...

  6. 最通俗易懂的 HashMap 源码分析解读

    HashMap 作为最常用的集合类之一,有必要深入浅出的了解一下.这篇文章会深入到 HashMap 源码,刨析它的存储结构以及工作机制. 1. HashMap 的存储结构 HashMap 的数据存储结 ...

  7. Python 聊天界面编写

    import os from tkinter import * import time os.chdir('E:\\actdata') def main(): def sendMsg():#发送消息 ...

  8. TensorFlow Windows 安装

    欢迎大家关注我们的网站和系列教程:http://www.tensorflownews.com/,学习更多的机器学习.深度学习的知识! 本系列教程将手把手带您从零开始学习Tensorflow,并最终通过 ...

  9. 前端学习(3)-CSS

    一 CSS CSS是Cascading Style Sheets的缩写,层叠样式表,用来控制网页数据的显示,可以使网页的显示与数据内容分离. 二 引入方式 (1)行内式:在标记的style属性中设置C ...

  10. Java是未来的第一编程语言吗?

    目录 一.前言 二.Java帝国的今天 2.1 依然霸占TIOBE热门编程语言的榜首 2.2 曾经想扼杀Java的微软宣布加入OpenJDK 2.3 Oracle发布开源全栈虚拟机GraalVM 三. ...