容器的网络入门
1. 创建相关实验资源。
- 在体验实验室,单击创建资源。
- (可选)在实验室⻚⾯左侧导航栏中,单击云产品资源列表,可查看本次实验资源相关信息(例如IP地址、⽤户信息等)。 说明:资源创建过程需要1~3分钟。
2. 创建实验环境镜像
在前面的实验中我们学习了Docker中的容器和容器镜像的用法。而容器作为一种虚拟机技术,其网络和存储模型也是非常重要的知识重点,因此本实验中我们讲的带领大家学习容器的网络模型的基本概念。
- 编写自定义Dockerfile
为了后续实验的进行,我们先来创建一个包含python环境的自定义镜像,我们基于python3.7构建实验镜像。接下来我们为实验镜像配置aliyun的ubuntu的apt源,并且进行apt的初始化操作,在初始化完成之后。我们为镜像安装curl,ping,ifconfig,traceroute等常用网络工具。最后我们设置镜像运行时在8000端口启动python3内置的http服务。
我们通过vi编辑Dockerfile,并将下面的内容添加到中Dockerfile中,注意使用vim编辑器时:
- 需要先按i键进入编辑模式。
- 编辑完成之后按esc退出编辑模式。
- 然后按大写的ZZ保存并退出vim。
vi Dockerfile
FROM python:3.7 EXPOSE 8000 RUN echo "deb http://mirrors.aliyun.com/ubuntu/ bionic main restricted universe multiverse \n\ deb http://mirrors.aliyun.com/ubuntu/ bionic-security main restricted universe multiverse \n\ deb http://mirrors.aliyun.com/ubuntu/ bionic-updates main restricted universe multiverse \n\ deb http://mirrors.aliyun.com/ubuntu/ bionic-proposed main restricted universe multiverse \n\ deb http://mirrors.aliyun.com/ubuntu/ bionic-backports main restricted universe multiverse \n\ deb-src http://mirrors.aliyun.com/ubuntu/ bionic main restricted universe multiverse \n\ deb-src http://mirrors.aliyun.com/ubuntu/ bionic-security main restricted universe multiverse \n\ deb-src http://mirrors.aliyun.com/ubuntu/ bionic-updates main restricted universe multiverse \n\ deb-src http://mirrors.aliyun.com/ubuntu/ bionic-proposed main restricted universe multiverse \n\ deb-src http://mirrors.aliyun.com/ubuntu/ bionic-backports main restricted universe multiverse" > /etc/apt/sources.list RUN apt-key adv --keyserver keyserver.ubuntu.com --recv-keys 3B4FE6ACC0B21F32 RUN apt-get update RUN apt-get install -y curl net-tools inetutils-ping traceroute CMD ["python3", "-m", "http.server", "8000"]
- 编译镜像
编辑好Dockerfile之后,通过docker build命令生成新的镜像。注意镜像生成过程中,需要通过网络安装相关组件,因此容器构建时间可能会比较长。
docker build -t py/http . docker images
- 验证镜像
容器制作完毕后,我们创建容器,然后使用docker exec命令在容器中执行curl 127.0.0.1:8000验证服务的启动。
docker run -itd --name check py/http docker exec check curl 127.0.0.1:8000 docker rm -f check
3. 容器和宿主机中的网卡
实验环境创建成功后,接下来我们来学习容器和宿主机中的网卡信息
- 容器的网卡信息
创建容器后。docker会为容器默认创建一块虚拟网卡。容器通过这块网卡实现网络连接,为了验证容器的网卡,我们首先用自定义镜像pyt/http创建两个容器,当容器创建好之后,我们通过docker inspect命令查看容器详细信息,详细信息中包含容器网卡的IP。为了简化容器信息的查看,我们可以使用-f参数来筛选容器的信息。
docker run -itd --name py1 py/http docker run -itd --name py2 py/http docker inspect -f '{{.NetworkSettings.IPAddress }}' py1 docker inspect -f '{{.NetworkSettings.IPAddress }}' py2
- 多容器信息查询
当Docker中的容器或者容器镜像数量较多的时候,每次使用一条命令来查询一个容器或者镜像信息就会变得非常的繁琐。这时我们就可以使用docker ps中-f "name=value"参数过滤所需要的对象,再用-q参数只获得所需要对象的ID。
接下来再配合linux命令行的$(),将对象的ID作为参数传给docker inspect命令。这样就可以一次性获得所有对象的配置信息。我们通过下列命令显示所有容器名称包含py的容器的IP地址。
docker ps -f "name=py" -q docker inspect -f '{{.Name}} {{.NetworkSettings.IPAddress }}' $(docker ps -f "name=py" -q)
- 宿主机的网卡信息
在docker安装之后,也会在宿主机上安装一块默认的虚拟网卡docker0,该网卡可以和容器中的虚拟网卡互联互通。我们先通过ifconfig查看docker0的网卡信息。
ifconfig docker0
4. 容器和宿主机的连通性
本小节中我们来测试容器和宿主机网络连通性
- 测试宿主机和容器之间的连通性
接下来我们来测试的宿主机和容器网卡的互联互通,会发现在默认情况下,宿主机可以通过docker0网卡访问容器中的服务。
ping -c 4 [py1容器IP] curl [py1容器IP]:8000 ping -c 4 [py2容器IP] curl [py2容器IP]:8000
- 容器之间的网络连接
接下来我们来测试容器之间的网络连通性,我们通过ifconfig命令查看容器详细信息,会可以发现各容器的的IP地址属于同一个子网,这种设置保证了容器之间的网卡可以互联互通,为了验证我们进入py1容器的控制台,然后测试py1到宿主机和py2的连通性。
docker exec -it py1 /bin/bash ping -c 4 [docker0 IP] ping -c 4 [py2容器IP] curl [py2容器IP]:8000 exit
- 容器的外网访问
在上一个步骤中查看容器的网络信息时,我们会发现容器的网卡中网关IP正是宿主机的docker0网卡的IP。这就意味着,如果容器的宿主机可以访问互联网,容器就可以通过宿主机的docker0网卡转发网络数据包访问互联网。为了验证我们进入py1容器的控制台,ping访问aliyun.com验证连通性,再通过traceroute命令验证容器访问外网的路径。会发现容器访问外网的第一条就是docker0网卡。
docker exec -it py1 /bin/bash ping -c 4 www.aliyun.com traceroute www.aliyun.com -w 0.1 exit
5. 容器的端口映射
在上面的几个小节中我们学习了了,容器和宿主机的互相访问,容器和容器的互相访问,以及容器对外网的访问。但是由于容器本身使用了Docker创建的私有网络地址,虽然可以通过docker0网卡转发访问外网,但是无法提供服务,让外网的使用者来访问。
为了解决这个问题,我们就需要用到容器的端口映射功能。通过端口映射功能,我们可以将宿主机的一个端口和一个指定容器的端口进行映射绑定,所有对宿主机端口的访问数据包,都会自动转发到指定容器的端口上。这样只要外网访问者只要能访问到宿主机,就可以通过端口映射功能,访问到容器中的服务。从而实现了通过容器对外发布服务的能力。
本小节中我们就来为大家演示Docker端口映射的常用用法。
- 端口映射的基本用法
第一种用法就是在docker run中通过-p参数进行容器和宿主机的端口映射绑定。-p参数有两种用法,第一种是分别指定宿主机端口和容器端口,其语法格式为 -p 宿主机端口:容器端口;第二种是只指定容器端口,由docker自动分配宿主机端口。其语法格式为 -p 容器端口。
如果需要为容器指定映射多个端口,可以在docker run中使用多个-p参数。在使用端口映射启动容器之后,我们可以通过docker ps命令查看容器的端口映射配置。
docker run -itd -p 18000:8000 -p 18001:8000 --name port1 py/http docker run -itd -p 8000 --name port2 py/http docker ps -f "name=port"
- 查看端口映射
端口映射完成后,我们往往需要查看映射信息,尤其是对docker自动分配宿主机端口的映射方式。除了可以用docker ps命令查看映射信息之外。还可以使用docker port命令查看映射信息,其调用格式为docker port 容器名或者docker port 容器名 容器端口。
docker port port1 docker port port1 8000 docker port port2
- 验证端口映射
当我们确定了容器在宿主机上的映射端口之后,我们就可以在宿主机上通过curl命令来验证映射功能。为了控制curl命令的输出,我们可以使用linux的|语法,配置head -n1压缩网页输出。。
curl 127.0.0.1:18000 | head -n1 curl 127.0.0.1:18001 | head -n1 curl 127.0.0.1:[port2宿主机端口] | head -n1
实验地址:https://developer.aliyun.com/adc/scenario/0d6f2eae2de840e68d5e0159d7c6e83e