1.容器通信
容器之间除了使用ip通信外,还可以使用容器名称通信
docker1.10开始,内嵌了一个DNS server
dns解析功能必须在自定义网络中使用
以容器demo的网络打开一个新容器,此时新容器的ip和demo的ip完全一致
处于这个模式下的docker容器会共享一个网络栈,这样两个容器之间可以使用localhost高效快速通信
[root@server2 ~]# docker ps
[root@server2 ~]# docker inspect demo
[root@server2 ~]# docker run -it --rm --network container:demo busybox
/ # ip addr
/ # netstat -antlp
–link可以用来链接两个容器
实验前删除不用的docker
[root@server2 ~]# docker rm -f demo demo2
传输一个nginx容器
[root@server1 mnt]# scp nginx.tar server2:
[root@server2 ~]# docker load -i nginx.tar
后台开启一个demo容器,在开启一个容器nginx链接demo,此时nginx可以ping通demo、nginx
[root@server2 ~]# docker run -d --name demo nginx
[root@server2 ~]# docker run -it --rm --link demo:nginx busybox
/ # env
/ # ping demo
/ # ping nginx
/ # cat /etc/hosts
查看他的解析
停止demo,开启demo2
[root@server2 ~]# docker stop demo
[root@server2 ~]# docker run -d --name demo2 nginx
[root@server2 ~]# docker inspect demo2
此时demo2的ip会占用demo的ip
开启demo,ip会变化
[root@server2 ~]# docker start demo
[root@server2 ~]# docker inspect demo
此时在之前未停止的容器上在去ping nginx,会发现解析已经自动变化,但是env下的没有变化
容器如何访问外网是通过iptables的SNAT实现的
外网如何访问容器
端口映射
-P 选项指定映射端口
[root@server2 ~]# docker rm -f demo demo2
[root@server2 ~]# docker ps
[root@server2 ~]# docker run -d --name demo -p 80:80 nginx
[root@server2 ~]# netstat -antlp
[root@server2 ~]# iptables -t nat -nL
[root@server2 ~]# kill 9658
[root@server2 ~]# curl localhost
[root@server2 ~]# [root@server1 ~]# curl 192.168.3.202
[root@server1 ~]# curl 192.168.3.202
删除docker-proxy,此时本地ping不同,但是ip可以
server1上访问
容器内部
如果单独删除docker-proxy进程,容器之间访问也不受影响
[root@server2 ~]# docker run -it --rm busyboxplus
/ # curl 172.17.0.2
删除iptables DNAT
[root@server2 ~]# docker rm -f demo
[root@server2 ~]# docker run -d --name demo -p 80:80 nginx
[root@server2 ~]# iptables -t nat -nL
[root@server2 ~]# netstat -antlp
[root@server2 ~]# iptables -t nat -D DOCKER 3
此时都可以访问
[root@server2 ~]# curl localhost
[root@server2 ~]# [root@server1 ~]# curl 192.168.3.202
[root@server1 ~]# curl 192.168.3.202
所以外王访问容器用到了docker-proxy和iptables DNAT,宿主机访问本机容器使用的是iptables DNAT,外部主机访问容器或者容器之间的访问是docker-proxy实现
2.跨主机容器网络
macvlan网络方案实现
linux kernel提供的一种网卡虚拟化技术
无需linux bridge,直接使用物理借口,性能及好。
实验条件:
在两台主机上个添加一块网卡,打开网卡混杂模式
打开混杂模式
[root@server2 ~]# ip link set eth1 promisc on
[root@server2 ~]# ip addr show eth1
创建自定义网络,添加子网和网关,父级网卡为eth1物理网卡
[root@server2 ~]# docker network create -d macvlan --subnet 172.21.0.0/24 --gateway=172.21.0.1 -o parent=eth1 mac_net1
[root@server2 ~]# docker network ls
server1进行上述相同步骤,此处不作展示
在两台主机上打开相同网段的容器,发现是可以相互ping通的
[root@server2 ~]# docker run -it --rm --network mac_net1 --ip 172.21.0.12 busybox
[root@server1 ~]# docker run -it --rm --network mac_net1 --ip 172.21.0.11 busybox
自定义第二个网络,注意和第一个的网络的区别
[root@server1 ~]# docker network create -d macvlan --subnet 172.22.0.0/24 --gateway=172.22.0.1 -o parent=eth1.1 mac_net2
[root@server2 ~]# docker network create -d macvlan --subnet 172.22.0.0/24 --gateway=172.22.0.1 -o parent=eth1.1 mac_net2
在自定义网络二下的相同网段两台主机上的容器也可以通
[root@server1 ~]# docker run -it --rm --network mac_net2 --ip 172.22.0.21 busybox
/ # ping 172.22.0.22
ctrl + pq保存退出
[root@server2 ~]# docker run -it --rm --network mac_net2 --ip 172.22.0.22 busybox
尝试用自定义网络一去ping网络二是不同的
[root@server1 ~]# docker ps
[root@server1 ~]# docker run -it --rm --network mac_net1 --ip 172.21.0.11 busybox
/ # ip addr
/ # ping 172.22.0.21
所以macvlan网络在二层上是隔离的,所以在不同macvlan网络的容器是不能通信的
可以在三层上通过网关将macvlan网络连通起来