Skip to content

Instantly share code, notes, and snippets.

@pawelkomarnicki
Last active December 6, 2018 09:32
Show Gist options
  • Save pawelkomarnicki/024dfe86b59cac4d0d48e4796cd2adb7 to your computer and use it in GitHub Desktop.
Save pawelkomarnicki/024dfe86b59cac4d0d48e4796cd2adb7 to your computer and use it in GitHub Desktop.
docker-compose guidelines

docker-compose conventions

Service naming convention

# Due to lack of "expressivity" in Compose, we define our own couple of service "pseudo-types":
#
#   - image-only services (name: *-image)
#     The only goal of these is to build images. No other services build images.
#     These have entrypoint overridden to exit immediately.
#
#   - base services (name: *-base)
#     These contain common configuration and are intended to be extended.
#     Their command (not entrypoint, to keep the original one) is overridden to
#     exit immediately. Service must support a command to exit immediately.
#
#   - task services (name: *-task)
#     These are intended for running one-off commands.
#     Their default command is overridden to exit immediately. Service must
#     support a command to exit immediately.
#
#   - "real" services
#     These are actual services that stay up and running.

docker-compose

Docker compose should follow the service naming convention, but also should have our internal naming, like web, worker, rspec:

version: '3'

networks:
  blinkist:
    external:
      name: cubitoo

services:

  services-base: &services-base
    tty: true
    stdin_open: true
    command: echo services-base is not a real service
    build:
      dockerfile: Dockerfile-dev
      context: .
    environment:
      - APP_NAME=service_name
      - RAILS_ENV=development
    volumes:
      - .:/app
    networks:
      - blinkist

  console-task:
    << : *services-base
    command: bundle exec rails console

  rspec-task:
    << : *services-base
    entrypoint: bundle exec rspec
    command: .

  web:
    << : *services-base
    command: bundle exec bin/rails s -p 80 -b 0.0.0.0
    container_name: service-name.dev
    hostname: serfice-name.dev
    expose:
      - 80
    labels:
      - 'traefik.frontend.rule=Host:service-name.dev'

Secret bash sauce

In order to make it easier to use the docker-compose, I've created a small snippet alias and bash function you can copy into your ~/.bash_profile:

# docker-compose utils
alias dcb='docker-compose build'
alias dcu='docker-compose up'
alias dcd='docker-compose down'

function dcr() {
  docker-compose run --rm $1-task ${@:2:99}
}

While aliases are self-explanatory (and allow stuff like dcu web worker), dcr takes the name of the service (like rspec), and because it follows the appropriate naming convention, runs docker-compose rspec-task arg1 arg2 ...)

Dockerfile

Dockerfile for development purposes should be a separate file from the production one. Moreover, it should be as simple as possible. Sample Dockerfile-dev from Messenger:

FROM ruby:2.5.1-alpine

ARG BUNDLE_GITHUB__COM

ENV BUILD_PACKAGES build-base git
ENV RUNTIME_PACKAGES supervisor mysql-dev

RUN apk update && apk upgrade && \
    apk add $BUILD_PACKAGES && \
    apk add $RUNTIME_PACKAGES

RUN mkdir /app
WORKDIR /app

COPY .ruby-version /app/
COPY Gemfile* /app/
RUN bundle install

COPY . /app
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment