I'm running Docker version 24.0.7, build afdd53b rootless on Ubuntu 22.04. A host folder I mounted to the container read-write is showing up effectively read-only.
On the host:
$ cat /etc/group
...
docker:x:999:gpeterso,mjl
mjl:x:3251:gpeterso
$ cat /etc/subuid
gpeterso:100000:65536
mjl:200000:65536
$ cat /etc/subgid
gpeterso:100000:65536
mjl:200000:65536
$ ls -al /home/gpeterso/mjl-dev/web/logs/
total 8
drwxrwxr-x 2 mjl mjl 4096 Dec 13 11:06 .
drwxrwxr-x 8 mjl mjl 4096 Sep 29 12:59 ..
Then I start the docker container and inspect it:
$ docker inspect mjl-dev-web
[
{
...
"Driver": "overlay2",
"Platform": "linux",
"MountLabel": "",
"ProcessLabel": "",
"AppArmorProfile": "",
...
"HostConfig": {
"Binds": [
...
"/home/gpeterso/mjl-dev/web/logs/:/usr/local/ROOT/logs/",
...
],
"Mounts": [
...
{
"Type": "bind",
"Source": "/home/gpeterso/mjl-dev/web/logs",
"Destination": "/usr/local/ROOT/logs",
"Mode": "",
"RW": true,
"Propagation": "rprivate"
},
...
],
"Config": {
...
"User": "mjl",
...
]
Then I connect to the container and try to access the directory:
$ docker exec -it mjl-dev-web /bin/bash
5af614bba1c8:/usr/local/ROOT$ cd logs
5af614bba1c8:/usr/local/ROOT/logs$ ls -al
total 8
drwxrwxr-x 2 nobody nobody 4096 Dec 13 11:06 .
drwxr-xr-x 1 root root 4096 Dec 13 11:20 ..
5af614bba1c8:/usr/local/ROOT/logs$ echo 'hi' >test.txt
bash: test.txt: Permission denied
5af614bba1c8:/usr/local/ROOT$ whoami
mjl
The docker container shows the folder mapped RW (read and write). So I assume it must be a user-mixup? Why is my mapped drive showing up as nobody or root instead of mjl? I tried sudo systemctl restart docker but I'm going to reboot now.
It's not a mixup, it's how user namespaces work. The uid/gid in the container is shifted according to the subuid/subgid entry. So uid/gid 0/0 in the container gets mapped to 200000/200000 on the host. There's no mapping of uid/gid on filesystem mounts, so if uid 200000 doesn't have access to write to the file on the host, uid 0 in the container won't have access to write to the file either.
One workaround is to define a subuid/subgid entry for the container root user that maps back to your host user, e.g. if mjl's uid/gid is 1001, an entry could be added like:
And root in the container would map to 1001/1001 on the host.
Another option would be to add a user on the host that matches the host mapped uid/gid that is a member of the group that can write to the folder. That may also need to be done in the container's /etc/group file with the container uid/gid, I'm not sure if the kernel enforces it at both places for bind mounts. In this case, that would involve adding a user to the host for mljcroot, uid/gid 200000/200000, that is a member of the mlj group.