I have a named-volume container deploying shared resources to worker nodes in a swarm for a production release. It seems to deploy, but won't populate the named volume.
The image for this container looks like this:
FROM alpine
RUN mkdir $HOME/node_modules
COPY ./node_modules $HOME/node_modules
VOLUME $HOME/node_modules
When built, the image copies the current set of modules from the dev machine into a layer in the container. This container is then deployed on a worker node as a service, defined in the compose file as:
version: "3"
services:
nmod_core:
image: nmod_core:1.0.0
environment:
- HOME=/root
volumes:
- nmod_core:$HOME/node_modules
deploy:
replicas: 2
placement:
constraints: [node.role == worker]
restart_policy:
condition: on-failure
max_attempts: 1
On deployment, docker creates a named volume on each worker node according to this script. Creating a named volume means it creates a host directory at /var/lib/docker/volumes/nmod_core/_data and copies the container's node_modules contents into that directory.
The container exits since it has no ongoing process. So I set a restart limit of 1 so the service will not keep trying to restart it. The data persists in the host directory because it's a named volume--that's the objective--other containers on the same node should be able to mount it.
With credentials to my private registry set up, I deploy the stack via:
docker stack deploy -c docker-compose.yml myapp --with-registry-auth
I watch the service get created. When I log into the worker nodes docker image ls shows the correct image has been pulled from the registry. Presumably these containers have indeed run because docker volume ls shows the named volume has been created on each node, called myapp_nmod_core. I can inspect these volumes and they report the mount location as /var/lib/docker/volumes/myapp_nmod_core/_data. However, this location does not exist on the node.
Nevertheless, I can mount this named volume to a container via:
docker run -v myapp_nmod_core:/nmod -it alpine
#/ ls /nmod
#/
However, as shown above, the volume is empty.
But if I run the container manually on the node:
docker run -it f2f55823173d
#/ ls /root/node_modules
[a big list of node modules]
I get different results: docker volume ls shows a new volume created. Inspect shows a similar mount path, which also doesn't exist. However, when I mount that named volume in a secondary container as above, I get the volume mounted to the specified mount point and it now contains the big list of node modules I'm looking for.
So when deployed via docker swarm, I get the image and the volume, and I can mount it in another container, but the contents of the volume are missing. When I run the same image manually, the contents of the volume are all correct.
Any clues/insight greatly appreciated. Thanks!