如何把文件从 Docker 容器复制到宿主机?
用 docker cp 容器名:容器内路径 宿主机路径 即可把容器内文件拷到宿主机,运行中与已停止的容器都支持;批量目录用挂载卷更方便。本文给出用法与限制。
做法:docker cp <容器名或ID>:/容器内路径 /宿主机路径——一条命令把容器里的文件或目录拷到宿主机,容器在运行或已停止状态都可以。典型场景:取回容器内生成的日志、构建产物、配置文件做排查。
基本用法
# 拷单个文件
docker cp myapp:/var/log/app/error.log ./error.log
# 拷整个目录
docker cp myapp:/var/log/app ./app-logs
若目标app-logs已存在为目录,复制源app目录会形成app-logs/app;只复制内容可使用容器源路径 /var/log/app/.。目标父目录需存在。
注意事项
- 容器无需运行:停止状态的容器同样能拷,适合抢救崩溃容器的现场文件。
- 特殊文件系统不能拷:
/proc、/sys、/dev、tmpfs 挂载点内的文件不在拷贝范围。 - 权限保持:拷贝以执行 docker 命令的用户身份落盘,文件属主可能变化,注意后续读取权限。
- 符号链接:
docker cp默认保留源符号链接;需要跟随源链接时使用-L,并核对目标范围。
替代方案:什么时候不该用 cp
- 持续共享文件(如日志持续产出)→ 用挂载卷
-v /host/logs:/var/log/app,宿主机实时可见 - 镜像内自带文件 → 直接从镜像取材:
docker create不启动容器 +docker cp,或重建镜像时 COPY 出来 - K8s 环境 → 用
kubectl cp pod/name:/path ./path -c 容器名
常见问题(FAQ)
Q:docker cp 会受容器内进程写入影响吗?
A:拷贝不是原子快照,期间并发写入可能得到不一致或不完整内容;重要文件先让应用 flush/轮转再拷。
Q:能拷到远程另一台机器的 Docker 吗?
A:Docker CLI可通过远程context/DOCKER_HOST连接远程daemon,容器端在远端,LOCALPATH仍是运行CLI这台机器的本地路径。
Q:拷大目录慢怎么办?
A:docker cp 底层走 tar 流,目录大时可在容器内先打包压缩再拷单文件。