Изучаем Docker, часть 2: термины и концепции

https://towardsdatascience.com/learn-enough-docker-to-be-useful-1c40ea269fa8
  • Перевод
В первой части перевода серии материалов, посвящённых Docker, мы сделали общий обзор этой системы. В частности, мы говорили о том, почему технологии контейнеризации важны в наше время, о том, что такое контейнеры Docker, и о том, с чем их можно сравнить. Сегодня мы поговорим об экосистеме Docker и рассмотрим важные термины, с которыми вы можете столкнуться на пути изучения и использования Docker. Продолжив аналогию с разными вкусностями, представим, что наши термины — это пончики. Дюжина пончиков.

Часть 1: основы
Часть 2: термины и концепции
Часть 3: файлы Dockerfile
Часть 4: уменьшение размеров образов и ускорение их сборки
Часть 5: команды
Часть 6: работа с данными




Термины экосистемы Docker


Я разбил термины, с которыми вы можете столкнуться в ходе работы с Docker, на две части. Думаю, это облегчит их запоминание. Первый блок терминов будет относиться к механизмам Docker. Второй — к средствам масштабирования решений, основанных на контейнерах.

Механизмы Docker


▍Платформа Docker



Docker

Платформа Docker (Docker Platform) — это программа, которая даёт нам возможность упаковывать приложения в контейнеры и запускать их на серверах. Платформа Docker позволяет помещать в контейнеры код и его зависимости. Как результат, системы, основанные на контейнерах, легко масштабировать, так как контейнеры можно переносить и воспроизводить.

▍Движок Docker



Движок

Движок Docker (Docker Engine) — это клиент-серверное приложение. Компания Docker разделила движок Docker на два продукта. Docker Community Edition (CE) — это бесплатное ПО, во многом основанное на опенсорсных инструментах.

Вероятно, вы будете пользоваться именно этой версией Docker. Docker Enterprise — это платная версия системы, дающая пользователям дополнительные возможности в области поддержки систем, управления ими и безопасности. Платная версия Docker даёт компании средства, необходимые для её существования.

▍Клиент Docker



Клиент Docker и другие механизмы экосистемы (взято из документации)

Клиент Docker (Docker Client) — это основное средство, которое используют для взаимодействия с Docker. Так, при работе с интерфейсом командной строки Docker (Docker Command Line Interface, CLI), в терминал вводят команды, начинающиеся с ключевого слова docker, обращаясь к клиенту. Затем клиент использует API Docker для отправки команд демону Docker.

▍Демон Docker


Демон Docker (Docker Daemon) — это сервер Docker, который ожидает запросов к API Docker. Демон Docker управляет образами, контейнерами, сетями и томами.

▍Тома Docker



Тома

Тома Docker (Docker Volumes) представляют собой наиболее предпочтительный механизм постоянного хранения данных, потребляемых или производимых приложениями.

▍Реестр Docker


Реестр Docker (Docker Registry) представляет собой удалённую платформу, используемую для хранения образов Docker. В ходе работы с Docker образы отправляют в реестр и загружают из него. Подобный реестр может быть организован тем, кто пользуется Docker. Кроме того, поставщики облачных услуг могут поддерживать и собственные реестры. Например, это касается AWS и Google Cloud.

▍Хаб Docker


Хаб Docker (Docker Hub) — это самый крупный реестр образов Docker. Кроме того, именно этот реестр используется при работе с Docker по умолчанию. Пользоваться хабом Docker можно бесплатно.

▍Репозиторий Docker


Репозиторием Docker (Docker Repository) называют набор образов Docker, обладающих одинаковыми именами и разными тегами. Теги — это идентификаторы образов.

Обычно в репозиториях хранятся разные версии одних и тех же образов. Например, Python — это имя популярнейшего официального репозитория Docker на хабе Docker. А вот Python:3.7-slim — это версия образа с тегом 3.7-slim в репозитории Python. В реестр можно отправить как целый репозиторий, так и отдельный образ.

Теперь поговорим о терминах экосистемы Docker, имеющих отношение к масштабированию.

Масштабирование решений, основанных на контейнерах


Следующие четыре термина имеют отношение к одновременному использованию нескольких контейнеров.

▍Сеть Docker



Сеть Docker (взято из документации)

