Docker:将容器UID映射到主机上“不存在”的UID

Docker:将容器UID映射到主机上“不存在”的UID

我正在研究 Linux 命名空间,以便更好地了解 Docker(或者说 runc)如何与它们交互。
默认情况下,Docker 不会创建用户命名空间对于容器来说,意味着0容器内的 UID 也意味着0主机上的 UID。

USER解决此潜在安全问题的一种方法是使用Dockerfile 中的指令或--userDocker CLI 中的标志来更改容器内进程运行的 UID 。

据我了解,分配给容器的 UID(例如通过USERDockerfile 内部)必须与主机上现有的 UID 相同(即 UID 必须存在于 中/etc/passwd并且 GID 必须存在于 中/etc/group

因此我进行了一个实验并创建了一个包含以下内容的 Dockerfile:

FROM ubuntu

RUN groupadd -r -g 1001 appuser
RUN useradd -r -u 1001 -g appuser appuser

USER appuser

ENTRYPOINT ["sleep", "infinity"]

在主机上,没有 UID 为 的用户,1001也没有 GID 为 的组1001。然而令我惊讶的是,当我运行容器时ps aux | grep sleepsleep infinityDocker 容器中的进程出现了,并且关联的用户名不是名称,而是相应的 UID 1001

所以我的问题是:如何要求容器的进程在主机不知道的 UID 下运行?而且,如果内核不知道该 UID,它如何检查权限(例如,它是否为此目的创建了一个临时的非特权用户)?

答案1

不,你错了。UID 和 GID 不需要位于主机 /etc/passwd 中。如果你使用不存在的用户名,UID 只会显示为所有者。这是完全合法的做法。

我喜欢这样做:

FROM whatever
ARG UID=80
ARG USER=user
RUN useradd -u $UID $USER && mkdir /deploy /logs && chown -R $USER:$USER {/deploy/,/logs/}
USER $USER

回答您的问题:

  1. 如何要求容器的进程在主机不知道的 UID 下运行?

如上。

  1. 如果内核不知道该 UID,它将如何检查权限(例如,它是否为此目的创建一个临时的非特权用户)?

如果 UID 没有权限,则它没有权限。例如,假设一个文件具有 chmod 770,组 root:users。用户 root 和组 users 中的任何人都具有读写和执行权限。具有未知 UID 的用户对该文件的权限为 0,这意味着它无法读取、写入或执行(查看)该文件。

现在假设一个文件具有 chmod 777。用户、组和任何人现在都具有 rwx 权限。这意味着即使用户是未知的并且因此没有权限,它仍然可以访问和执行此文件。

这就是为什么您永远不要对任何东西设置 chmod 777。并且通常避免对代表“任何人”组的第三位设置超过读取权限。

相关内容