【问题标题】:Why does the uid of files created in a docker bind mount differ based on the host OS?为什么在 docker bind mount 中创建的文件的 uid 会因主机操作系统而异?
【发布时间】:2019-09-11 23:32:49
【问题描述】:

运行以下命令会在当前目录中创建一个文件foo

docker run --rm -v `pwd`:/workspace -w /workspace alpine:3.10.2 touch foo

在我的 Mac(macOS 10.14.6 (18G95),Docker 版本 19.03.2,内部版本 6a30dfc)上,创建的文件归“我”所有,正如输出 ls -l foo 所确认的那样。

-rw-r--r--  1 till  staff  0 11 Sep 14:08 foo

但是,在工作站(Ubuntu 16.04.1,Docker 版本 19.03.2,内部版本 6a30dfc)上,创建的文件归 root 所有。

-rw-r--r-- 1 root root 0 Sep 11 13:32 foo

你知道为什么相同的命令会产生不同的结果吗?

【问题讨论】:

    标签: macos docker ubuntu


    【解决方案1】:

    我不是 Mac 用户,但我相信我知道会发生什么:您看到的可能是 Docker for Mac 实际上在虚拟机中运行 Docker 的结果。

    当你在 Docker 的原生环境 Linux 中运行 Docker 时,一切都按预期工作:容器化进程是运行在主机内核上的普通进程;它有一些 UID 和 GID(在您的情况下 - 0:0,即 root:root),并且当此进程创建任何文件时,该文件由这些 UID 和 GID 拥有。 Linux 中的 Docker 卷只是绑定挂载,因此当写入从容器传播到主机系统时,这里没有什么特别的事情发生。

    当你在 Mac 上做同样的事情时,事情就更复杂了:Docker 并不直接在 Mac 主机上运行,​​而是在底层使用 Linux 虚拟机,而 Linux 虚拟机反过来又运行 Docker。在这种情况下,卷只是绑定挂载 - 将目录挂载到 VM 的工作由管理程序管理。

    我不熟悉 Docker 在 Mac 中使用的特定管理程序,但是,例如,在 VirtualBox 中,当您与 VM 共享某个主机目录时,VM 内的实际挂载点具有特殊的文件系统类型( vboxsf),并且这个文件系统的驱动是 VBox 的客户添加的一部分,它协助主机-虚拟机交互。

    从 VM 中写入此目录的结果与您观察到的完全一样:所有者被 VBox翻译 为适当的 UID/GID。

    假设,我在与主机同步的 VM 中有一个目录 /test

    # mount | grep test
    test on /test type vboxsf (rw,nodev,relatime,iocharset=utf8,uid=1000,gid=1000)
    

    我在root的同时向这个目录写了一些东西:

    # cd /test
    # echo abcd > testfile
    # ls -ln
    ...
    -rw-r--r-- 1 1000 1000 5 Sep 11 14:57 testfile
    

    如您所见,该文件的所有者不是root — 它被翻译为1000:1000。来自主机的相同文件是:

    $ ls -ln test
    ...
    -rw-r--r-- 1 1000 1000 5 Sep 11 17:57 testfile
    

    因此,您很可能会观察到相同的行为:当 Linux VM 中的 Docker 对卷执行写入时,Docker 使用的管理程序(无论它在您的系统中是什么)执行相同的转换,并且您会看到文件更改后的所有者(您的 user:group 而不是 root:root)。

    【讨论】:

      猜你喜欢
      • 2021-10-01
      • 2018-12-30
      • 1970-01-01
      • 2015-06-07
      • 1970-01-01
      • 2017-06-06
      • 2017-08-30
      • 2015-08-09
      相关资源
      最近更新 更多