Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

UID/GID sync scripts #25

Open
Chuxel opened this issue Apr 7, 2022 · 11 comments
Open

UID/GID sync scripts #25

Chuxel opened this issue Apr 7, 2022 · 11 comments
Labels
proposal Still under discussion, collecting feedback

Comments

@Chuxel
Copy link
Member

Chuxel commented Apr 7, 2022

Using bind mounts on Linux (inclusive of WSL) can be confusing since the actual file descriptors from the host are used - inclusive of all permissions. The problem is that the user in the container - whether root or otherwise, can have different UID/GIDs than the host user - which means that files in the source folder can be unreadable or unwritable on either the host or the container depending on the situation. While you can use a volume to house source code instead of bind mounts, its useful to be able to use local source code mounts as well and can be manditory in CI/Automation scenarios as #9 is released.

The spec and reference CLI includes an updateRemoteUserUID property that defaults to true to deal with this problem which automatically updates a specified non-root user (in containerUser or rootUser).

However, while this does automatically update permissions in that user's $HOME directory in the container, it does not update other locations. This is problematic in a number of cases, but particularly when packages or other content the user needs to work with is not located there.

Generally, the needed update is a chown -R on a directory, but this is not always the case - and more subtle updates can often be better (e.g. using find /location -uid 1000 -execdir chown username-here {} \+). To provide a nuanced way to handle this, I'd propose a model similar to #19 where either Dockerfiles or dev container features can add a script to a known location. When a processor like the dev container CLI then executes a UID/GID update, these bash scripts are fired to make the needed updates. These would run as root and should be owned by root as a part of final image prep much like the usermod/groupmod commands when this step is needed.

@Chuxel Chuxel added the proposal Still under discussion, collecting feedback label Apr 7, 2022
@bhack
Copy link

bhack commented Apr 30, 2022

We could consider also moby/moby#42134 (comment)

@Chuxel
Copy link
Member Author

Chuxel commented Aug 29, 2022

@bhack Namespace remapping can actually make things worse since you have to run the container as root for bind mounting to work. At that point, any tool that dislikes running as root will fail.

Cloning into a volume instead avoids that particular problem, but it's also less convenient for quick actions and work when the source is local. I haven't found a slam dunk for how to resolve that particular issue. Namespace mapping also breaks certain things like docker-in-docker that are quite common.

If you are running namespace mapped, you can disable UID sync'ing via the updateRemoteUserUID in devcontainer.json property already.

I wish there was an optional remapping on bind mounts but there isn't right now. 🤷‍♂️ Doesn't seem to be a perfect answer near as I can tell yet. Love to know if anyone finds one.

@bhack
Copy link

bhack commented Aug 29, 2022

@bhack Namespace remapping can actually make things worse since you have to run the container as root for bind mounting to work. At that point, any tool that dislikes running as root will fail.

Are you talking about the idmapping part of the mentioned thread?

This could (probably) be made easier if support for idmapped mounts would be added, but this requires very recent kernel versions (see moby/moby#2259 and moby/moby#2259 (comment) for a longer discussion)

P.s. See also moby/moby#28593 (comment)

@Chuxel
Copy link
Member Author

Chuxel commented Aug 29, 2022

@bhack Namespace remapping can actually make things worse since you have to run the container as root for bind mounting to work. At that point, any tool that dislikes running as root will fail.

Are you talking about the idmapping part of the mentioned thread?

This could (probably) be made easier if support for idmapped mounts would be added, but this requires very recent kernel versions (see moby/moby#2259 and moby/moby#2259 (comment) for a longer discussion)

Yeah the referenced comment is making a statement about the design for the docker daemon running as something other than root. Running as non-root actually makes wanting to run as non-root inside the container harder - and that makes this overall situation worse. If you're cool running your container as root and you don't need elevated container privs it works fine. One thing I haven't tried is to see if you can run the daemon as some other user than your user to see if the sync'ing can kick in correctly in that case.

Or did I misunderstand the reference in your comment?

@bhack
Copy link

bhack commented Aug 30, 2022

Running as non-root actually makes wanting to run as non-root inside the container harder - and that makes this overall situation worse.

Yes this is the current case of docker rootless case with non-root user in the image.

But with future idmppaing mount support (moby/moby#28593 (comment)) cannot we map the mount in the container with the user we want?

@bhack
Copy link

bhack commented Aug 30, 2022

I don't know if you could test it with podman as it seems mereged there containers/podman#12298

@Chuxel
Copy link
Member Author

Chuxel commented Aug 30, 2022

Yes this is the current case of docker rootless case with non-root user in the image.

But with future idmppaing mount support (moby/moby#28593 (comment)) cannot we map the mount in the container with the user we want?

Got it, yeah, once that is there the situation probably changes, I agree. Some of the comments from May in 2259 are encouraging. Fingers crossed that lands. We'd still need a fallback for kernels < 5.12, but that would narrow the problem and speed the whole process up.

@chrmarti
Copy link
Contributor

On using rootless: To use a non-root user (containeruser) inside the container in rootless mode we need two users (root and the non-root user) inside the container mapped to two users on the host (at least that is my understanding). Can we use a secondary host user (hostuser-root) belonging to the primary host user (hostuser)? The mapping would be hostuser-root > root and hostuser > containeruser. Files would be owned by hostuser and containeruser. We would need sudo set up for hostuser to run processes as hostuser-root (e.g., to start the container). This might avoid the need for updating the UID/GID completely.

@bhack
Copy link

bhack commented Sep 12, 2022

I don't know if this is still valid and/or the same on Docker:

https://www.redhat.com/sysadmin/rootless-podman-makes-sense

@chrmarti
Copy link
Contributor

Reading the article, it looks like there is only one regular host user per container, all others map to >100000 host UIDs.

@felipecrs
Copy link

felipecrs commented Oct 28, 2022

I have a suggestion for now: allow users to provide their own updateRemoteUserUID scripts through custom features (in this case we are only missing the exposure of some additional ARGs/ENVs like LOCAL_USER, LOCAL_UID, LOCAL_GID, and LOCAL_HOME).

For example, I use docker-on/from-docker in all my devcontainers, and I would like to perform some additional remappings to the user within the container instead of only changing its UID/GID. For example, I'd like to change the username from vscode (example) to $LOCAL_USER and the /home/vscode to $LOCAL_HOME as well.

This would be super nice for me. :)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
proposal Still under discussion, collecting feedback
Projects
None yet
Development

No branches or pull requests

4 participants