ryanwhocodes Feb 13, 2018 · 4 min read

The Ups and Downs of Docker Compose

How to run multi-container applications with Docker Compose.

Defining your applications in a docker-compose.yml and running them with the up and down commands gives you control over multi-container applications.

Compose is a tool for defining and running multi-container Docker applications. With Compose, you use a Compose file to configure your application’s services. Then, using a single command, you create and start all the services from your configuration.
Docker Compose on Github

Contents

Similarities to Docker Commands

Docker Compose CLI commands are similar to those for Docker, except with a few additions related to instructions for multiple containers and images. In particular, the following commands are familiar if you have used them with docker:

  • ps
  • build
  • pull
  • push
  • run
  • logs

Find out more in the Docker Compose docs.

Docker Compose Up and Down

up

Use docker-compose up to create and start a container. In “detached” mode (-d), Compose exits after starting the containers, but the containers continue to run in the background.

docker-compose up -d rabbit-mq

up - Docker Compose docs

down

Use docker-compose down to stop and remove containers, networks, images, and volumes.

docker-compose down -v

This has some useful options…

  • --rmi [type] - remove images.
  • -v, --volumes - remove named volumes declared in the volumes section of the Compose file and anonymous volumes attached to containers.
  • --remove-orphans - remove containers for services not defined in the Compose file.

down - Docker Compose docs

Create a Dockerfile

Just like with running docker, you need a Dockerfile to specify how to create the image and containers for your program. An example Dockerfile for a Ruby on Rails application could be:

FROM ruby:2.3.3
RUN apt-get update -qq && apt-get install -y build-essential libpq-dev nodejs
RUN mkdir /myapp
WORKDIR /myapp
COPY Gemfile /myapp/Gemfile
COPY Gemfile.lock /myapp/Gemfile.lock
RUN bundle install
COPY . /myapp

The docker-compose: getting started guide gives you step-by-step instructions on creating a Dockerfile and integrating it into your Docker Compose file.

A tour of docker-compose.yml - its structure and components

To define your multi-container application, you use a docker-compose.yml file in the root of your project. The compose file docs provides detailed explanations and a guide to generating this. Here is a quick-start guide to some of the key features:

At the top you include the version, such as version: "3"

Then services:

After this you list the containers you want to create, such as with each one having configuration options.

image

This could be an image stored in docker hub, or one stored locally.

image: ruby:alpine

image - Docker Compose docs

depends_on

Other containers that this container requires, creating the parent container will also create and start the dependent containers.

version: '3'
services:
  web:
    build: .
    depends_on:
      - db
      - redis
  redis:
    image: redis
  db:
    image: postgres

depends_on - Docker Compose docs

environment

Add environment variables.

environment:
  RACK_ENV: development
  SHOW: 'true'
  SESSION_SECRET:
environment:
  - RACK_ENV=development
  - SHOW=true
  - SESSION_SECRET

environment - Docker Compose docs

volumes

Include host paths or named volumes. You can replace data in a container using the format : and can follow this with the permissions, such as :ro for read-only.

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

db:
    image: postgres:latest
    volumes:
      - "/var/run/postgres/postgres.sock:/var/run/postgres/postgres.sock"
      - "dbdata:/var/lib/postgresql/data"

volumes - Docker compose docs

ports

Either specify both ports (HOST:CONTAINER), or just the container port (an ephemeral host port is chosen).

ports:
 - "3000"
 - "3000-3005"
 - "8000:8000"
 - "9090-9091:8080-8081"
 - "49100:22"
 - "127.0.0.1:8001:8001"
 - "127.0.0.1:5000-5010:5000-5010"
 - "6060:6060/udp"

ports - Docker Compose docs

Find out more

Docker Compose is a powerful tool for running multi-container applications. There are many ways to configure your apps with docker-compose.yml as well as other Docker Compose CLI commands to learn. Check out the Docker docs and my other posts for more.

Header image source: The Docker Compose logo used with permission from Docker - https://www.docker.com/brand-guidelines