Adding a volume to an existing Docker container is a simple process that can add extra storage space and improve performance. To add a volume to an existing Docker container, first create a new file in the container’s root directory called “volumes” and paste the following content into it:
mkdir volumes # cd volumes # touch volumes/1
Next, create a new file in the container’s root directory called “docker-compose.yml” and paste the following content into it:
vi docker-compose.yml # docker-compose up -d
While Docker is a useful tool for packaging and managing applications, it also presents many unique challenges, such as dealing with stored data. Usually, you add volumes to containers in the creation script, but what if you need to make new ones?
Adding a Volume To a Running Docker Container
Unfortunately it’s not as simple as just adding a new volume. Containers must have their volumes configured on startup, which means to add a new volume, you must restart the container. While there is a hacky solution (more on that below), it’s highly recommended that a container restart should be done anyway.
This is for a few reasons. Restarting the container is fairly easy, and most code updates require a restart of the service anyway. Having updates tracked in Git is another big factor, especially if you’re using Docker Compose, and editing the launch script is far better than manually adding the volume to a running container.
If your service is big enough that you are concerned about a few minutes (at most) of potential scheduled downtime to restart the container, you should probably be running a scaling deployment with multiple instances that can be updated independently. Modern auto-scaling systems should be designed to handle that, as code deployments happen often.
If you want to add a volume, you’ll need to stop the running container:
Create a new volume if you need to:
And then run it with an updated launch command, adding the –mount flag to configure the source volume and target destination.
If you’re using Docker Compose, you can automate and track this process more easily, since the volume configuration is handled through a settings file. you’ll need to add the volume to the docker-compose.yml file:
Then, you can restart Docker Compose’s services. Compose has a “restart” command, but it’s actually to just refresh the running service without any config changes. If you want to update the images, you’ll need to run docker-compose up with the –build flag:
You can also manually run docker-compose down beforehand to stop the services, but it isn’t necessary in most cases unless you want to run it with the -v flag to destroy existing volumes.
RELATED: What Is Docker Compose, and How Do You Use It?
Cloning From An Existing Container
In almost all cases, you shouldn’t be depending on a container’s current running state. Anything that you care about, such as application data, should be stored in a volume so that it can be persisted across container restarts and rebuilds.
This method probably isn’t a good idea for most people, as it requires you to make a new image every time you want to do this, and it still requires downtime. But, if you do need to add a volume to a running container, you can use docker commit to make a new image based on that container, and then clone it with the new volume.
Grab the container ID from docker ps:
And then, clone it with commit:
Then, you can run the new image, replacing the old image with the cloned one.
The Hacky Solution
Docker volumes are really just trickery that the Docker runtime uses to expose host directories to containers, and it all depends on configuration. Because of this, you can actually modify that configuration directly, and restart the entire Docker daemon for your system to apply those changes without restarting at all.
Of course, this is far more complicated than just dealing with a container restart, so if you can manage a minute of downtime, we highly recommend doing that instead.
You’ll need to navigate to Docker’s storage directory:
In here will be many folders cooresponding to Docker container IDs, which you can find with docker ps. Open up the one for the container you want to modify.
The config file is config.v2.json, but it’s in a compact format and hard to edit. You can install jq to pretty-print JSON on the command line, and pipe this to a new file for editing:
You’ll need to scroll down to find “MountPoints,” which contains the configuration for all the volumes and bind mounts. You can add a new one here, which should be in the following format:
Then, once it’s done, you can minify the JSON again back into the config file:
jq is a powerful utility, so if you wanted to automate this process entirely, you could do that.
RELATED: How to Work With JSON On the Command Line
Then, simply restart the Docker service to apply the changes: