Skip to main content

Docker Volume(s)

DISCLAIMER: The information in this guide is provided "as is" without any guarantee of completeness, accuracy, timeliness, or of the results obtained from the use of this information. The author assumes no responsibility for any errors or omissions in the content. It is meant for general information purposes only and should not be used as a substitute for professional advice. The author is not responsible for any damages caused by the use of this information. By using this guide, you agree to hold the author harmless from any and all claims, damages, or expenses that may arise from your use of the information.


Introduction

Generally, the Docker container data does not persist after the Docker container is restarted or removed. In this regard, Docker volumes and bind mounts are used to solve this issue. Docker volumes and bind mounts allow the persistance and sharing of data - even between containers.


Requirements

  • N/A

Docker Volumes

Anonymous Volumes

Running the  following docker-compose example will create an anonymous volume. The data will persist when the Docker container is restarted, but not after the Docker container is removed. It is important to note that the Docker container is also not accessible by other Docker containers. Anonymous volumes are useful when the data only needs to persist temporarily.

NOTE: These volumes are created inside /var/lib/docker/volume local host directory.

version: '3.8'
services:
  db:
    image: mysql
    restart: always
    environment:
      MYSQL_ROOT_PASSWORD: root
      MYSQL_DATABASE: test_db
    ports:
      - "3306:3306"
    volumes:
      - /var/lib/mysql

The docker-compose example above does not specify a host directory. Only the directory inside the Docker container is used.

If the volume is removed from the docker-compose example, the container will create an anonymous volume by default, because it is specified inside the MySQL Dockerfile. The MySQL image ensures that the data is still accessable even if the volume information is not specified:

VOLUME /var/lib/mysql

An anonymous volume with a random identifier is created:

docker volume ls
DRIVER    VOLUME NAME
local  4e679725b7179e63e8658bc157a1980f320948ab819f271fd5a44fe94c16bf23

Inspect the Docker conatiner for further information:

docker inspect mysql_db_1
.
.
."Mounts": [
            {
                "Type": "volume",
                "Name": "4e679725b7179e63e8658bc157a1980f320948ab819f271fd5a44fe94c16bf23",
                "Source": "/var/lib/docker/volumes/4e679725b7179e63e8658bc157a1980f320948ab819f271fd5a44fe94c16bf23/_data",
                "Destination": "/var/lib/mysql",
                "Driver": "local",
                "Mode": "",
                "RW": true,
                "Propagation": ""
            }
        ],
.
.
.

Use the following command to remove the Docker container and its associated anonymous volume:

docker rm -v mysql_db_1

If the anonymous volume is not removed with the Docker container, it becomes a dangling volume:

docker rm mysql_db_1

List and remove all the dangling volumes using the following commands:

docker volume ls -qf dangling=true
docker volume rm $(docker volume ls -qf dangling=true)

Named Volumes

Named volumes can persist data after a Docker container restart or removal. Also, it’s accessible by other Docker containers.

NOTE: These volumes are created inside /var/lib/docker/volume local host directory.

version: '3.8'
services:
  db:
    image: mysql
    restart: always
    environment:
      MYSQL_ROOT_PASSWORD: root
      MYSQL_DATABASE: test_db
    ports:
      - "3306:3306"
    volumes:
      - db_data:/var/lib/mysqlvolumes:
  db_data:

A named volume contains two parts, each part seperated by a colan ( : ). The first part is a unique name of the volume on a host machine. The second part is the path in the container. Also, keep in mind that the first part (e.g., db_data on line 12) is declared outside the volume configuration (e.g., db_data on line 13). This declaration ensures that docker can prepare the host path prior to binding.

As an additonal note to outline differences between anonymous volumes versus named volumes, removing the container using the following command will only remove the container and not the volume:

docker rm -v mysql_db_1

Host Volumes (Bind Mounts)

Host volumes aka bind mounts, can persist data after a Docker container restart or removal. Named volumes and host volumes are the same, except named volumes can be found under a specific host directory, and host volumes can be any specified host directory.

version: '3.8'
services:
  db:
    image: mysql
    restart: always
    environment:
      MYSQL_ROOT_PASSWORD: root
      MYSQL_DATABASE: test_db
    ports:
      - "3306:3306"
    volumes:
      - $PWD/data:/var/lib/mysql

In the above docker compose example, a host folder is mounted. The first part is the path in the host machine. The second part is the path in the container.


Sources

 

KB Change/Issue Log

yyyy/mm/dd - Title

Issue

N/A

Solution

N/A


KB Meta

Page Includes @9#bkmrk-callout-danger-NoResponsibilityDisclaimer-5wod5ufe