Telling Docker Who You Are

by Christoph Schiessl on DevOps and Docker

Did you ever notice that if you create files on a Docker bind mount from within a container, they all belong to root on the host system? This behavior can lead to permission problems if, for instance, you depend on Docker to automate parts of your build pipeline.

Let me start with some background information about user management on Linux. Internally, Linux maps user names to user IDs (aka UIDs) and group names to group IDs (aka GIDs). ID 0 is special for users and groups because it identifies the root user and the root group. This is hard-coded in the kernel and is true on all Linux systems - even inside Docker containers.

With id, it's straightforward to find the UID/GID of a given user:

$ echo "My UID is $(id -u), and my GID is $(id -g)."
My UID is 1000, and my GID is 1000.
$ echo "root's UID is $(id -u root), and root's GID is $(id -g root)."
root's UID is 0, and root's GID is 0.

Similarly, you can use stat to find the owner of files and directories:

$ touch first-experiment
$ stat --format="Owner UID is %u, and owner GID is %g." first-experiment
Owner UID is 1000, and owner GID is 1000.

Alright, that's all the background information you need to know. Now, let's create a simple Docker image and run our first experiment:

FROM alpine:latest

VOLUME /work

ENTRYPOINT ["sh", "-c"]
$ echo "My UID is $(id -u), and my GID is $(id -g)."
My UID is 1000, and my GID is 1000.
$ docker build -t bugfactory/permission-test .
[[[ ... output removed ... ]]]
$ docker run --volume $(pwd):/work \
             bugfactory/permission-test \
             "touch second-experiment"
$ stat --format="Owner UID is %u, and owner GID is %g." second-experiment
Owner UID is 0, and owner GID is 0.

Our command successfully created the file second-experiment, but the file belongs to root as indicated by the UID/GID in the output's last line. As it turns out, Docker runs commands as root by default. To tell Docker to use a different UID/GID, we can use its --user UID:GID flag. On the man page for docker run, this is documented as follows:

-u, --user=""
   Sets the username or UID used and optionally the groupname or GID for the specified command.

Knowing about --user and id, we can compose an option such that Docker always runs commands as the user who invoked docker run on the host system: --user $(id -u):$(id -g). Let's try this:

$ echo "My UID is $(id -u), and my GID is $(id -g)."
My UID is 1000, and my GID is 1000.
$ docker run --volume $(pwd):/work \
             --user $(id -u):$(id -g) \
             bugfactory/permission-test \
             "touch third-experiment"
$ stat --format="File owner UID is %u, and owner GID is %g." third-experiment
File owner UID is 1000, and owner GID is 1000.

As before, the command successfully created the file third-experiment, but this time, it belongs to our UID/GID, as proven by the output's last line. Problem solved!

Ready to Learn More Web Development?

Join my Mailing List to receive one article per week.

I send one email per week on building performant and resilient Web Applications with Python, JavaScript and PostgreSQL. No spam. Unscubscribe at any time.

Continue Reading?

Here are a few more Articles for you ...

Correctly Link Atom/RSS Feeds with your HTML Pages

Learn how to <link> Atom and RSS feeds from your HTML documents to make them discoverable for clients and, by extension, for your readers.

By Christoph Schiessl

Generating Random Numbers According to a Probability Distribution

Learn how to generate random numbers in PostgreSQL whose distribution follows the uniform, exponential, or normal probability distribution.

By Christoph Schiessl on PostgreSQL

Tracking Scroll Depth to Measure Visitor Engagement

Calculate Scroll Depth as a percentage of page height and send custom events to Plausible, the GDPR-compliant analytics platform. Vanilla JavaScript only.

By Christoph Schiessl on JavaScript

Christoph Schiessl

Hi, I'm Christoph Schiessl.

I help you build robust and fast web applications.

I'm available for hire as a freelance web developer, so you can take advantage of the more than a decade of experience I have collected working on many projects across several industries. Most of my clients are building web-based SaaS applications in a B2B context and depend on my expertise in various capacities.

More often than not, my involvement includes hands-on development work using technologies like Python, JavaScript, and PostgreSQL. Furthermore, if you already have an established team, I can support you as a technical product manager with a passion for simplifying complex processes. Lastly, I'm also an avid writer and educator who takes pride in breaking down technical concepts into the simplest possible terms.