Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I mount a host directory as a volume in docker compose

People also ask

Can Docker compose create volumes?

We can also create a volume with Docker compose service or also specify existing volumes. For example, the following screenshot shows a 'docker-compose' file that creates a docker-compose service with a volume. As a result of the above command, a volume with the name 'myvolume' gets created.


Checkout their documentation

From the looks of it you could do the following on your docker-compose.yml

volumes:
    - ./:/app

Where ./ is the host directory, and /app is the target directory for the containers.


EDIT:
Previous documentation source now leads to version history, you'll have to select the version of compose you're using and look for the reference.

For the lazy – v3 / v2 / v1

Side note: Syntax remains the same for all versions as of this edit


There are a few options

Short Syntax

Using the host : guest format you can do any of the following:

volumes:
  # Just specify a path and let the Engine create a volume
  - /var/lib/mysql

  # Specify an absolute path mapping
  - /opt/data:/var/lib/mysql

  # Path on the host, relative to the Compose file
  - ./cache:/tmp/cache

  # User-relative path
  - ~/configs:/etc/configs/:ro

  # Named volume
  - datavolume:/var/lib/mysql

Long Syntax

As of docker-compose v3.2 you can use long syntax which allows the configuration of additional fields that can be expressed in the short form such as mount type (volume, bind or tmpfs) and read_only.

version: "3.2"
services:
  web:
    image: nginx:alpine
    ports:
      - "80:80"
    volumes:
      - type: volume
        source: mydata
        target: /data
        volume:
          nocopy: true
      - type: bind
        source: ./static
        target: /opt/app/static

networks:
  webnet:

volumes:
  mydata:

Check out https://docs.docker.com/compose/compose-file/#long-syntax-3 for more info.


If you would like to mount a particular host directory (/disk1/prometheus-data in the following example) as a volume in the volumes section of the Docker Compose YAML file, you can do it as below, e.g.:

version: '3'

services:
  prometheus:
    image: prom/prometheus
    volumes:
      - prometheus-data:/prometheus

volumes:
  prometheus-data:
    driver: local
    driver_opts:
      o: bind
      type: none
      device: /disk1/prometheus-data

By the way, in prometheus's Dockerfile, You may find the VOLUME instruction as below, which marks it as holding externally mounted volumes from native host, etc. (Note however: this instruction is not a must though to mount a volume into a container.):

Dockerfile

...
VOLUME ["/prometheus"]
...

Refs:

  • https://docs.docker.com/compose/compose-file/#driver
  • https://docs.docker.com/compose/compose-file/#driver_opts

It was two things:

I added the volume in docker-compose.yml:

node:
  volumes:
    - ./node:/app

I moved the npm install && nodemon app.js pieces into a CMD because RUN adds things to the Union File System, and my volume isn't part of UFS.

# Set the base image to Ubuntu
FROM    node:boron

# File Author / Maintainer
MAINTAINER Amin Shah Gilani <[email protected]>

# Install nodemon
RUN npm install -g nodemon

# Add a /app volume
VOLUME ["/app"]

# Define working directory
WORKDIR /app

# Expose port
EXPOSE  8080

# Run npm install
CMD npm install && nodemon app.js

we have to create your own docker volume mapped with the host directory before we mention in the docker-compose.yml as external

1.Create volume named share

docker volume create --driver local \
--opt type=none \
--opt device=/home/mukundhan/share \
--opt o=bind share

2.Use it in your docker-compose

version: "3"

volumes:
  share:
    external: true

services:
  workstation:
    container_name: "workstation"
    image: "ubuntu"
    stdin_open: true
    tty: true
    volumes:
      - share:/share:consistent
      - ./source:/source:consistent
    working_dir: /source
    ipc: host
    privileged: true
    shm_size: '2gb'
  db:
    container_name: "db"
    image: "ubuntu"
    stdin_open: true
    tty: true
    volumes:
      - share:/share:consistent
    working_dir: /source
    ipc: host

This way we can share the same directory with many services running in different containers


In docker-compose.yml you can use this format:

volumes:
    - host directory:container directory

according to their documentation