企业级容器技术Docker 20250917总结
一、Docker 的组成和定义
Docker 官网: http://www.docker.com
帮助文档链接: https://docs.docker.com/
Docker 镜像: https://hub.docker.com/
Docker 中文网站: http://www.docker.org.cn/
Docker 是一个开源的容器化平台,它允许开发者将应用程序及其依赖项打包到一个标准化的单元(称为 “容器”)中,从而确保应用在任何支持 Docker 的环境中都能以相同的方式运行。
简单来说,Docker 的核心思想是 “一次构建,到处运行”,解决了传统开发中 “在我电脑上能运行,到你电脑上就出错” 的环境一致性问题。
核心概念:
容器(Container):一个独立运行的应用单元,包含应用程序及其所有依赖(代码、运行时、库、环境变量等)。容器是轻量级的,因为它们共享主机的操作系统内核,不需要像虚拟机那样单独安装操作系统。
镜像(Image):容器的 “模板”,是一个只读的文件系统,包含运行应用所需的所有内容。可以把镜像理解为容器的源代码,容器是镜像的运行实例。
Dockerfile:用于构建镜像的文本文件,包含一系列指令(如安装软件、配置环境等),通过
docker build
命令可生成镜像。仓库(Repository):用于存储和分发 Docker 镜像的地方,类似代码仓库(如 GitHub),最常用的公共仓库是 Docker Hub。官方仓库: https://hub.docker.com/ 可搭建私有仓库harbor
- Docker 主机(Host): 一个物理机或虚拟机,用于运行Docker服务进程和容器,也称为宿主机, node节点
- Docker 服务端(Server):Docker守护进程,运行docker容器 docker engine
- Docker 客户端(Client):客户端使用 docker 命令或其他工具调用docker API
主要优势:
- 环境一致:消除开发、测试、生产环境的差异,减少 “环境问题”。
- 轻量高效:容器比虚拟机更节省资源,启动速度快(秒级)。
- 隔离性:不同容器之间相互隔离,避免依赖冲突。
- 可移植性:容器可以在任何支持 Docker 的平台(Linux、Windows、Mac 等)上运行。
常见用途:
- 应用程序的打包和分发
- 微服务架构的部署
- 持续集成 / 持续部署(CI/CD)流程
- 开发环境的快速搭建和隔离
例如,开发者可以在本地用 Docker 构建一个包含 Python 环境和特定库的容器,然后直接将这个容器部署到服务器,无需担心服务器上的环境配置问题。
1.Docker 优化配置
https://docs.docker.com/reference/cli/dockerd/#daemon-configuration-file
注意:这种方式只对新建的容器有效的,之前的容器不生效
范例: 支持官方仓库和私有仓库镜像下载
就是一些加速镜像 略
范例:通过ssh 协议远程连接
[root@ubuntu2204 ~]#ssh-keygen
[root@ubuntu2204 ~]#ssh-copy-id 10.0.0.100
[root@ubuntu2204 ~]#docker -H ssh://root@10.0.0.100 version
[root@ubuntu2204 ~]#ssh 10.0.0.100 docker images
2.容器镜像管理
[root@ubuntu1804 ~]#docker image history nginx #查看镜像分层历史
[root@ubuntu1804 ~]#docker inspect nginx #获取镜像的详细信息
[root@ubuntu1804 ~]#docker save nginx -o nginx.tar #将 Docker 镜像保存为一个 tar 归档文件
[root@ubuntu1804 ~]#docker search centos
[root@ubuntu1804 ~]#docker search -s 100 centos #搜索点赞100个以上的镜像(旧)
[root@ubuntu1804 ~]#docker search -s 100 centos #搜索点赞100个以上的镜像(旧)
[root@ubuntu1804 ~]#docker search --filter=stars=100 centos #搜索点赞100个以上的镜像(新)
3.Alpine 介绍
Alpine 官网: https://www.alpinelinux.org/
Alpine 官方仓库: https://github.com/alpinelinux
Alpine 官方镜像: https://hub.docker.com/_/alpine/
Alpine 官方镜像仓库: https://github.com/gliderlabs/docker-alpine
Alpine 阿里云的镜像仓库: https://mirrors.aliyun.com/alpine/
要理解 Alpine,首先需要明确它的核心身份 ——Alpine Linux,这是一款基于 Linux 内核的轻量级、安全优先的开源操作系统。
Alpine Docker 镜像也继承了 Alpine Linux 发行版的这些优势。相比于其他 Docker 镜像,它的容量非常小,仅仅只有 5 MB 左右(对比 Ubuntu 系列镜像接近 200 MB),且拥有非常友好的包管理机制。 官方镜像来自 docker-alpine 项目。在保持瘦身的同时,Alpine 还提供了自己的包管理工具 apk,可以通过 https://pkgs.alpinelinux.org/packages 网站上查询包信息,也可以直接通过 apk 命令直接查询和安装各种软件。
范例:alpine 管理软件
/ # cat /etc/apk/repositories
https://dl-cdn.alpinelinux.org/alpine/v3.15/main
https://dl-cdn.alpinelinux.org/alpine/v3.15/community
[root@ubuntu2204 ~]#sed -i 's/dl-cdn.alpinelinux.org/mirrors.ustc.edu.cn/' /etc/apk/repositories
#修改源替换成阿里源,将里面 dl-cdn.alpinelinux.org 的 改成 mirrors.aliyun.com
vi /etc/apk/repositories
https://mirrors.ustc.edu.cn/alpine/v3.16/main
https://mirrors.ustc.edu.cn/alpine/v3.16/communityhttp://mirrors.aliyun.com/alpine/v3.8/main/
http://mirrors.aliyun.com/alpine/v3.8/community/
[root@ubuntu2204 ~]#sed -i 's/mirrors.aliyun.com/mirrors.ustc.edu.cn/' repositories
[root@ubuntu2204 ~]#docker cp repositories alpine-image-3.16.2:/etc/apk/repositories
将宿主机当前目录下名为
将宿主机当前目录下名为
repositories
的文件,复制到名为 alpine-image-3.16.2
的容器内的 /etc/apk/repositories
路径。#更新源
apk update = apt update
#安装软件
apk add vim = apt install vim
#删除软件
apk del openssh openntp vim = apt remove openssh
#安装常见软件
apk update && apk --no-cache add bash curl telnet wget net-tools pstree zip
unzip
#安装常用编译工具
apk update && apk --no-cache add gcc make curl zip unzip net-tools pstree wget
libgcc libc-dev libcurl libc-utils pcre-dev zlib-dev libnfs pcre pcre2 libevent
libevent-dev iproute2
#修改时区
apk update && apk --no-cache add tzdata && ln -s /usr/share/zoneinfo/Asia/Shanghai /etc/localtime && echo "Asia/Shanghai" > /etc/timezone
方式1:docker run -it --rm alpine:3.22.1 进入到容器里面进行操作
方式2:
docker run -it --name haha alpine:3.22.1 #创立一个名为haha的容器
docker exec -it haha /bin/sh #进入到haha容器,(Alpine 用
docker exec -it haha /bin/sh #进入到haha容器,(Alpine 用
/bin/sh
,其他系统可能用 /bin/bash
)[root@ubuntu2204 ~]#docker images -f dangling=true #查看dangling镜像 下面是出现此镜像的原因。
docker save -o /path/file.tar IMAGE1 IMAGE2 ...
docker save IMAGE1 IMAGE2 ... > /path/file.tar
#导出为压缩格式
docker save IMAGE1 IMAGE2 ... | gzip > /path/file.tar.gz
- 镜像重建:当重新构建一个镜像时,Docker 会为新的镜像分配一个新的镜像 ID,而旧的镜像 ID 如果没有被其他标签引用,就会变成悬空镜像。例如:
# dockerfile文件第一次构建 docker build -t myimage:v1 .# 第二次构建,使用相同标签 docker build -t myimage:v1 . 第一次构建的旧镜像失去标签,成为悬空镜像(<none>:<none>)。
- 删除标签:如果手动删除了一个镜像的标签,且这个镜像没有被其他标签引用,那么它也会成为悬空镜像。例如:
docker pull nginx:latest docker tag nginx:latest mynginx:temp # 新增一个临时标签docker rmi mynginx:temp # 仅删除标签,不删除镜像本身 如果被删除的 mynginx:temp 是该镜像唯一的标签,原镜像会变成悬空镜像。
4.镜像导出
常见用法
#导出为tar格式docker save -o /path/file.tar IMAGE1 IMAGE2 ...
docker save IMAGE1 IMAGE2 ... > /path/file.tar
#导出为压缩格式
docker save IMAGE1 IMAGE2 ... | gzip > /path/file.tar.gz
案例:导出所有镜像到一个打包文件
使用image ID导出镜像,在导入后的镜像没有REPOSITORY和TAG,显示为<none>
[root@ubuntu1804 ~]#docker save `docker images -qa` -o all.tar
案例:导出所有镜像至不同的文件中
[root@centos8 ~]#docker images | awk 'NR!=1{print $1,$2}' | while read repo tag;do docker save $repo:$tag -o /opt/$repo-$tag.tar ;done
范例:导出镜像并压缩
[root@ubuntu2204 ~]#docker save rockylinux:9.1-minimal | gzip - > rockylinux-9.1-minimal.tar.gz
范例: 导出指定镜像
[root@ubuntu1804 ~]#docker save mysql:5.7.30 alpine:3.11.3 -o /data/myimages.tar
#或者
[root@ubuntu1804 ~]#docker save mysql:5.7.30 alpine:3.11.3 > /data/myimages.tar
5.镜像导入
常见用法
docker load -i /path/file.tar
docker load < /path/file.tar.gz
6.删除镜像
格式
docker rmi [OPTIONS] IMAGE [IMAGE...]
docker image rm [OPTIONS] IMAGE [IMAGE...]
#选项:
-f, --force Force removal of the image
--no-prune Do not delete untagged parents
下面两条命令达到的效果是一样的
docker image rm nginx:1.27
docker rmi nginx:1.27
docker rmi nginx:1.27
[root@centos7 ~]#docker rmi -f alpine:3.11.3 #删除alpine:3.11.3镜像 -f可强删除正在使用的镜像
[root@ubuntu1804 ~]#docker rmi nginx tomcat #删除多个镜像
[root@ubuntu2204 ~]#docker rmi -f `docker images -q -f dangling=true` 删除dangling状态的镜像
[root@ubuntu1804 ~]#docker image prune -a -f #清除dangling和不再使用的镜像
7. 镜像打标签
[root@ubuntu1804 ~]#docker tag alpine alpine:3.11 (之前存在alpine:latest镜像,重新打标签原标签文件不会被删除)
8. 拉取不可描述的镜像
利用下面网站做代理,可以实现拉取原本从国内可能无法直接访问的镜像
https://docker.aityp.com/
https://dockerproxy.com/
https://github.com/DaoCloud/public-image-mirror
https://github.com/kubesre/docker-registry-mirrors/
docker pull registry.k8s.io/ingress-nginx/controller:v1.7.1 #无法拉取成功
docker pull k8s.dockerproxy.com/ingress-nginx/controller:v1.7.1 #可拉取成功
9. 总结: 企业使用镜像及常见操作
搜索、下载、导出、导入、删除
docker search centos
docker pull alpine
docker images
docker save > /opt/centos.tar #centos #导出镜像
docker load -i /opt/centos.tar #导入本地镜像
docker rmi 镜像ID/镜像名称 #删除指定ID的镜像,此镜像对应容器正启动镜像不能被删除,除非将容器全部关闭
二、容器的操作基础命令
1. docker container相关命令如下
范例: 设置容器内的主机名 a1.wang.org
[root@ubuntu1804 ~]#docker run -it --name a1 -h a1.wang.org alpine
范例: 一次性运行容器,退出后立即删除,用于测试
[root@ubuntu1804 ~]#docker run --rm alpine cat /etc/issue
Welcome to Alpine Linux 3.11
Kernel \r on an \m (\l)
范例: 创建容器后直接进入并退出
退出两种方式: exit 容器也停止,按ctrl+p+q 容器不停止
[root@ubuntu1804 ~]#docker run -it --name alpine3 alpine
#同时按ctrl+p+q 三个键退出后,容器不停止,exit 会停止。
范例: 启动前台守护式容器
[root@ubuntu1804 ~]#docker run nginx
[root@ubuntu1804 ~]#docker run --rm --name b1 busybox wget -qO - 172.17.0.3
[root@ubuntu1804 ~]#docker run --rm --name b1 busybox wget -qO - 172.17.0.3
范例: 启动后台守护式容器
[root@ubuntu1804 ~]#docker run -d nginx
范例: 开机自动运行容器
[root@ubuntu1804 ~]#docker run -d --name nginx -p 80:80 nginx #reboot后也自动关闭容器
[root@ubuntu1804 ~]#docker run -d --name nginx -p 80:80 nginx #reboot后也自动关闭容器
[root@ubuntu1804 ~]#docker run -d --name nginx --restart=always -p 80:80 nginx #容器总是运行
2. --privileged 选项
大约在0.6版,--privileged 选项被引入docker。使用该参数,container内的root拥有真正的root权限。 否则,container内的root只是外部的一个普通用户权限。privileged启动的容器,可以看到很多host上的设备,并且可以执行mount。甚至允许你在docker容器中启动docker容器。
范例:使用--privileged 让容器获取 root 权限
[root@ubuntu2204 ~]#docker run --name pod-test -d xiaoming/pod-test:v0.1
[root@ubuntu2204 ~]#docker exec -it pod-test sh
[root@08cfefa34a87 /]# iptables -vnL #提示权限不足
#加--privileged选项再创建容器
[root@ubuntu2204 ~]#docker run --name pod-test --privileged -d wangxiaochun/pod-test:v0.1
范例: 使用--privileged 让容器获取 root 权限
[root@centos8 ~]#podman run -it --privileged centos
[root@centos8 ~]#echo host data >> /data/containter.txt #可以看到能正常创建文件
3.查看容器信息
显示当前存在容器:https://docs.docker.com/engine/reference/commandline/ps/
[root@ubuntu1804 ~]#docker ps #显示运行的容器
[root@ubuntu1804 ~]#docker ps -a #显示全部容器,包括退出状态的容器
[root@ubuntu1804 ~]#docker ps -a -q #只显示容器ID
[root@ubuntu1804 ~]#docker ps -a -s #显示容器大小
[root@ubuntu1804 ~]#docker ps -l #显示最新创建的容器(停止的容器也能显示)
[root@ubuntu1804 ~]#docker ps -f 'status=exited' #查看退出状态的容器
4.查看容器内的进程
[root@ubuntu1804 ~]#docker run -d httpd
[root@ubuntu1804 ~]#docker top db144f19 #db144f19是httpd生成容器的ID
[root@ubuntu1804 ~]#docker top db144f19 #db144f19是httpd生成容器的ID
5.各种命令
[root@ubuntu1804 ~]#docker stats 251c7c7cf2aa 查看容器资源使用情况
#限制内存使用的大小
[root@ubuntu1804 ~]#docker run -d --name elasticsearch -p 9200:9200 -p 9300:9300 -e "discovery.type=single-node" -e ES_JAVA_OPTS="-Xms64m -Xmx128m" elasticsearch:7.6.2
docker inspect 可以查看docker各种对象的详细信息,包括:镜像,容器,网络等
[root@ubuntu1804 ~]#docker inspect 9997
[root@ubuntu1804 ~]#docker inspect -f "{{.Metadata}}" test:v1.0 #选择性查看,最新版本不支持
查看容器的日志
[root@ubuntu1804 ~]#docker run -d --name alpine01 alpine /bin/sh -c 'i=1;while
true;do echo hello$i;let i++;sleep 2;done'
512622b006c05673630eb04f081f8475400b1cda786b0a8a5d1c1c2fd6dc56a7
[root@ubuntu1804 ~]#docker logs 5126
[root@ubuntu1804 ~]#docker logs --tail 3 5126 #查看倒数三行的日志
[root@ubuntu1804 ~]#docker logs -f 5126 #持续跟踪
[root@ubuntu1804 ~]#docker logs --tail 0 -t 5126 #显示时间
容器的启动和停止 批量正常启动或关闭所有容器
docker start $(docker ps -a -q)
docker stop $(docker ps -a -q)
[root@ubuntu1804 ~]#docker kill `docker ps -a -q` #强制关闭所有运行中的容器
进入正在运行的容器
格式:docker attach [OPTIONS] CONTAINER
[root@ubuntu1804 ~]#docker run -it centos
[root@94a5c5c69b14 /]# cat /etc/redhat-release
CentOS Linux release 8.1.1911 (Core) #ctrl+p+q 退出(exit的话容器也会停止运行
)
[root@94a5c5c69b14 /]# [root@ubuntu1804 ~]#docker ps 可以看到centos对应的容器在运行
[root@ubuntu1804 ~]#docker attach 94a5 #进入容器
[root@94a5c5c69b14 /]#cat /etc/redhat-release

