I’ve seen variations of this question but for some reason I think I’m missing something.
Problem
I’m running a couple of containers on docker swarm. Every time my DB container, or backend container restarts, the database gets cleared. I thought that volumes were supposed to prevent this from happening.
This is how I created my swarm and the containers.
docker swarm init
docker network create --driver overlay network
docker volume create -d local --name mysql_data
docker service create --name db
--replicas 1
--env MARIADB_ALLOW_EMPTY_ROOT_PASSWORD="yes"
--env-file ../server/.env
--network network
--mount source=mysql_data,destination=/var/lib/mysql/data/
mariadb:10.7.3
docker service create --name django
--replicas 1
--env CONTAINER="True"
--env-file ../server/.env
--network network
--with-registry-auth
client_backend:deploy
docker service create
--name frontend
--replicas 1
--network network
-p 8080:80
--with-registry-auth
client_frontend:latest
Am I mounting my volume wrong or is there something else I’m missing?
Thanks,
2
Answers
Turns out the issue was that I was mapping to the wrong directory.
I had
--mount source=mysql_data,destination=/var/lib/mysql/data/
but it's supposed to be
--mount source=mysql_data,destination=/var/lib/mysql
The docker "local" volume driver is just that. It creates volumes on each nodes local file system.
To get persistent storage that is swarm aware you have several options:
If you are using something like a PureStorage SAN you can use their Trident docker volume plugin which is swarm aware. Rancher 1 could also build swarms with persistent volume support.
Otherwise you can roll your own persistent network storage using nfs or glusterfs servers. With nfs there is a syntax to create the volume using the local driver but with nfs options and credentials, and docker will mount the nfs volume on each node the service is deployed onto.
With glusterfs there are some community docker volume plugins of varying quality levels, or you can just mount a big /mnt/gfs/docker mount on each host and just use bind mounts from each container/service that needs persistent storage.