18附录:命令速查

4112 字
21 分钟
18附录:命令速查

命令速查#

按主题汇总全系列出现过的命令。同一条命令往往在好几关里反复出现,所以这里只收一处,正文在用到时链到对应小节。

上下文#

命令作用
docker context ls列出所有上下文,带 * 的是当前在用的那个
docker context use <名字>切换当前上下文
docker --context <名字> <子命令>只对这一条命令指定上下文,不动全局设置

容器生命周期#

命令作用
docker run hello-world最简的一次运行:拉镜像、建容器、跑一次、退出
docker run -d -p 8080:80 nginx后台运行一个容器,把宿主机 8080 转发到容器的 80
docker ps列出运行中的容器
docker ps -a连已停止的容器一起列出
docker start <容器>启动一个已停止的容器
docker stop <容器>停止一个运行中的容器
docker restart <容器>重启容器
docker rm <容器>删除容器
docker rm -f <容器>强制删除,运行中的也能删
docker rename <容器> <新名字>改容器名,运行中或已停止都能改,不用重启

运行时的参数#

命令作用
docker run -d --name <名字> <镜像>给容器指定名字;不指定则随机生成一个,用名字或 ID 指代容器都可以
docker run --hostname <名字> <镜像>指定主机名;不写就是容器 ID。容器名(--name)和主机名是两回事,内建 DNS 两个都登记
docker run --rm <镜像>容器退出后自动删除
docker run -e 名字=值 <镜像>用环境变量改掉镜像的默认行为,要传几个就写几遍
docker run -v 宿主路径:容器路径 <镜像>把宿主机的目录或文件接到容器里,顺序是「宿主<容器>」
docker run -v 宿主路径:容器路径:ro <镜像>同上,但容器里只能读不能改
docker run <镜像> <命令>覆盖镜像默认启动的那个程序(顶掉的是 CMD)
docker run --entrypoint <程序> <镜像>连 ENTRYPOINT 一起换掉,而不只是换 CMD

日志与进入容器#

命令作用
docker logs <容器>查看容器主进程的输出
docker logs -f <容器>持续跟随输出
docker inspect --format '{{.LogPath}}' <容器>看这个容器的日志文件落在哪(在虚拟机里)
docker run --log-opt max-size=10m --log-opt max-file=3 <镜像>给日志设上限:单文件最大 10m,最多留 3 个
docker exec -it <容器> bash在运行中的容器里另起一个进程,通常是开一个交互式终端

进程与信号#

命令作用
docker top <容器>列出容器里跑着的进程
docker stop -t <秒> <容器>改那个宽限期;默认 10 秒,-t 0 直接发 SIGKILL
docker kill <容器>直接发 SIGKILL,不给商量的余地
docker kill -s <信号> <容器>发指定信号,发完就走,不等

镜像#

命令作用
docker login [仓库]登录仓库,不写就是 Docker Hub;正经场景用 access token 而不是账号密码
docker logout [仓库]退出登录
docker pull <镜像>把镜像从仓库拉到本地
docker tag <镜像> <新名字>给同一个镜像再挂一个名字,不复制镜像
docker push <名字:标签>把镜像推到仓库;名字要带上仓库里的路径,否则不知道往谁那儿推
docker images列出本地已有的镜像
docker rmi <镜像>删除镜像,前提是没有容器还引用着它
docker inspect <镜像或容器>打出完整的配置,包含镜像的默认值与这次运行实际用的值
docker inspect --format '{{.State.ExitCode}}' <容器>只取一个字段,不用在整段 JSON 里翻;{{json .Config.Env}}、{{json .Mounts}} 同理

构建镜像#

命令作用
docker build -t 名字:标签 .用当前目录的 Dockerfile 构建;末尾的 . 指的就是当前目录,材料都从这儿取
docker build --no-cache -t 名字:标签 .不用缓存,每次都从零重来
docker build --target <阶段> .多阶段构建里,只建到指定阶段为止
docker builder prune清掉构建缓存
docker history <镜像>列出这个镜像是一层层怎么来的
docker commit <容器> <新镜像>把容器当前的改动冻成一个新镜像(不推荐当常规手段)

卷与数据#

