为什么我对Docker容器中具有读取权限的文件的权限被拒绝?

为什么我对Docker容器中具有读取权限的文件的权限被拒绝?,docker,Docker,我有一个docker容器,在容器内的用户帐户“go”下运行GOCD服务器(java应用程序) 此容器将/etc/hosts装载为644(对所有用户都可读),但“go”帐户似乎无法读取此文件 这是证据: [~] # docker -v Docker version 1.10.2, build 0762ca4 # first enter the container as root and read the contents of # /etc/hosts ~] # docker exec -i

我有一个docker容器,在容器内的用户帐户“go”下运行GOCD服务器(java应用程序)

此容器将/etc/hosts装载为644(对所有用户都可读),但“go”帐户似乎无法读取此文件

这是证据:

[~] # docker -v
Docker version 1.10.2, build 0762ca4

# first enter the container as root and read the contents of 
# /etc/hosts
~] # docker exec  -it 0dac9bf0eab5 bash
  root@gocd:/# ls -la /etc/hosts
  -rw-r--r--+ 1 root root 164 Jun  2 22:03 /etc/hosts

    #no problem - file is readable
   root@gocd:/# cat /etc/hosts
   127.0.0.1    localhost
   ::1  localhost ip6-localhost ip6-loopback
   10.0.3.2 gocd
   root@gocd:/#

  # now change user to 'go'
   root@gocd:/# su - go -c bash
   go@gocd:/$ id
   uid=999(go) gid=999(go) groups=999(go)

   # check permissions - still 644
   go@gocd:/$ ls -la /etc/hosts
    -rw-r--r--+ 1 root root 164 Jun  2 22:03 /etc/hosts

   # but trying to read the file - causes error:
     go@gocd:/$ cat /etc/hosts
     cat: /etc/hosts: Permission denied

知道为什么会发生这种情况吗?

这个问题与ACL权限有关,ACL权限将/etc/hosts和/etc/resolv.conf的读取权限限制在根目录下

结果,在容器内任何其他帐户下运行的应用程序无法读取这些文件,这会导致网络堆栈出现问题。例如,需要将主机解析为ip的java应用程序将获得未知主机异常

如果容器是使用ContainerStation创建的,则问题会发生在QNAP系统中。ContainerStation中显然没有用于更改此行为的设置,但可以通过将以下命令添加到容器中的启动脚本中进行修复:

# modify ACL so go user would have read access
# to /etc/hosts and /etc/resolv.conf
# this is to avoid HostUnknown exception which happends
# when the gocd container is used on QNAP with ContainerStation
setfacl -m user:${USER_ID}:r /etc/resolv.conf
setfacl -m user:${USER_ID}:r /etc/hosts
对于想要运行GOCD server的QNAP用户,我已经在docker hub上创建了一个docker容器,其中已经包含此修复程序:


该问题与ACL权限有关,ACL权限将/etc/hosts和/etc/resolv.conf的读取权限仅限于根用户

结果,在容器内任何其他帐户下运行的应用程序无法读取这些文件,这会导致网络堆栈出现问题。例如,需要将主机解析为ip的java应用程序将获得未知主机异常

如果容器是使用ContainerStation创建的,则问题会发生在QNAP系统中。ContainerStation中显然没有用于更改此行为的设置,但可以通过将以下命令添加到容器中的启动脚本中进行修复:

# modify ACL so go user would have read access
# to /etc/hosts and /etc/resolv.conf
# this is to avoid HostUnknown exception which happends
# when the gocd container is used on QNAP with ContainerStation
setfacl -m user:${USER_ID}:r /etc/resolv.conf
setfacl -m user:${USER_ID}:r /etc/hosts
对于想要运行GOCD server的QNAP用户,我已经在docker hub上创建了一个docker容器,其中已经包含此修复程序:


我也试过了。它向我展示了/etc/hosts。相同的权限。唯一的区别是:-rw-r--r--。而不是+.+'表示这是一个ACL。检查它是否是带有“ls-le filename”的ACL。要删除ACL,请对文件运行echo | sudo chmod-E filename,或对目录运行echo | sudo chmod-R-E目录名。让我知道它是否有用。(如果它有效的话,我会把它作为一个答案发布)你是绝对正确的-这是ACL的事情。我已使用“删除ACL”root@gocd:/#setfacl-b/etc/hosts'和容器中的应用程序开始工作。所以所有的好处——唯一的一件事——我希望避免对我创建的每个容器都这样做。我使用QNAP和ContainerStation——它是docker的包装器,我怀疑是ContainerStation在/etc/hosts上创建了一个带有ACL的容器。非常感谢你的想法!以下是QNAP论坛上的相关讨论:将您的步骤作为答案发布。我也尝试过同样的方法。它向我展示了/etc/hosts。相同的权限。唯一的区别是:-rw-r--r--。而不是+.+'表示这是一个ACL。检查它是否是带有“ls-le filename”的ACL。要删除ACL,请对文件运行echo | sudo chmod-E filename,或对目录运行echo | sudo chmod-R-E目录名。让我知道它是否有用。(如果它有效的话,我会把它作为一个答案发布)你是绝对正确的-这是ACL的事情。我已使用“删除ACL”root@gocd:/#setfacl-b/etc/hosts'和容器中的应用程序开始工作。所以所有的好处——唯一的一件事——我希望避免对我创建的每个容器都这样做。我使用QNAP和ContainerStation——它是docker的包装器,我怀疑是ContainerStation在/etc/hosts上创建了一个带有ACL的容器。非常感谢你的想法!以下是QNAP论坛上的相关讨论:将您的步骤作为答案发布