Docker Compose. Обзор для начинающих.

Все это время мы работали с отдельными сервисами, docker compose поможет же нам собрать их все воедино. Если вы только начинающий и начали разбираться в этом докере – то, возможно, задавались вопросом как запустить приложение состоящее из множества сервисов, например из php, mysql, nginx, redis,… Давайте рассмотрим немного подробнее.

В предыдущих статьях мы без проблем научились создавать контейнеры в отдельности и, скажу, у нас это прекрасно получалось. Но живое приложение состоит не из одного контейнера mysql, а из множества разных сервисов: базы данных, nginx, mysql и т.д. Давайте, для примера, запустим несколько контейнеров: php и nginx.

docker run -d --name=app-php php
docker run -d --name=app-nginx nginx

Главной проблемой на пути к успеху будет взаимодействие между контейнерами: они совсем ничего не знают друг о друге. Как на первом свидании. И их нужно познакомить гораздо ближе: они должны узнать о существовании друг друга и вести работу сообща, тогда наше приложение станет более полноценным. В решении этой проблемы нам поможет docker compose. Давайте разберем этот момент более детально.

Docker Compose и YML

Docker Compose состоит из файла docker-compose.yml. В нем прописаны все инструкции которые прольют свет на взаимодействие наших контейнеров. Он позволяет запустить несколько докер контейнеров.

Формат YAML – это язык разметки. В этом формате мы будем писать наши инструкции. Я не буду детально останавливаться на этом, так как ничего сложного здесь нет и, думаю, вы подхватите понимание синтаксиса в процессе знакомства. Если будет спрос на более детальный обзор – тогда обсудим в комментариях.

Файл docker-compose.yml

Теперь попробуем создать типичный docker-compose.yml файл. Итого, начнем, пожалуй, с сервиса nginx. Для этого используем образ image: nginx и прокинем, скорее для интереса чем надобности, порты 5000:80. Если вы не понимаете о чем идет речь – в предыдущих статьях можно найти больше информации. Например, здесь: Docker. Играем с контейнерами внутри и снаружи.

В итоге, у нас должен быть создан файл с названием docker-compose.yml. Содержание будет следующего вида:

nginx-app:
  container_name: nginx-app
  image: nginx
  ports:
     - 5000:80

Очень важно здесь учитывать пробелы, отступы, заступы и подступы. В противном случае вы неизбежно столкнетесь с ошибкой при запуске. Сейчас построчно глянем что мы написали и попробуем запустить вот это вот все.

Первая строка nginx-app: это есть наш сервис, который мы добавляем. Вы можете назвать его как угодно. Я серьезно. Даже как-то нецензурно-бранными словами. Далее дадим нашему контейнеру имя. Без этой строки все и так будет прекрасно работать, но так мы сможем быстро найти и распознать его, к примеру, в списке запущенных контейнеров.

В целом, из содержания файла все интуитивно ясно: image – используем изображение, в данном случае мы используем nginx. Вы можете попробовать аналогично создать контейнер из другого образа. Ну и последнее – ports – прикидываем наши порты.

Запуск docker-compose.yml

Теперь запустим наш сервис с помощью docker compose. Это совсем не сложно. Достаточно перейти в директорию, где находится этот файл и выполнить следующую команду:

docker-compose up

Или же запустите docker compose в фоновом режиме

docker-compose up -d

Думаю Вы сможете выбрать команду по душе. В итоге вы должны увидеть результат вашей работы. Если все сделали верно. Только в этом случае. Не забудьте потом остановить/удалить контейнер, если вы запустили его в фоновом режиме.

Этот контейнер мы могли запустить старыми проверенными способами. Пришло время познать силу docker compose. А конкретней – создадим еще несколько сервисов, которые будут связаны между собой.

Предположим, что на понадобится php, nginx и mysql для работы нашего приложения. Файл docker-compose.yml будет выглядеть примерно следующим образом:

db-app:
  image: mysql:5.7
  restart: always
  environment:
       MYSQL_ROOT_PASSWORD: pwd
       MYSQL_DATABASE: dbname
       MYSQL_USER: user
       MYSQL_PASSWORD: pwd
  volumes:
    - ./:/var/lib/mysql
php-app:
  image: php:7-apache
  working_dir: /var/www
  links: 
    - nginx-app
nginx-app:
  container_name: nginx-app
  image: nginx
  ports:
     - 5000:80

Для запуска вы можете использовать проверенную выше команду docker-compose up.

Проведя аналогию с первым примером можно понять каким образом создается этот файл. Многие параметры должны быть вам знакомы из предыдущих статей. Кратко глянем что мы здесь написали.

Мы создали контейнер для базы данных mysql, установили ей значения для подключения к базе. В контейнере php у нас появился параметр links (устаревший), который как раз и связывает его с контейнером nginx. Но эта информация вам особо не нужна, так как это нужно делать только в первой версии docker compose. В остальных это происходит автоматически. А что, есть версии?

Версии docker compose

В примере выше у нас использовалась первая версия docker compose. Но как это понять? На самом деле в файле мы нигде не прописывали версию. Значит автоматически она определена как первая. Она является устаревшей и не используется.

Теперь перейдем к вопросу какие версии бывают и как указать докер компостеру версию?

Давайте попробуем использовать версию 2. Что у нас теперь изменится? Для того, что бы объявить версию – вверху файла необходимо указать:

version: '2'

Теперь docker compose знает что мы работаем со второй версией. При этом все сервисы перенесутся под services:. Параметр links нам больше не нужен, так как со второй версии все контейнеры будут видеть друг-друга.

Должно получится что-то похожее на следующий файл:

version: '2'
services:
  db-app:
    image: mysql:5.7
    restart: always
    environment:
         MYSQL_ROOT_PASSWORD: pwd
         MYSQL_DATABASE: dbname
         MYSQL_USER: user
         MYSQL_PASSWORD: pwd
    volumes:
      - ./:/var/lib/mysql
  php-app:
    image: php:7-apache
    working_dir: /var/www
    depends_on:
      - db-app
  nginx-app:
    container_name: nginx-app
    image: nginx
    ports:
       - 5000:80

Вы можете заметить что здесь я добавил в контейнер для php строку depends_on – это значит что этот контейнер у нас зависит от базы данных и он запустится только после того как будет запущена база. На второй версии все не заканчивается. Есть еще 3 версия, там есть свои отличия которые мы с вами рассмотрим в следующих статьях. В официальной документации можно ознакомится с более детальным различием в версиях.

Leave a Reply