命令作用
docker volume create <名字>建一个卷
docker volume ls列出所有卷;看起来像一长串随机字符的是匿名卷
docker volume inspect <名字>看这个卷在磁盘上的位置
docker volume rm <名字>删卷,前提是没有容器在用它
docker volume prune清掉所有没被使用的卷(不问就删)
docker run -v 卷名:容器路径 <镜像>把卷挂进容器
docker run -v 容器路径 <镜像>只写一边 → Docker 自动建一个匿名卷
docker run --tmpfs 容器路径 <镜像>挂一块内存盘,不落磁盘,容器一停就没

网络#

命令作用
docker network ls列出所有网络;bridge、host、none 是自带的三张
docker network create <名字>建一张自定义网络
docker network inspect <名字>看这张网里有谁、各自的 IP
docker network connect <网络> <容器>把容器接上网络,运行中的也能接
docker network disconnect <网络> <容器>摘下来
docker network rm <名字>删网络,前提是没有容器还挂在上面
docker network prune清掉没有容器在用的网络(不问就删)
docker run --network <名字> <镜像>起容器时直接接上某张网络
docker run --network host <镜像>容器不单独隔离网络——但 macOS 上那个「host」是虚拟机,见第 5 关

Compose#

命令作用
docker compose up -d按当前目录的 compose.yaml 后台拉起整个项目,缺的镜像先拉
docker compose down停并删掉项目的容器和它自动建的网;卷不删
docker compose down -v连文件里声明的卷一起删,数据就没了
docker compose ps只看这个项目的容器,STATUS 一列带 (healthy) 这类健康状态
docker compose logs -f <服务>跟踪输出,不写服务名就是整个项目
docker compose exec <服务> <命令>在某个服务里另起一个进程,服务名就是文件里的键
docker compose config校验并打印合并后的完整配置(叠了多份文件时,用它看最后长什么样)
docker compose -f a.yaml -f b.yaml up -d按顺序叠多份文件,后面的覆盖前面的
docker compose --profile <名> up -d连同这个 profile 的服务一起起;可写多遍,或用 "*" 全开
docker compose up -d <服务>只起点名的那个服务;就算它的 profile 没激活也会起

Compose 常用字段#

正文用到的字段(image、ports、environment、volumes、depends_on、healthcheck、profiles)在各关讲过。下面这些同样常用,只是还没轮到,写到对应关再展开:

字段作用
build: .不用现成镜像,就地按 Dockerfile 构建
command: / entrypoint:覆盖镜像的启动命令,相当于 docker run 的 <命令> 和 --entrypoint
restart: unless-stopped重启策略:no(默认)/ on-failure / always / unless-stopped
env_file: .env从文件读环境变量,一行一个 名字=值
container_name: <名字>固定容器名(默认是 <项目>-<服务>-<序号>);名一固定,这个服务就不能起多个副本
networks:显式定义、接入网络;不写就用项目自建的那张
secrets:敏感数据,以文件形式挂在 /run/secrets/<名字>;只支持 Linux 容器
deploy:资源上限、副本数等;哪些键本地 docker compose 认、哪些只给 Swarm,看官方参考
logging:日志驱动与上限,如 max-size、max-file(为什么要限制,第 11 关讲)

完整字段清单见官方 Compose file reference。

系统与清理#

命令作用
docker version分别列出客户端与服务端的版本
docker info列出服务端的详细信息(存储、内核、内存等)
docker system df查看镜像、容器、卷、构建缓存各占多少空间
docker system df -v同上,再列出每一项具体是谁
docker container prune清掉已停止的容器
docker image prune清掉悬空镜像;加 -a 连没被任何容器引用的镜像也清
docker system prune清理未使用的容器、网络与悬空镜像
docker system prune -a连未被引用的镜像与构建缓存一起清理
docker system prune -a --volumes再加一样:连没在用的卷也清

用法备忘#

这些不是命令,是命令里那些容易记反、记漏的地方。

带冒号的参数,两边都是「宿主机在前,容器在后」——-p 宿主:容器(端口同理)和 -v 宿主:容器 一个规矩。

-v 的第一段决定它是路径还是卷名:

  • / 开头是绝对路径,./、../ 开头是相对当前目录的路径;
  • 不是这两种开头的(如 mysql-data:/var/lib/mysql),会被当成卷的名字(见前面「卷与数据」);
  • ~ 由 shell 展开,所以不能写进引号——-v "~/x:/y" 会把字面量 ~ 传给 Docker,开头不是 /,于是被当成卷名而报错。

