Back to Blog
Lesson 17 of the Docker: Containers & Your First Image course
DevOpsAugust 4, 20264 min read

Introduction to Volumes: Mastering Docker Data Persistence

Learn how to use Docker volumes for reliable data persistence. This guide covers creating, attaching, and verifying storage so your data survives restarts.

dockervolumesstoragedevopspersistencecontainers
Shipping containers and cranes at Hamburg port showcasing global trade.

Previously in this course, we explored building your first image and managing container states. Up until now, everything we've run has been "stateless"—meaning if you deleted the container, all the files created inside it vanished. In the real world, your applications need to save configuration, logs, or database records that outlive the container itself. This lesson introduces volumes, the primary mechanism for persistent data management in Docker.

The Problem: Ephemeral File Systems

When you run a container, Docker creates a thin "writable layer" on top of the image. Any file you create or edit inside the container lives exclusively in that layer. If you stop, remove, and recreate the container, that layer is destroyed.

Think of a container like a whiteboard in a classroom: you can write data on it while the class is in session, but as soon as the session ends (the container stops) and the board is wiped (the container is removed), everything is gone. Volumes act like a secure, external notebook that you keep in your bag—independent of the whiteboard.

Creating and Using Named Volumes

A "named volume" is a storage area managed by Docker that exists outside of any specific container's lifecycle. It is stored in a part of the host file system that Docker controls (/var/lib/docker/volumes/ on Linux).

Step 1: Create a volume

You don't need to manually create a directory. Use the Docker CLI to provision the volume managed by the engine:

Bash
docker volume create my-app-data

You can verify it exists by running docker volume ls.

Step 2: Attach the volume to a container

To use this volume, you "mount" it when starting a container using the -v flag. The syntax is [volume_name]:[container_path].

Bash
docker run -d --name web-server -v my-app-data:/app/data nginx

Here, we've told Docker: "Take the my-app-data volume and map it to the /app/data directory inside the Nginx container." Any file written to /app/data inside the container is now physically saved in the volume on your host machine.

Step 3: Verify data persistence

Let's test this by creating a file inside that directory and then destroying the container.

  1. Create a file inside the container:
    Bash
    docker exec web-server sh -c "echo 'Hello World' > /app/data/test.txt"
  2. Stop and remove the container:
    Bash
    docker stop web-server && docker rm web-server
  3. Start a new container using the same volume:
    Bash
    docker run -d --name web-server-2 -v my-app-data:/app/data nginx
  4. Check if the file still exists:
    Bash
    docker exec web-server-2 cat /app/data/test.txt

You will see the output "Hello World." Even though the original container was deleted, your data persisted.

Hands-on Exercise

  1. Create a new volume named project-db.
  2. Run a postgres container, mounting project-db to /var/lib/postgresql/data.
  3. Stop the container.
  4. Run a new container with the same volume. Verify that the files (or the database state) are accessible.
  5. List your volumes to see where the data is being stored on your host.

Common Pitfalls

  • Permissions: When you mount a volume, the container process might not have the correct user permissions to write to it. If you get "Permission Denied," ensure the user inside your container has ownership of the mounted path.
  • Namespace Collisions: If multiple containers mount the same volume simultaneously, they will all see and modify the same files. This is great for sharing data, but dangerous if they conflict.
  • Ignoring Cleanup: Volumes do not get deleted when you remove a container. If you create many test volumes, your disk will fill up. Use docker volume prune to clean up unused volumes.

FAQ

Q: Where is my data physically stored? A: Docker manages the location, typically in /var/lib/docker/volumes/ on Linux. Avoid editing these files directly; always use the container to manipulate the data to prevent corruption.

Q: Is a volume better than a Bind Mount? A: Yes, for production data. Volumes are managed by Docker, safer for cross-platform use, and easier to back up. Bind mounts are better for local development where you want to edit source code on your host and see changes instantly in the container.

Q: Can I backup these volumes? A: Absolutely. Because they are just directories on your host, you can use standard tools to archive them, though more advanced strategies like Docker data persistence: Backing up volumes with Restic and Cron are highly recommended for production environments.

Recap

We've moved from ephemeral, disposable containers to persistent, stateful services. By leveraging named volumes, we ensure that critical application data survives container lifecycle events. This is the cornerstone of running any persistent service, like a database, in a containerized environment.

Up next: We will learn how to sync your local source code with a container using Bind Mounts, enabling faster feedback loops for development.

Similar Posts