使用 exec 命令
测试环境使用此方式,使用exit退出,但容器还在运行,此为推荐方式
[root@ubuntu1804 ~]#docker exec 2478 cat /etc/redhat-release #执行一次性命令
[root@ubuntu1804 ~]#docker exec -it 2478 bash #进入容器,执行命令,exit退出但容器不停止
传递环境变量
范例:指定环境变量给 wordpress 和MySQL
[root@ubuntu2404 ~]#docker run -d -p 3306:3306 --name mysql -e MYSQL_ROOT_PASSWORD=123456 -e MYSQL_DATABASE=wordpress -e MYSQL_USER=wordpress -e MYSQL_PASSWORD=123456 -d --restart=always registry.cn-beijing.aliyuncs.com/xiaoming/mysql:8.0.29-oracle
[root@ubuntu2404 ~]#docker run -d -p 80:80 --name wordpress -e WORDPRESS_DB_HOST=10.0.0.200 -e WORDPRESS_DB_USER=wordpress -e
WORDPRESS_DB_PASSWORD=123456 -e WORDPRESS_DB_NAME=wordpress --restart=always registry.cn-beijing.aliyuncs.com/xiaoming/wordpress:php8.2-apache
[root@ubuntu2404 ~]#docker exec -it mysql sh #确认变量生效
暴露所有容器端口
docker port 可以查看容器的端口映射关系
格式:docker port CONTAINER [PRIVATE_PORT[/PROTO]]