:ro 是 Linux 挂载的 read-only 选项(mount -o ro 的那两个字母),写在末尾让容器里只能读。对称的 :rw 是默认值,一般不用写。这套挂载只对那一个容器可见,宿主机的目录树不变。

docker build 末尾的那个 . 指的就是当前目录,不是 Dockerfile 的位置。COPY 只能从当前目录里拿东西,而这里面的东西随时可能被复制进镜像——不想要的用 .dockerignore 挡掉(写法同 .gitignore)。目录里东西多时这一步也可能变慢;守护进程跑在本机时不一定全传,但「可能被复制进镜像」永远成立。

-t 名字:标签:冒号前是名字、后是标签;不写标签就是 latest(那个陷阱见第 10 关)。一个镜像可以挂多个「名字<标签>」。

latest 不是「最新」,只是「没写标签时的默认值」——它随时会变,指向哪由最后一次推送决定。生产用明确版本(1.0、提交号),别用它。想看「绝对跑的是这一份」,用 digest:nginx@sha256:...,由内容算出来、变一个字节就变,天生不可变。

镜像名的完整结构:[仓库地址/]命名空间/名字:标签。省掉前两段时默认是 Docker Hub 加你自己的账号;官方镜像的命名空间是 library(所以 nginx 就是 docker.io/library/nginx)。

构建会复用上次的层——每条指令算一个指纹(RUN 是命令本身,COPY 是文件内容),没变就打 CACHED;一变,它后面所有层一起重做,不是只有那一条。所以 Dockerfile 里不会变的放前面、会变的放后面。

COPY --from=<阶段> 源 目标 从另一个阶段(或另一个镜像)的文件系统里拷文件——多阶段构建靠它把编译产物挑出来、把编译工具留在门外。

VOLUME 声明过的目录,docker run 时会自动生成匿名卷,哪怕一个 -v 都没写——这是僵尸卷的一大来源。

三种挂载怎么选:要长期留住、要交付给别人 → 卷;开发时改文件、要能用编辑器直接看到 → 绑定挂载;不该落盘的临时东西 → --tmpfs。卷住在虚拟机里(docker volume inspect 能看到位置),绑定挂载就是你磁盘上的一个目录——所以 macOS 上绑定挂载慢一截。

备份一个卷:开一个临时容器,同时挂上「要备份的卷(:ro)」和「宿主机上一个落地的目录」,在里头 tar。两个 -v 少一个都不行;打包时加 -C 卷里的路径,否则包里会带上绝对路径。

-it 两个参数缺一不可:-i 保持输入,-t 分配终端,少一个就没有交互。

docker stop 和 docker kill 不是一回事——stop 先发 SIGTERM 再等(默认 10 秒),等不到才 SIGKILL;kill 默认直接 SIGKILL,-s 可换信号但同样不等待。

信号只发给容器里的 1 号进程,不会挨个通知。真正干活的程序想收到信号、想优雅退出,它自己就得是 1 号——ENTRYPOINT 脚本结尾的 exec、以及 CMD 用数组写法而不是整句话交给 shell,都是为了让它顶上 1 号。

想无条件钻进任何镜像,用 --entrypoint sh——它在 Docker 这一层直接换掉 ENTRYPOINT,不看镜像自己怎么写。直接用 docker run -it <镜像> sh 不保证有效:镜像名后面那个位置的含义由镜像决定,有的镜像把它当「要跑的程序」启动,有的只当「参数」。

docker network ls 里三张自带网的差别,在 DRIVER 那一列:bridge(驱动 bridge)搭一台虚拟交换机,是容器默认接的那张;host(驱动 host)不给容器单独建网络、直接用宿主机的;none(驱动叫 null)什么都不搭。自己建的网络驱动也是 bridge——所以「默认 / 自定义」的差别不在驱动,在有没有内建 DNS(下一条)。

容器名能被解析,靠的是内建 DNS,不是默认网络——默认网络(bridge)不做名字解析:它的 /etc/resolv.conf 指向宿主机 DNS,里面没有容器名;自定义网络里 /etc/resolv.conf 是 nameserver 127.0.0.11,那是 Docker 内建的 DNS,容器名就登记在它那儿。所以容器之间要用名字互相访问,得先接上同一张自定义网络。

