【Docker】容器端口暴露+镜像生成实战
博主有话说
在完成了之前博文专栏对linux和docker指令的介绍后,接下来开始对docker的应用进行实战。本博文主要对容器端口暴露、镜像生成进行要点的记录与实战。
容器端口暴露
在之前【Docker】常用帮忙、镜像、容器、其他命令合集(2)的博文中,有介绍过docker run
指令,以nginx为例,通过docker run -d nginx
进行后台运行,成功后,通过 curl localhost:80
去进行访问,结果没通。
对容器端口向主机CenOS7进行暴露,重新采用docker run -d -p 3344:80 nginx
进行启动,可以发现通过 curl localhost:3344
去进行访问,可以正常访问nginx。
在理解这部分端口暴露内容之前,可以先回顾一下虚拟机、容器之间的关系!
虚拟机、容器
容器和虚拟机(VM)都是实现 "资源隔离与环境一致性" 的技术,但底层原理和适用场景有本质区别,核心差异在于隔离粒度、资源效率和启动速度。
隔离粒度是 "隔离强度 " 与 "资源效率 " 的权衡工具 ------粒度越粗,隔离越安全,但资源浪费越多、成本越高;粒度越细,资源利用率越高、成本越低,但安全性依赖更精细的软件 / 技术控制。
- 粗粒度隔离:如物理服务器级隔离;
- 中粒度隔离:如虚拟机级隔离;
- 细粒度隔离:如容器级隔离。
一、核心原理对比
用一个直观的比喻理解:
-
虚拟机 像 "独立的房子":每套房子(VM)有自己的 "地基(硬件模拟)""墙体(操作系统)" 和 "家具(应用)",完全独立,互不干扰。
-
容器 像 "同一套房子里的独立房间":房子(宿主机)只有一个地基(物理硬件)和一个墙体(宿主机操作系统),每个房间(容器)共享房子的基础设施,但通过门(namespace)和墙(cgroups)隔离,只放自己的家具(应用)。
1. 虚拟机(VM)的工作方式
- 多层结构:
物理硬件 → Hypervisor(虚拟机监控器,如 VMware、KVM)→ 虚拟机操作系统(Guest OS,如 Linux、Windows)→ 应用程序。 - 核心特点:
Hypervisor 会模拟完整的硬件环境 (CPU、内存、磁盘、网络卡等),每个虚拟机都需要安装独立的操作系统,应用程序运行在虚拟机的 OS 中。
虚拟机与宿主机、虚拟机之间完全隔离(硬件级隔离),一个虚拟机崩溃不会影响其他虚拟机或宿主机。
2. 容器(Container)的工作方式
- 单层结构:
物理硬件 → 宿主机操作系统(如 Linux)→ 容器引擎(如 Docker、containerd)→ 容器(应用 + 依赖库)。 - 核心特点:
容器不模拟硬件,而是通过宿主机 OS 的内核隔离技术 (Linux 的 namespace 和 cgroups)实现隔离:- namespace:让容器拥有独立的 "进程、网络、文件系统" 等视图(比如容器内的进程看不到宿主机的进程);
- cgroups:限制容器的资源使用(如最多用 2 核 CPU、4GB 内存)。
所有容器共享宿主机的操作系统内核,容器内只需包含应用程序及其依赖的库(无需完整 OS)。
二、关键差异对比表

端口暴露分析
通过以上的分析,可以清楚,多个容器用的其实是同一套操作系统、物理硬件等。那么联系到刚刚实战上,可以认识到,docker run -d nginx
虽然对容器的端口进行了暴露,但是并未对linux系统的进行暴露;而docker run -d -p 3344:80 nginx
将容器的80端口映射到宿主机即cenos7的3344端口,实现了端口暴露,从而让外网正常访问,如下图所示。由于是虚拟机,因此不需要进行安全组的设置 ;如果用的第三方云平台,则还需要再进行安全组的设置 ,实现端口的暴露。
由于虚拟机与主机桥接,虚拟机ip是192.168.1.9,因此,在主机中用http://192.168.1.9:3344 进行访问,同样可以正常访问!
ps: 学到这里,想到最初学习docker的目的,是为了用docker实现内网穿透。有点眉目了,此时感觉有点类似向日葵,2台主机a、b都安装向日葵软件,a、b都由软件公司控制,然后a将识别码给b,b就可以访问a。这里软件公司就类似于docker,a 就类似于nginx,b类似于虚拟机外面的主机。只是肤浅的理解,随着后面继续学习,对错见知晓!
镜像生成
bash
# 提交容器成为一个新的副本
docker commit -m="提交的描述信息" -a="作者" 容器id 目标镜像名:[TAG]
在tomcat容器的可写层进行写入,且运行容器
在指令测试前,先对tomcat进行运行,可以发现docker run -d --name=tomcat -p 8080:8080 tomcat
后,curl localhost:8080
无法访问。
这个因为库里面的tomcat是阉割版的,比官网下载的少了很多配置文件,需要进行配置文件的增加 。由于之前已经对容器进行了tomcat的命名,通过docker exec -it tomcat /bin/bash
进行bash交互页面,用cp -r ./webapps.dist/* webapps
将webapps.dist里面的文件全部复制到webapps里面即可 。
tomcat新镜像生成
完成了容器可写层的写入后,通过docker commit -a="haitao" -m="add wwbapps" tomcat tomcatfinal:1.0
完成新镜像的生成。
新镜像文件的放置路径可以通过docker info
进行查询,里面Docker Root Dir 的路径就是放置路径,默认是/var/lib/docker
。但是由于是docker是联合文件系统,一层层的导致很难找!如果有镜像仓库,建议docker push/pull
最方便;如果是本地,可以采用docker save
导出为 tar文件,该文件会保存在当前执行命令的工作目录下。故用docker save -o tomcatfinaltar.tar tomcatfinal:1.0
进行保存,然后在xshell中打开xftp,可以将tar文件进行复制即可。
后续要用了,再用docker load -i tomcatfinaltar.tar
导入即可。