[root@centos7 ~]#docker run -P nginx #前台启动的会话窗口无法进行其他操作,除非退出,但是退出后容器也会退出

端口映射的本质就是利用NAT技术实现的
范例: 端口映射和iptables
#端口映射前的iptables规则
[root@ubuntu1804 ~]#iptables -S
[root@ubuntu1804 ~]#iptables -S -t nat
[root@ubuntu1804 ~]#iptables -S > pre.filter
[root@ubuntu1804 ~]#iptables -S -t nat > pre.nat
#实现端口映射
[root@ubuntu1804 ~]#docker run -d -P --name nginx1 nginx
[root@ubuntu1804 ~]#docker exec -it nginx1 hostname -i
[root@ubuntu1804 ~]#docker port nginx1
#对比端口映射前后的变化
[root@ubuntu1804 ~]#iptables -S > post.filter
[root@ubuntu1804 ~]#iptables -S -t nat > post.nat
[root@ubuntu1804 ~]#diff pre.filter post.filter
[root@ubuntu1804 ~]#diff pre.nat post.nat
指定端口映射
docker run -p 可以将容器的预定义的指定端口映射到宿主机的相应端口
docker run -p 81:80 --name nginx-test-port2 nginx 容器80端口映射到宿主机本地端口81 其他略
传递运行命令
容器需要有一个前台运行的进程才能保持容器的运行,可以在构建镜像的时候指定容器启动时运行的前台命令,也可以通过启动容器时传递运行参数实现
容器里的PID为1的守护进程的实现方式
服务类: 如: Nginx,Tomcat,Apache ,但服务不能停
命令类: 如: tail -f /etc/hosts ,主要用于测试环境,注意: 不要tail -f <服务访问日志> 会产生不
必要的磁盘IO
[root@ubuntu1804 ~]#docker run -d alpine #docker ps 可以看到该容器没运行
[root@ubuntu1804 ~]#docker run -d alpine tail -f /etc/hosts #docker ps 可以看到该容器在运行