判断名字解析对不对,看 getent hosts <名字>,别看 curl 通不通——两者不是一回事。

host.docker.internal 是容器里指回宿主机的名字(Docker Desktop 提供),容器要访问宿主机上的服务就用它。

-p 在 macOS 上等于 Docker Desktop 在宿主机上占住了那个端口——lsof -nP -iTCP:<端口> -sTCP:LISTEN 看到的是 com.docker.backend(Windows 用 netstat -ano | findstr :<端口>)。不写 -p,这个端口在宿主机上就不存在。

compose 的服务名就是容器之间互相叫的名字,网络也不用自己建——compose 自动建一张 <项目名>_default 网,项目名默认是 compose.yaml 所在目录的名字。挂载写命名卷,卷要在文件末尾的顶层 volumes: 里声明。

depends_on 只管顺序,不管就绪——它只等对面跑起来,不等它能应答。要等真的就绪,得给对面写 healthcheck,再用 condition: service_healthy(还有 service_started、service_completed_successfully)。start_period 是开头宽限期,这期间的失败不计数,专治启动慢的服务。

叠多份文件,后一份覆盖前一份,但按条目类型分:单值项(image、command)直接换;键值项(environment、labels)按键名合并;挂载(volumes)按容器路径合并;而 ports、expose 是累加,不是替换——以为第二份文件写了新端口就顶掉了旧的,是错的。拿不准就先 docker compose config 看合并结果。文件名叫 compose.override.yaml 时会被自动叠上,不用写 -f。

profile 只控制「起不起」:没写 profiles 的服务永远起,写了的一律默认不起,得 --profile <名> 激活。点名 docker compose up -d <服务> 可以绕过 profile 直接起。down 默认不碰带 profile 的服务。

容器主进程写进 stdout/stderr 的东西,Docker 全接住存成文件——路径用 docker inspect --format '{{.LogPath}}' <容器> 看(在跑引擎的那台机器上),docker logs 读的就是它。默认没有上限,话多的容器能把磁盘写满。设上限:单次用 --log-opt,或全局改守护进程配置 daemon.json 的 log-opts(Linux 是 /etc/docker/daemon.json,Docker Desktop 走 Settings → Docker Engine。改完重启,只对新容器生效)。轮转的代价是旧日志会被丢。

prune 不碰正在跑的容器的日志,也不治根——缓存会再攒、匿名卷会再造。它是扫帚不是堵源头:真办法是日志设上限、.dockerignore、RUN 里装完就清。

macOS 上 prune 释放的空间不一定立刻还给硬盘——Docker Desktop 的磁盘镜像是只长不缩的。

退出码直接说明「怎么死的」:0 正常结束;1 程序报错;125 docker run 自己参数错;126 命令不可执行;127 命令找不到;137 被 SIGKILL(128+9,常见于内存超限或 stop 超时);143 被 SIGTERM(128+15)。

Connection refused 和 Connection timed out 是两回事:前者说明到了那台机器、只是端口上没人在听(服务没起 / 没就绪 / 端口写错);后者说明包根本没到(网络不通)。

docker inspect 不用整段读:Config.Cmd、Config.Entrypoint 看启动配置;Config.Env 看最终环境变量(镜像默认值和你 -e 的合并);Config.ExposedPorts 看端口;Mounts 看挂载;State.ExitCode、State.Error、State.OOMKilled 看死因。

支持与分享

如果这篇文章对你有帮助,欢迎分享给更多人或打赏支持!

打赏
18附录:命令速查
https://hecloud.top/posts/tech/docker/18docker命令速查/
作者
贺小云
发布于
2026-10-04
许可协议
CC BY-NC-SA 4.0

评论区

Profile Image of the Author
贺小云
热爱技术与折腾的博客 Dancing with uncertainty. 与不确定性共舞
公告
出于成本考虑,贺云已全面转型Serverless架构
分类
标签
碎碎念
站点统计
文章
91
分类
5
标签
44
总字数
103,192
运行时长
0 天
最后活动
0 天前
站点信息
构建平台
Cloudflare Pages
博客版本
Firefly v6.16.5
文章许可
CC BY-NC-SA 4.0