Сетевые механизмы Docker (Docker Networking) позволяют организовывать связь между контейнерами Docker. Соединённые с помощью сети контейнеры могут выполняться на одном и том же хосте или на разных хостах. Подробности о сетевой подсистеме Docker можно почитать здесь.

▍Docker Compose


Docker Compose — это инструмент, который упрощает развёртывание приложений, для работы которых требуется несколько контейнеров Docker. Docker Compose позволяет выполнять команды, описываемые в файле docker-compose.yml. Эти команды можно выполнять столько раз, сколько потребуется. Интерфейс командной строки Docker Compose упрощает взаимодействие с многоконтейнерными приложениями. Этот инструмент устанавливается при установке Docker.

▍Docker Swarm



Рой пчёл

Docker Swarm — это решение, предназначенное для управления контейнерными развёртываниями (то есть, как говорят, для оркестрации контейнеров). В этом материале из официального учебного курса по Docker можно найти сведения о Docker Swarm. Мне хотелось бы порекомендовать вам не тратить время на изучение Docker Swarm в том случае, если у вас нет на то веской причины.

▍Сервисы Docker


Сервисы Docker (Docker Services) — это различные части распределённого приложения. Вот что о них говорится в документации:

Сервисы — это всего лишь «контейнеры в продакшне». В пределах сервиса выполняется лишь один образ, но сервис определяет то, как именно выполняется образ. В частности, речь идёт о том, какие порты должны использоваться, сколько реплик контейнера должно выполняться для того, чтобы сервис обеспечивал бы необходимую вычислительную мощность, и так далее. Масштабирование сервисов предусматривает изменение количества экземпляров контейнера, в которых работает некая программа, благодаря чему сервису выделяется столько системных ресурсов, сколько ему требуется для решения некоей задачи.

Сервисы Docker позволяют масштабировать контейнеры в пределах нескольких демонов Docker, благодаря им существует и технология Docker Swarm.

Краткий перечень терминов


Давайте, буквально в двух словах, повторим только что представленные вам термины:

Механизмы Docker:

  1. Платформа Docker — ПО, благодаря которому можно работать с контейнерами.
  2. Движок Docker — клиент-серверное приложение (CE или Enterprise).
  3. Клиент Docker — программа, которая позволяет взаимодействовать с демоном Docker посредством CLI.
  4. Демон Docker — сервер Docker, отвечающий за управление ключевыми механизмами системы.
  5. Тома Docker — хранилище информации, используемое в контейнерах.
  6. Реестр Docker — удалённое хранилище образов.
  7. Хаб Docker — самый крупный реестр Docker, используемый по умолчанию.
  8. Репозиторий — коллекция образов Docker с одним и тем же именем.

Масштабирование:

  1. Сетевая подсистема Docker — среда, которая позволяет организовывать взаимодействие контейнеров.
  2. Docker Compose — технология, упрощающая работу с многоконтейнерными приложениями.
  3. Docker Swarm — средство для управления развёртыванием контейнеров.
  4. Сервисы Docker — контейнеры в продакшне.

Выше мы говорили о том, что рассмотрим дюжину терминов экосистемы Docker, сравнивая их с дюжиной пончиков. Мы рассмотрели уже 12 терминов, и, казалось бы, на этом можно и остановиться. Но мы, на всякий случай, добавим в наш список ещё один термин.


Вот, на всякий случай, ещё один пончик

Этот термин относится не к самой платформе Docker, а к технологии, которая очень часто используется совместно с Docker.

Kubernetes



Kubernetes

Kubernetes — это технология, которая позволяет автоматизировать развёртывание и масштабирование контейнеризированных приложений, а также управление ими. Это — бесспорный лидер рынка средств для оркестрации контейнеров. Если вам нужен инструмент для работы с группами контейнеров, для масштабирования решений, основанных на них, используйте не Docker Swarm, а Kubernetes. Kubernetes не является частью Docker. Они с Docker, скорее, похожи на лучших друзей.

Теперь, когда вы ознакомились с общими понятиями Docker и с терминологией, вы можете приступить к практическим экспериментам.

Итоги: печём пончики с Docker


Помните, как в прошлый раз мы сравнивали платформу Docker с духовкой, которую устанавливают в кухне? Сейчас самое время установить Docker на вашей «кухне» и что-нибудь приготовить.

