在容器和本地文件系统之间复制文件/文件夹
概要
podman cp [选项][*容器*:]源文件路径 [容器:]目标文件路径
podman container cp [选项][*容器*:]源文件路径 [容器:]目标文件路径
说明
podman cp 命令允许将 源文件路径 的内容复制到 目标文件路径。文件可以从容器复制到本地机器,也可以从本地机器复制到容器,或者在两个容器之间复制。
如果为 SRC_PATH
或 DEST_PATH
指定了 -
,则还可以从 STDIN
接收或向 STDOUT
输出 tar 归档文件。
容器可以是运行状态或停止状态,而 源文件路径 或 目标文件路径 可以是文件或目录。
重要提示:podman cp 命令假定容器路径是相对于容器根目录(/
)的,这意味着提供初始的正斜杠是可选的,因此将 compassionate_darwin:/tmp/foo/myfile.txt
和 compassionate_darwin:tmp/foo/myfile.txt
视为相同的。
本地机器的路径可以是绝对路径或相对路径。 该命令将本地机器的相对路径解释为相对于运行 podman cp 的当前工作目录的路径。
假设路径分隔符为 /
,第一个参数为 源文件路径,第二个参数为 目标文件路径,则行为如下:
源文件路径 指定一个文件:
- 目标文件路径 不存在
- 文件将被保存到在 目标文件路径 创建的新文件中(请注意,父目录必须存在)。
- 目标文件路径 存在且是一个文件
- 目标文件将被源文件的内容覆盖。
- 目标文件路径 存在且是一个目录
- 文件将被复制到此目录中,并使用从 源文件路径 获取的基本名称。
源文件路径 指定一个目录:
- 目标文件路径 不存在
- 创建一个 目标文件路径 作为目录,并将源目录的内容复制到这个目录中。
- 目标文件路径 存在且是一个文件
- 错误条件:无法将一个目录复制到一个文件中。
- 目标文件路径 存在且是一个目录
- 源文件路径 以
/
结尾- 源目录将被复制到这个目录中。
- 源文件路径 以
/.
结尾(即斜杠后跟一个点)- 源目录的内容将被复制到这个目录中。
- 源文件路径 以
该命令要求根据以上规则 源文件路径 和 目标文件路径 必须存在。
如果 源文件路径 是本地的并且是一个符号链接,则默认情况下将复制符号链接的目标。
冒号 ( : ) 被用作容器与其路径之间的分隔符,它也可以用于在本地机器上指定 src_path 或 dest_path 的路径,例如 file:name.txt
。
重要提示:在本地机器路径中使用 冒号 ( : ) 时,必须明确指定相对路径或绝对路径,例如:/path/to/file:name.txt
或 ./file:name.txt
使用 -
作为 src_path 会将 STDIN
的内容作为 tar 归档文件进行流处理。命令会将 tar 的内容提取到容器中的 DEST_PATH
。在这种情况下,dest_path 必须指定一个目录。使用 -
作为 dest_path 会将资源(可以是目录)的内容作为 tar 归档文件流处理到 STDOUT
。
请注意,当从正在运行的非 root 容器复制文件时,podman cp
会忽略权限错误。非 root 容器内部的 TTY 设备属于主机上的 root 用户,因此无法在容器的用户命名空间中读取它们。
此外,请注意 podman cp
不支持通配符(例如 cp dir/*.txt
)。要从主机复制多个文件到容器,请使用 xargs(1)
或 find(1)
(或用于命令串联的类似工具)与 podman cp
结合使用。要从容器复制多个文件到主机,请使用 podman mount CONTAINER
并操作返回的挂载点(请参阅下面的替代方案)。
选项
--archive, -a
归档模式(复制所有 UID/GID 信息)。 当设置为 true 时,复制到容器的文件将更改其所有权为主要 UID/GID。 当设置为 false 时,保持从归档源中的 UID/GID 而不是将它们更改为目标容器的主要 UID/GID。 默认值为 true。
--overwrite
允许目录被非目录覆盖,反之亦然。默认情况下,当尝试覆盖时(例如,用一个目录覆盖一个常规文件),podman cp
会报错。
替代方案
Podman 在实现主机与容器之间复制文件的功能时,除了 podman cp
之外,还具有更强的能力。
使用标准的 podman-mount(1) 和 podman-unmount(1) 命令可以利用整个 Linux 工具链,而不仅仅是 cp 命令。
通过几个简单的命令,就可以实现将内容从容器中复制出来或复制到容器中。例如:
要将容器中的 /etc/foobar
目录复制到主机上的 /tmp
目录,可以执行以下命令:
mnt=$(podman mount CONTAINERID)
cp -R ${mnt}/etc/foobar /tmp
podman umount CONTAINERID
要将 tar 包解压到容器中,可以执行以下命令:
mnt=$(podman mount CONTAINERID)
tar xf content.tgz -C ${mnt}
podman umount CONTAINERID
要在没有安装 dnf 的容器中安装软件包,可以执行以下命令:
mnt=$(podman mount CONTAINERID)
dnf install --installroot=${mnt} httpd
chroot ${mnt} rm -rf /var/log/dnf /var/cache/dnf
podman umount CONTAINERID
通过使用 podman mount
和 podman umount
,可以使用所有标准的 Linux 工具来在容器内外移动文件,而不仅仅是 cp 命令。
EXAMPLES
示例
从主机复制文件到容器
podman cp /myapp/app.conf containerID:/myapp/app.conf
这个命令将主机上的 /myapp/app.conf
文件复制到容器 containerID
的 /myapp/app.conf
路径下。
从一个容器复制文件到另一个容器的目录
podman cp containerID1:/myfile.txt containerID2:/tmp
这个命令将容器 containerID1
中的 /myfile.txt
文件复制到容器 containerID2
的 /tmp
目录下。
从容器复制目录到主机目录
podman cp containerID:/myapp/ /myapp/
这个命令将容器 containerID
中的 /myapp/
目录复制到主机的 /myapp/
目录下。
复制容器目录内容到主机目录
podman cp containerID:/home/myuser/. /home/myuser/
这个命令将容器 containerID
中的 /home/myuser/
目录下的所有内容复制到主机的 /home/myuser/
目录下,注意结尾的 .
表示复制目录内容而非目录本身。
将一个容器中的目录复制到另一个容器的目录
podman cp containerA:/myapp containerB:/newapp
这个命令将容器 containerA
中的 /myapp
目录复制到容器 containerB
的 /newapp
目录下。
从标准输入流复制 tar 归档到容器
podman cp - containerID:/myfiles.tar.gz < myfiles.tar.gz
这个命令将本地文件 myfiles.tar.gz
作为 tar 归档,通过标准输入流复制到容器 containerID
的 /myfiles.tar.gz
路径下。注意 -
符号的使用,它表示从标准输入读取数据。
另请参阅
podman(1), podman-mount(1), podman-unmount(1)
这些命令和工具与 podman cp
相关,提供了不同的功能来管理和操作容器。podman
是主要的容器管理工具,而 podman-mount
和 podman-unmount
则用于挂载和卸载容器的文件系统,允许用户直接访问容器内部的文件系统。这些工具提供了更灵活的方式来处理容器和主机之间的文件交互。