我使用官方的golang docker镜像来编译我的go程序,并将生成的可执行文件放在映射到我的主机目录的卷上。
问题是docker生成的文件属于root:root,这非常烦人,因为我不想通过sudo运行我的脚本。
我搜索了使docker容器以非root身份运行的解决方案,但是我发现的方法需要更改Dockerfile并将用户添加到图像中,例如
http://gbraad.nl/blog/non-root-user-inside-a-docker-container.html
有没有办法使docker容器作为主机上的CURRENT用户运行,即用户A运行此图像将生成文件属于A:A,而用户B生成文件属于B:B,而A和B都是在主机上定义的用户(即卷所在的位置),而不需要通过Dockerfile将A和B添加到映像中?
答案 0 :(得分:1)
我能够为这个问题制定一个“解决方案”。有点粗糙,但据我目前所知,它无需将用户安装到映像中即可完成工作。
本质上,我将libnss-wrapper
与定制的run_as_user
脚本结合使用,而我又使用这些脚本为那些使我为未知UID麻烦的命令命名(例如ssh
)。
Dockerfile
FROM whatever
RUN apt-get update && apt-get install -y libnss-wrapper
COPY run_as_user /usr/local/bin/
RUN chmod a+x /usr/local/bin/run_as_user
# copy some command aliases that need to be early on the path
COPY ssh /usr/local/sbin
RUN chmod a+x /usr/local/sbin/ssh
run_as_user
脚本此脚本根据当前用户的UID和GID创建一个passwd
和group
文件,然后使用该文件来参数化libnss-wrapper
#!/bin/sh
# run a command as (non-existent) user, using libnss-wrapper
U=`id -u`
G=`id -g`
HOME_DIR=/tmp/user
PASSWD=/var/tmp/passwd
GROUP=/var/tmp/group
if [ ! -d "$HOME_DIR" ]; then
mkdir "$HOME_DIR"
fi
if [ ! -f "$PASSWD" ]; then
echo "user::$U:$G::$HOME_DIR:" > "$PASSWD"
fi
if [ ! -f "$GROUP" ]; then
echo "user::$G:" > "$GROUP"
fi
LD_PRELOAD=libnss_wrapper.so NSS_WRAPPER_PASSWD="$PASSWD" NSS_WRAPPER_GROUP="$GROUP" "$@"
ssh
别名脚本#!/bin/sh
SSH=/usr/bin/ssh
/usr/local/bin/run_as_user "$SSH" "$@"
同样,这是有效的,因为/usr/local/sbin
首先在我的路上。
到目前为止,这一直为我工作。如果对此有(严重)问题,我很乐意向他们指出。
答案 1 :(得分:0)
我用base alphine-golang加上git工具),在我的笔记本电脑上使用-u arg运行,但是如果我在debian虚拟机上运行它,它会告诉我uid 1001没有用户
理想情况下,您可以使用正确的预期ID制作自己的图像(基于现有图像):
RUN useradd -r -u 1001 -g appuser appuser
USER appuser
请参阅 Understanding how uid and gid work in Docker containers 中的“Marc Campbell”:
OP补充道:
我理解原因,因为这正是我试图避免的:将用户添加到图像中 如果我的问题没有解决,我会尝试直接修改容器。
实际上,还有另一种选择,它允许您不修改图像而不添加用户: userns or user remap (since docker 1.10)。但是,正如我mention here所示,您需要使用docker 17.06来避免一些错误。