Docker containers are isolated environments. However, containers sometimes need to persist and share data. It may happen when a second container needs to access a shared cache or use database data. We may also need to backup or perform operations on user-generated data.
In this short tutorial, we'll see how to share data between Docker containers with an example using Docker Compose.
2. Persist and Share Data with Docker Storage
When containers run, all files get a writable space. However, they no longer exist once we stop the container.
Storing files also improves performance because it writes directly to the host filesystem instead of using the container’s writable layer.
2.1. Docker Volumes
Let's have a quick look at Docker Volumes. For example, let's run an Nginx container with a named volume.
First, let's create our volume:
docker volume create --name volume-data
Then, let's run our container:
docker run -d -v volume-data:/data --name nginx-test nginx:latest
In this case, Docker will mount in the container’s /data folder. It will also copy the directory’s contents into the volume if the container has files or directories in the path to be mounted.
We can also have a look at bind mounts for persistent storage.
2.2. Share Data with Volumes
Multiple containers can run with the same volume when they need access to shared data.
For example, let's start our web application:
docker run -d -v volume-data:/usr/src/app/public --name our-web-app web-app:latest
Docker creates a local volume by default. However, we can use a volume diver to share data across multiple machines.
Finally, Docker also has –volumes-from to link volumes between running containers. It may help for data sharing or more general backup usage.
3. Share Data with Docker Compose
Let's create a docker-compose.yml to run both an Nginx container and our web application sharing the same volume:
services: nginx: container_name: nginx build: ./nginx/ volumes: - shared-volume:/usr/src/app web-app: container_name: web-app env_file: .env volumes: - shared-volume:/usr/src/app/public environment: - NODE_ENV=production volumes: shared-volume:
Again, in Docker Compose, the default driver will be local. We can also specify a driver to use for this volume:
volumes: db: driver: some-driver
We may also need to use a volume external to Docker Compose:
volumes: data: external: true name: shared-data
In this article, we've seen how to share Docker containers' data using volumes. We have also seen the same concept with a simple example using Docker Compose.