I want all running containers on my server to always use the latest version of an official base image e.g. node:16.3
in order to get security updates. To achieve that I have implemented an image update mechanism for all container images in my registry using a CI workflow which has some limitations described below.
I have read the answers to this question but they either involve building or inspecting images on the target server which I would like to avoid.
I am wondering whether there might be an easier way to achieve the container image updates or to alleviate some of the caveats I have encountered.
Current Image Update Mechanism
I build my container images using the FROM
directive with the minor version I want to use:
FROM node:16.13
COPY . .
This image is pushed to a registry as my-app:1.0
.
To check for changes in the node:16.3
image compared to when I built the my-app:1.0
image I periodically compare the SHA256 digests of the layers of the node:16.3
with those of the first n=(number of layers of node:16.3
) layers of my-app:1.0
as suggested in this answer. I retrieve the SHA256 digests with docker manifest inpect <image>:<tag> -v
.
If they differ I rebuild my-app:1.0
and push it to my registry thus ensuring that my-app:1.0
always uses the latest node:16.3
base image.
I keep the running containers on my server up to date by periodically running docker pull my-app:1.0
on the server using a cron job.
Limitations
- When I check for updates I need to download the manifests for all my container images and their base images. For images hosted on Docker Hub this unfortunately counts against the download rate limit.
- Since I always update the same image
my-app:1.0
it is hard to track which version is currently running on the server. This information is especially important when the update process breaks a service. I keep track of the updates by logging the output of thedocker pull
command from the cron job. - To be able to revert the container image on the server I have to keep previous versions of the
my-app:1.0
images as well. I do that by pushing incremental patch version tags along with themy-app:1.0
tag to my registry e.g.my-app:1.0.1
,my-app:1.0.2
, ... - Because of the way the layers of the base image and the app image are compared it is not possible to detect a change in the base image where only the uppermost layers have been removed. However I do not expect this to happen very frequently.
Thank you for your help!