Docker можно запускать локально на Linux, Mac и Windows. Если вы пользуетесь Mac или Windows, вы можете установить свежую версию Docker Desktop отсюда. Вместе с этой программой, кстати, устанавливается и Kubernetes. Если вы устанавливаете Docker на другой платформе, то загляните сюда для того, чтобы найти подходящую версию.

После установки Docker взгляните на первые две части официального руководства.

В следующий раз мы продолжим разговор о Docker. В частности, поговорим о файлах Dockerfile.

Уважаемые читатели! Если, читая материалы этой серии, вы открываете для себя Docker, просим рассказать о том, как вы планируете использовать технологии контейнеризации приложений.

RUVDS.com
952,00
RUVDS – хостинг VDS/VPS серверов
Поделиться публикацией

Комментарии 33

    0
    Объясните мне кто-нибудь, а для чего мне все это нужно? Усть у меня сервер, на нем нормально крутится nginx + php + mysql и всякое такое.
    Что мне дает запихивание этих сервисов в контейнеры? (стабильность, производительность etc...)
    Где (dev / prod) это делать уместно, а где нет?
    Как все это администрировать? Если обычно у меня есть "$service --status-all" [start|stop|resrtart|reload], что делать при перемещении сервисов в контейнеры?
    В общем пока для меня докер создал больше вопросов, чем ответов.
    Единственный действительно ощутимый плюс — кросплатформенность. В докере (на Deb 8) у меня отлично заработало приложение предназначенное исключительно для CentOS.
      0
      Вот здесь есть удобная площадка для тренировки labs.play-with-docker.com
        +5
        • воспроизводимость окружения, чтобы не случилось так, что разработчик говорит, что у него всё работает, а при разворачивании на сервере всё ломается из-за того, что разработчик забыл описать в требованиях какую-то зависимость.
        • изолированость окружения, чтобы не случилось так, что для работы одному проекту нужна версия 1 какого-то инструмента, а другому проекту — версия 2, а одновременно на одну машину эти версии не становятся.
        • поддержка чистоты на хост-машине, чтобы не случилось так, что для проекта нужно установить с десяток зависимостей, которые потом нужно долго и нудно выковыривать из системы, контейнер удаляется в одну команду, не зависимо от того, насколько глубоко пакеты в нём интегрированы в систему
        • замена пакетному менеджеру(?), чтобы не случилось так, что для вашего дистрибутива или для вашего пакетного менеджера нет готовых бинарников нужного пакета, можно просто поднять его в докере и не морочить себе голову с курением мануалов (на самом деле этот пункт — лишь забавный побочный эффект от других преимуществ докера)
        • простота разворачивания, чтобы можно было проще настраивать инструменты непрерывного развертывания
          0
          чтобы не случилось так, что для вашего дистрибутива или для вашего пакетного менеджера нет готовых бинарников нужного пакета, можно просто поднять его в докере и не морочить себе голову с курением мануалов

          Не понимаю, внутри докера ОС ведь будет та же, что и на хосте? Или это похоже на OpenVZ контейнер, где можно поставить любую ОС?
            0
            Докер использует лишь ядро. ОС, а точнее, дистрибутив Линукса, по сути набор программ и утилит поверх ядра. Вот Докер так и делает
              0
              OpenVZ делает так же. Чем docker от OpenVZ отличается?
              0
              Да, в контейнере может быть любая система
                0
                Докер использует от хостового линукса только ядро (это если говорить упрощенно). Поэтому внутри контейнера можно поднять абсолютно любой дистрибутив. Часто там используются специально заточенные под использование внутри контейнера минимальные версии дистрибутивов. OpenVZ использует очень похожий подход, но сложнее в использовании и не имеет столь широкой базы готовых контейнеров
                  0
                  У меня есть web приложение, работающее на nginx + php + mysql + несколько консольных утилит, сейчас работает на отдельной физической машине. Docker подходит для запуска всего этого в контейнере? Хотелось бы избавиться от отдельной физической машины.

                  Я просто вчера почитал про docker и я так понял, что основной подход, который он проповедует, это одно приложение в одном контейнере. Может я не прав, но по моему это перебор. Например есть образы с одним только phpmyadmin или вообще только с одним composer, это же дикий overhead.
                    0
                    Для вас оптимально будет использовать docker-compose с тремя контейнерами — отдельно nginx, отдельно mysql (можно брать прямо официальные образы), отдельно php-fpm+утилиты (скорее всего придется сбилдить свой образ на основе официального, но это несложно, в него же можно прикрутить composer с phpmyadmin), возможно еще +контейнер под хранение файлов если связку предполагается таскать с машины на машину. Можно заводить отдельный контейнер на phpmyadmin, а можно и нет. Но работать с кучей небольших официальных образов контейнеров часто проще, чем городить один свой, в котором запихнуто всё. И вся эта конструкция будет элементарно запускаться/глушиться одной командой.
                      0
                      Спасибо.
                      А почему nginx и mysql не поставить в тот же контейнер, где и php-fpm с утилитами? Может mysql вообще на хост машине оставить с отдельной учетной записью?
                      Я, наверное, чего-то до конца не понимаю, но мне пока не очень понятна вот эта концепция с кучей контейнеров.

                      Да, еще nginx и утилиты у меня из исходников собранные, в docker не будет проблем со сборкой из исходников?
                        0
                        А почему nginx и mysql не поставить в тот же контейнер, где и php-fpm с утилитами?

                        Потому что гораздо быстрее взять готовые образы и подключить их к связке, чем устанавливать их внутрь контейнера основного приложения. И бонусом получить горизонтальное масштабирование на проде
                          0
                          У меня nginx с модулями собран, готовый мне не подойдет.
                          То есть в принципе это как кому удобнее и ничто не мешает все в один контейнер поставить?
                            0
                            Абсолютно. Вы не получите некоторой части плюшек, связанных с модульностью, например горизонтальное масштабирование, но это будет вполне работоспособное решение — преимущества стандартного и изолированного окружения, а также возможность разворачивания через службы CI/CD никуда не деваются
                    0
                    Внутри контейнера вообще может не быть никакого дистрибутива линукса, например если контейнер содержит в себе приложение Python, или Java. Или nginx например. Т.е. контейнер содержит только то что нужно для запуска приложения, для которого этот контейнер был создан.
                      0
                      Нет, хоть урезанный, но линукс будет. Откройте Dockerfile любого образа контейнера на докер хабе и посмотрите что там происходит. Обычно в самой первой директиве FROM описано какой дистрибутив взят за основу. Но даже если там написано FROM scratch, всё равно используется докеровский дистрибутив по умолчанию
                0
                Что мне дает запихивание этих сервисов в контейнеры?

                Возможность поднять ещё десяток таких же серверов одной строкой.


                что делать при перемещении сервисов в контейнеры?

                docker logs, docker start, docker inspect...


                Докер позволяет сформировать и сохранить стабильную и воспроизводимую в любом месте и количестве среду для работы приложений.
                Соответственно, правильно собирая докерные кубики — можно быстро экспериментировать с композициями приложений, не отвлекаясь на артефакты установок-переустановок, общие зависимости и взаимные побочные эффекты.

                  0
                  Как все это администрировать? Если обычно у меня есть "$service --status-all" [start|stop|resrtart|reload], что делать при перемещении сервисов в контейнеры?


                  Простой ответ — docker ps.
                  Но учитывая, что у вас простое приложение и вы не задумываетесь о репликации, то вам не нужен докер.
                  Потому что, когда вам понадобится докер, вам понадобится:
                  1. Билд-сервер (Jenkins/TeamCity/etc), потому как не удобно готовить контейнеры ручками. А тут сервер, который берет из git-а и автоматизирует
                  2. Либо DockerHub, либо локальный репозитарий. Если репозитарий локальный, то вам понадобится сертификат (действительный, либо самоподписанный но который принимают сервера)
                  3. Watchdog на хост-сервере, чтобы следит за обновлениями в репозитарии.

                  В итоге, у вас будет инфраструктура, в которой по пушу будет собираться приложение, выкладываться в репозитарий и ставится в прод или в тест.
                    0

                    не пугайте человека раньше времени, jenkins, dockerhub и watchdog можно заменить парой .sh скриптов и докерфайлом. А когда втянется и поймёт на простом, тогда уже можно и всю инфраструктуру разворачивать.

                    0
                    Предположим, вам нужно запустить 50 веб-приложений, причем у некоторых могут быть разные требования к версии Python или версии java.
                    И вы хотите, чтобы приложения крутились максимально независимо друг от друга, не знали друг о друге, и одним кликом вы могли бы их развернуть или тут или на другой машине.

                    Простое решение независимости — виртуальные машины.
                    Вопрос, сколько виртуальных машин вы запустите на вашем сервере?

                    А 50 докер контейнеров — могут вполне влезть, потому что с небольшим навеском, это по памяти и CPU практически сами приложения. Да и по диску неслишком больше.
                    0
                    Вопрос возможно дурацкий, но все же.
                    Docker можно запускать локально на Linux, Mac и Windows.

                    Насколько оно кроссплатформено в итоге?
                    Вот под windows, например, заведется линуксовый контейнер?
                      +1
                      Не дурацкий, нормальный вопрос.
                      У нас бэки, которые на юниксах, всё готовят в докерах для фронтов, которые на Widnows. Неустранимых проблем не было.
                      Вообще, на windows поднимается любой *nix: Ubuntu, alpine, FreeBSD.
                      И там вы творите всё, что душе угодно.
                        +1
                        Ой, вот купился я на то, что под Windows можно легко и просто запускать Linux Docker контейнеры.
                        Сначала выяснили, что если это Windows сервер под VMWare, то во-первых важна версия. Ниже определенной не работает Hyper-V. Linux хостов это ограничение не касается, кстати.
                        Затем, когда проапгрейдили версию, все равно не заработало. Выделили физическую железку. Под ней тоже пляски с бубном: то оно сходу не поднимается, надо убить процесс, потом стартовать приложение под правами админа и тому подобное.
                        В GitHub issues for Windows уже пару лет не закрытые проблемы на винду.
                        Ну и самое обидное, что на рабочем виндовом компе всё работает.
                          +1
                          Учитывая, что если включить VMWare/Hyper-V, то, фактически, перестают работать другие виртуалки, то у нас многие не заморачиваются с «нативным» докером под виндой, а ставят в Virtualbox любой серверный линукс и ставят докер уже на него. С одной стороны, добавляется немного головной боли на пробрасывание ресурсов туда-сюда, с другой — нет проблем с несовместимостью VMWare/Hyper-V, всё отлично работает хоть из-под XP
                            +1
                            Ну что ж делать, пляски с бубном никто не отменял. За это и платят DevOps-ам хорошие зарплаты на уровне сисадминов и программистов.
                            Если говорить о моих личных предпочтениях, отчего я не пожалею времени на развёртывание докеров:
                            docker system prune -a
                            Потому что мне кажется это в разы проще, чем сперва понаставить mysql, postgres, rabbit и прочих спутников жизни, а потом мучительно удалять их. Не говоря уже о каких-нибудь OpenSSL, которые я вообще уже не представляю, как в Windows втыкать и можно ли в принципе это делать.
                        0
                        Подскажите пожалуйста прав ли я. Использование Докера оправдано в том случае, если потом это же приложение будет работать в другом месте под Докером — тогда не надо будет ничего перенастраивать.
                        Если же я локально делаю что-то под докером, а потом переношу это (условно) на хостинг, где докерами и не пахнет, я имею точно такие же шансы заиметь проблемы с разными настройками, несовместимостями и т.п. как и если бы я разрабатывал приложение под обычной ОС?
                          0
                          Докер нужен для того, чтобы легко перенести приложение например из разработки в продакшен, и при этом никаких зависимостей в саму ОС не устанавливать, поскольку все уже собрано внутри конкретного docker image.
                          Нет смысла разрабатывать приложение для работы в контейнере, а потом выдрать его из контейнера и запускать как обычно.
                          0

                          Подскажите, а где хранить docker compose если две части приложения находятся в разных репозиториях, но должны взаимодействовать на продакшине?

                            0
                            У меня примерно так:
                            |-- docker-compose
                            |-- service-1
                            |-- service-2
                            `-- service-3


                            service-1, service-2, service-3 хранятся в разных репозиториях.
                              0
                              А сам docker-compose в каком из репизиториев или он где-то на самом CI хранится?
                                0
                                docker-compose в своем отдельном репозитории.
                                Он используется только для локальной разработки, чтобы запускать/останавливать все контейнеры одно командой.
                            +3
                            Во всю эту красотишшу надо добавить пару камушков, ну чтобы юные падаваны не расшибли себе лоб.
                            1. Докер практически исключительно для кода, не для данных. Данные надо держать где-то снаружи, и потом пробрасывать внутрь контейнеров папки/диски/луны/чотамувас для тех данных, которые должны пережить рестарт контейнера. Не, ну если надо на локалхосте поставить какого-нибудь монстра, два часа потыкать в него и снести — можно и внутри данные хранить. В тестовых контейнерах опять же можно. Но на проде так делать не надо.
                            2. Вводя докер, вы переходите на коммуникации через tcp/ip. Монолитный nginx + php-fpm + mysql на сокетах может работать раза в два быстрее, чем то же самое, но в отдельных контейнерах по локальному tcp/ip. Потому что сокет он в разделяемой общей памяти и без копирования, а по сети данные минимум трижды копируются при упаковке/распаковке пакетов.
                            3. Вводя докер, вы вводите серьёзные зависимости непонятно от кого. Ну, точнее, следите, чьи именно репы вы используете. Они могут что-нибудь сломать в очередном апдейте (бывало и много раз), или вообще запихать какую-нибудь гадость (не слышал, но...).
                              0
                              Мы работаем с Docker Swarm + Ceph. Все работает неплохо. Мы планируем перенести в Swarm больше как наших собственных, так и сторонних приложений. Но есть проблемка:

                              Допустим, я развернул 10 сторонних приложений в виде docker swarm stack'ов. Я делаю это с помощью команды Docker stack deploy. Отдаю ему файл docker-compose (часто, в свою очередь, составленный из нескольких файлов docker-compose-*.yml, скомпилированных через docker-compose config). Но, если я хочу что-то изменить в стеке, мне часто нужны мои исходные файлы compose. Существует ли какой-либо реестр для дескрипторов развертывания docker-compose? Как реестр образов Docker, но для дескрипторов docker-compose?

                              Одна из идей, которые приходят на ум, состоит в том, чтобы завести Git или Mercurial репозиторий с некоторой структурой каталогов для версионирования дескрипторов развёртывания. Эта идея выглядит интересной, но работает (полу)хорошо только для сторонних приложений. С нашими собственными приложениями это добавляет проблем, так как мы часто используем CI/CD (тот самый пресловутый дженкинс и развёртывание на стейджинг после того, как тесты пройдут успешно). И это будет означать, что нам нужно извлечь еще один репозиторий во время развертывания, заменить deployment-дескрипторы для наших приложений и закоммитить их. Это может быть проблематично, так как это может привести к merge конфликтам и т. д. Да и вытягивать целый репозиторий ради коммита одного файла…

                              Видел забавное решение, когда docker-compose.yml запаковывается в docker image FROM docker/compose (https://hub.docker.com/r/docker/compose/) и пушится в локальный докер регистри. Но это решение тоже не супер, т.к., по сути, никакого версионирования между docker-compose-файлами нет.

                              Чтобы не кормить троллей: речь не идёт о Dockerfile, имейджах, билд-дкриптах и т.д. Это всё хранится в нормальных git/HG вместе с исходниками самих приложений и спользуется во время CI. Чтобы нагляднее представить себе проблему: представьте, что у вас несколько десятков stack'ов запущено в swarm'e. И вот вам понадобилось, скажем, заменить volume-driver. Для этого нужно взять тот докер-композ файл, из которого каждый стэк разворачивался и поправить в нём конфигурацию томов. А где взять все эти десятки композов? Они деплоились разными людьми в разное время с разных хостов.

                              В идеале, решение, которое я ищу, должно обеспечить простой способ получить последние версии дескрипторов развертывания определенного (развернутого) стека и одновременно содержать их предыдущие версии. Кроме того, чтобы я мог легко обновлять дескрипторы развертывания — без вытягивания всего git/hg репозитория

                              Как вы, ребята, управляете своими файлами для создания докеров, если их слишком много?

                              Только полноправные пользователи могут оставлять комментарии. Войдите, пожалуйста.

                              Самое читаемое