I’m pretty new with Docker. I am taking over a project previously set up by someone else. The containers for this project are managed by Docker Swarm.
I understood that the Docker images are unmutable but it’s possible to modify application parameters within the container.
However, in the way the project is currently done, if our customer wants to modify a setting on his platform (for example change the frequency of a batch execution, enable or disable an option, …), he must regenerate a Docker image from the current state of the container to create a new Docker image, because if he modifies settings only in the container, modifications risk being lost (because they are only on the write-layer).
I’d like to improve this behavior because it is not acceptable for our customer not to be able to just change a setting. I have a feeling that it would be good to use a Docker volume containing the configuration files that can be changed by the customer.
But it means that we have to put these files in a specific directory ? the application may stop working because it expects to find these files inside of itself, in her own file tree (much like files for a webapp in the shared/resources directory in a tomcat server).
What’s the best way to make files editable without having to regenerate an image ?
It pretty much depends on how your application is designed.
You can map any single folder (and all its files ans subfolders) from the host to any folder inside the container - the same is possible for single files. You can map remote fileshares into container folders. Make sure to observe and understand the behavior of what happens when you mount folders into container folder.
May I suggest this free and highly recommend self-paced docker training: https://container.training/intro-selfpaced.yml.html? If you read slides 450 to 475 you should get a basic understanding of volume. Though, I would recommend to read all slides and activly perform the exercerses. Docker is more fun, if you know what you’re doing Now imagine your predecesor would have read it and your would inherit an environment managed by such someone…
This simple example shows how configs work in just a few commands. For a real-world example, continue to Advanced example: Use configs with a Nginx service.
Add a config to Docker. The docker config create command reads standard input because the last argument, which represents the file to read the config from, is set to -.
$ echo “This is a config” | docker config create my-config -
Create a redis service and grant it access to the config. By default, the container can access the config at /my-config, but you can customize the file name on the container using the target option.
$ docker service create --name redis --config my-config redis:alpine
Verify that the task is running without issues using docker service ps. If everything is working, the output looks similar to this:
$ docker service ps redis
ID NAME IMAGE NODE DESIRED STATE CURRENT STATE ERROR PORTS
bkna6bpn8r1a redis.1 redis:alpine ip-172-31-46-109 Running Running 8 seconds ago
Get the ID of the redis service task container using docker ps, so that you can use docker container exec to connect to the container and read the contents of the config data file, which defaults to being readable by all and has the same name as the name of the config. The first command below illustrates how to find the container ID, and the second and third commands use shell completion to do this automatically.
$ docker ps --filter name=redis -q
docker container exec (docker ps --filter name=redis -q) ls -l /my-config
-r–r--r-- 1 root root 12 Jun 5 20:49 my-config
docker container exec (docker ps --filter name=redis -q) cat /my-config
This is a config
Try removing the config. The removal fails because the redis service is running and has access to the config.
$ docker config ls
ID NAME CREATED UPDATED
fzwcfuqjkvo5foqu7ts7ls578 hello 31 minutes ago 31 minutes ago
$ docker config rm my-config
Error response from daemon: rpc error: code = 3 desc = config ‘my-config’ is
in use by the following service: redis
Remove access to the config from the running redis service by updating the service.
$ docker service update --config-rm my-config redis
Repeat steps 3 and 4 again, verifying that the service no longer has access to the config. The container ID is different, because the service update command redeploys the service.
docker container exec -it (docker ps --filter name=redis -q) cat /my-config
cat: can’t open ‘/my-config’: No such file or directory
Stop and remove the service, and remove the config from Docker.
$ docker service rm redis
$ docker config rm my-config