Docker image now defaults to non-root user

Greetings! I wanted to announce that the container image for the next nightly (which will eventually end up in the 8.1.26 release) contains changes to the default user/group that is used to launch Ignition.

The default user is now ignition with UID/GID of 2003. You'll have to perform a migration in order to successfully transition your existing data volumes, otherwise you may encounter an error such as this one below:

init     | 2023/02/13 11:50:21 | Creating init.properties file
init     | 2023/02/13 11:50:21 | Detected Ignition Volume from prior version (8.1.24), running Upgrader...
java.io.FileNotFoundException: /usr/local/bin/ignition/data/ignition.conf (Permission denied)
...

The above is one such manifestation of the new ignition user being unable to modify files that are owned by root within an attached data volume. You can choose between at least a couple options:

  • Explicitly set the user for the container to be 0:0 (i.e. root user:group), overriding the new default. You can do this with either --user 0:0 in your docker run or the user directive in Compose. Note that you're not getting any of the advantages here of non-root execution.
  • Migrate your data volume by temporarily launching a container with --user 0:0 and environment variables IGNITION_UID=2003 and IGNITION_GID=2003. This will leverage the existing root step-down functionality and remap your data volume file ownership to the target UID/GID that matches the new default user. After startup, you can stop the container and re-launch without any explicit user or UID/GID environment variable overrides in the future.

We're working on updating the docs site with more detailed guidance on the migration that should be available for the final release.

Let me know if you have any questions!

3 Likes

So, AmbientCapabilities=CAP_NET_BIND_SERVICE CAP_NET_RAW in an override?

If you also need these capabilities (for sub-1024 port binding as non-root user and raw socket use for ICMP, respectively), yes, you'd specify those in your container config.

refs:

My point was that those should be the default--your image should include that in an override. IMNSHO. { Well, arguably, Ignition's default SystemD unit file should have it. }

I should clarify that the Docker image launches that gateway directly, no systemd involved (as is typical in most container images). The capabilities that a container gets when launched is controlled by the container runtime--see some info here. There isn't a way to "request" default capabilities within the OCI image definition that I'm aware of.

1 Like

Tiny addendum: We just upgraded over this bump today and it broke us since we build a derivative image with git tools and our old Dockerfile was expecting root. After double-checking that things run as ignition normally, just adjusted our Dockerfile to look like this:

FROM inductiveautomation/ignition:8.1.26
USER root
RUN apt-get update && \
    apt-get install -y git && \
    rm -rf /var/lib/apt/lists/*
USER ignition

If I was more thoroughly adept with Docker I would've expected this, but I'm not and I didn't. Thankfully someone else on our team knows more Docker and set me straight quickly.

There is migration guidance for existing volumes (that are being upgraded to 8.1.26) in our documentation here: Docker Image - Ignition User Manual 8.1 - Ignition Documentation

@justin.brzozoski, agreed that for derived images going forward, you'll need to temporarily set USER root to do things like OS package updates and then set USER ignition at the end. Just be careful if you do anything that creates files within the Ignition installation, you'll want to make sure that those files remain chown'd to ignition:ignition. :+1:

2 Likes

Not out of the woods yet ... we have our developer stations set up such that data/projects is mounted to a working directory on the host system and I just ran into this:

> git fetch
fatal: detected dubious ownership in repository at '/home/justin/work/ignition_projects'
To add an exception for this directory, call:

        git config --global --add safe.directory /home/justin/work/ignition_projects

Probably simplest to run the image on my devstation as root and pass in my UID/GID ... :confused:

Also agreed. If you use the IGNITION_UID and IGNITION_GID environment variables combined with starting the gateway as root, it should work fine (and Ignition itself will still end up running as that desired IGNITION_UID through the root stepdown). Only other path would be to reset file ownership of the Ignition installation within your derived image to your target UID/GID; only trouble there is if you've got other users whose workstations have different UID/GIDs (likely). That is why we've retained that root stepdown functionality--for dev.