Docker краткое руководство

Содержание

  • Вопросы и ответы
  • Введение
    • Пре-реквизиты
    • Настройка компьютера

  • 1.0 Играем с Busybox
    • 1.1 Docker Run
    • 1.2 Терминология

  • 2.0 Веб-приложения и Докер
    • 2.1 Статические сайты
    • 2.2 Образы
    • 2.3 Наш первый образ
    • 2.4 Dockerfile
    • 2.5 Docker на AWS

  • 3.0 Многоконтейнерные окружения
    • 3.1 SF Food Trucks
    • 3.2 Сети Docker
    • 3.3 Docker Compose
    • 3.4 AWS Elastic Container Service

  • 4.0 Заключение
    • 4.1 Следующие шаги
    • 4.2 Фидбек автору

Вопросы и ответы

Что такое Докер?

Определение Докера в Википедии звучит так:

программное обеспечение для автоматизации развёртывания и управления приложениями в среде виртуализации на уровне операционной системы; позволяет «упаковать» приложение со всем его окружением и зависимостями в контейнер, а также предоставляет среду по управлению контейнерами.

Ого! Как много информации. Простыми словами, Докер это инструмент, который позволяет разработчикам, системными администраторам и другим специалистам деплоить их приложения в песочнице (которые называются контейнерами), для запуска на целевой операционной системе, например, Linux. Ключевое преимущество Докера в том, что он позволяет пользователям упаковать приложение со всеми его зависимостями в стандартизированный модуль для разработки. В отличие от виртуальных машин, контейнеры не создают такой дополнительной нагрузки, поэтому с ними можно использовать систему и ресурсы более эффективно.

Что такое контейнер?

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

Виртуальные машины отлично подходят для полной изоляции процесса для приложения: почти никакие проблемы основной операционной системы не могут повлиять на софт гостевой ОС, и наоборот. Но за такую изоляцию приходится платить. Существует значительная вычислительная нагрузка, необходимая для виртуализации железа гостевой ОС.

Контейнеры используют другой подход: они предоставляют схожий с виртуальными машинами уровень изоляции, но благодаря правильному задействованию низкоуровневых механизмов основной операционной системы делают это с в разы меньшей нагрузкой.

Почему я должен использовать их?

Взлет Докера был по-настоящему эпичным. Не смотря на то, что контейнеры сами по себе — не новая технология, до Докера они не были так распространены и популярны. Докер изменил ситуацию, предоставив стандартный API, который сильно упростил создание и использование контейнеров, и позволил сообществу вместе работать над библиотеками по работе с контейнерами. В статье, опубликованной в  The Register в середине 2014 говорится, что Гугл поддерживает больше двух миллиардов контейнеров в неделю.

Google Trends для слова ‘Docker’
interest

В дополнение к продолжительному росту Докера, компания-разработчик Docker Inc. была оценена в два с лишним миллиарда долларов! Благодаря преимуществам в эффективности и портативности, Докер начал получать все больше поддержки, и сейчас стоит во главе движения по контейнеризации (containerization). Как современные разработчики, мы должны понять этот тренд и выяснить, какую пользу мы можем получить из него.

Чему меня научит это пособие?

Это единое и полное пособие по всем аспектам работы с Докером. Кроме разъяснения мифов о Докере и его экосистеме, оно позволит вам получит небольшой опыт по сборке и деплою собственных веб-приложений в облаке. Мы будем использовать Amazon Web Services для деплоя статичных сайтов, и два динамических веб-приложения задеплоим на EC2 с использованием Elastic Beanstalk и Elastic Container Service. Даже если вы никогда ничего не деплоили, это пособие даст вам все необходимое.

Как использовать этот документ

Этот документ содержит несколько разделов, каждый из которых посвящен определенному аспекту Докера. В каждом разделе мы будем вводить команды или писать код. Весь код доступен в репозитории на Гитхабе.

Введение

Внимание: В этом пособии используется версия Докера 1.12.0-rc2. Если вы столкнулись с несовместимостью, пожалуйста, отправьте issue. Спасибо!

Пре-реквизиты

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

  • Amazon Web Services
  • Docker Hub

Настройка компьютера

Установка и настройка всех необходимых инструментов может быть тяжелой задачей, но, к счастью, Докер стал довольно стабильным, и установка и запуск его на любой ОС стало очень простой задачей. Итак, установим Докер.

Докер

Еще несколько релизов назад запуск Докера на OS X и Windows был был проблемным. Но команда разработчиков проделала огромную работу, и сегодня весь процесс — проще некуда. Этот туториал getting started включает в себя подробные инструкции по установке на Мак, Linux и Windows.

Проверим, все ли установлено корректно:

$ docker run hello-world

Hello from Docker.
This message shows that your installation appears to be working correctly.
...

Python

Python обычно предустановлен на OS X и на большинстве дистрибутивов Linux. Если вам нужно установить Питон, то скачайте установщик здесь.

Проверьте версию:

$ python --version
Python 2.7.11

Мы будем использовать pip для установки пакетов для нашего приложения. Если pip не установлен, то скачайте версию для своей системы.

Для проверки запустите такую команду:

$ pip --version
pip 7.1.2 from /Library/Python/2.7/site-packages/pip-7.1.2-py2.7.egg (python 2.7)

Java (не обязательно)

Разрабатываемое нами приложение будет использовать Elasticsearch для хранения и поиска. Для локального запуска Elasticsearch вам понадобится Java. В этом пособии все будет запускаться внутри контейнера, так что локально не обязательно иметь Java. Если Java установлена, то команда java -version должна сгенерировать подобный вывод:

$ java -version
java version "1.8.0_60"
Java(TM) SE Runtime Environment (build 1.8.0_60-b27)
Java HotSpot(TM) 64-Bit Server VM (build 25.60-b23, mixed mode)


1.0 Играем с Busybox

Теперь, когда все необходимое установлено, пора взяться за работу. В этом разделе мы запустим контейнер Busybox на нашей системе и попробуем запустить docker run.

Для начала, запустите следующую команду:

$ docker pull busybox

Внимание: в зависимости от того, как вы устанавливали Докер на свою систему, возможно появление сообщения permission denied. Если вы на Маке, то удостоверьтесь, что движок Докер запущен. Если вы на Линуксе, то запустите эту команду с sudo. Или можете создать группу docker чтобы избавиться от этой проблемы.

Команда pull скачивает образ busybox из регистра Докера и сохраняет его локально. Можно использовать команду docker images, чтобы посмотреть список образов в системе.

$ docker images
REPOSITORY              TAG                 IMAGE ID            CREATED             VIRTUAL SIZE
busybox                 latest              c51f86c28340        4 weeks ago         1.109 MB

1.1 Docker Run

Отлично! Теперь давайте запустим Докер-контейнер с этим образом. Для этого используем волшебную команду docker run:

$ docker run busybox
$

Подождите, ничего не произошло! Это баг? Ну, нет. Под капотом произошло много всего. Докер-клиент нашел образ (в нашем случае, busybox), загрузил контейнер и запустил команду внутри этого контейнера. Мы сделали docker run busybox, но не указали никаких команд, так что контейнер загрузился, запустилась пустая команда и программа завершилась. Ну, да, как-то обидно, так что давайте сделаем что-то поинтереснее.

$ docker run busybox echo "hello from busybox"
hello from busybox

Ура, наконец-то какой-то вывод. В нашем случае клиент Докера послушно запустил команду echo внутри контейнера, а потом вышел из него. Вы, наверное, заметили, что все произошло очень быстро. А теперь представьте себе, как нужно загружать виртуальную машину, запускать в ней команду и выключать ее. Теперь ясно, почему говорят, что контейнеры быстрые!

Теперь давайте взглянем на команду docker ps. Она выводит на экран список всех запущенных контейнеров.

$ docker ps
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS              PORTS               NAMES

Контейнеров сейчас нет, поэтому выводится пустая строка. Не очень полезно, поэтому давайте запустим более полезный вариант: docker ps -a

$ docker ps -a
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS                      PORTS               NAMES
305297d7a235        busybox             "uptime"            11 minutes ago      Exited (0) 11 minutes ago                       distracted_goldstine
ff0a5c3750b9        busybox             "sh"                12 minutes ago      Exited (0) 12 minutes ago                       elated_ramanujan

Теперь виден список всех контейнеров, которые мы запускали. В колонке STATUS можно заметить, что контейнеры завершили свою работу несколько минут назад.

Вам, наверное, интересно, как запустить больше одной команды в контейнере. Давайте попробуем:

$ docker run -it busybox sh
/ # ls
bin   dev   etc   home  proc  root  sys   tmp   usr   var
/ # uptime
 05:45:21 up  5:58,  0 users,  load average: 0.00, 0.01, 0.04

 

Команда run с флагом -it подключает интерактивный tty в контейнер. Теперь можно запускать сколько угодно много команд внутри. Попробуйте.

Опасно!: Если хочется острых ощущений, то можете попробовать rm -rf bin в контейнере. Но удостоверьтесь, что запускаете ее внутри контейнера, а не снаружи. Если сделаете это снаружи, на своем компьютере, то будет очень плохо, и команды вроде lsecho перестанут работать. Когда внутри контейнера все перестанет работать, просто выйдете и запустите его заново командой docker run -it busybox sh. Докер создает новый контейнер при запуске, поэтому все заработает снова.

На этом захватывающий тур по возможностям команды docker run закончен. Скорее всего, вы будете использовать эту команду довольно часто. Так что важно, чтобы мы поняли как с ней обращаться. Чтобы узнать больше о run, используйте docker run --help, и увидите полный список поддерживаемых флагов. Скоро мы увидим еще несколько способов использования docker run.

Перед тем, как продолжать, давайте вкратце рассмотрим удаление контейнеров. Мы видели выше, что с помощью команды docker ps -a все еще можно увидеть остатки завершенных контейнеров. На протяжении этого пособия, вы будете запускать docker run несколько раз, и оставшиеся, бездомные контейнеры будут съедать дисковое пространство. Так что я взял за правило удалять контейнеры после завершения работы с ними. Для этого используется команда docker rm. Просто скопируйте ID (можно несколько) из вывода выше и передайте параметрами в команду.

$ docker rm 305297d7a235 ff0a5c3750b9
305297d7a235
ff0a5c3750b9

При удалении идентификаторы будут снова выведены на экран. Если нужно удалить много контейнеров, то вместо ручного копирования и вставления можно сделать так:

$ docker rm $(docker ps -a -q -f status=exited)

Эта команда удаляет все контейнеры, у которых статус exited. Флаг -q возвращает только численные ID, а флаг -f фильтрует вывод на основе предоставленных условий. Последняя полезная деталь — команде docker run можно передать флаг --rm, тогда контейнер будет автоматически удаляться при завершении. Это очень полезно для разовых запусков и экспериментов с Докером.

Также можно удалять ненужные образы командой docker rmi.

1.2 Терминология

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

  • Images (образы) — Схемы нашего приложения, которые являются основой контейнеров. В примере выше мы использовали команду docker pull чтобы скачать образ busybox.
  • Containers (контейнеры) — Создаются на основе образа и запускают само приложение. Мы создали контейнер командой docker run, и использовали образ busybox, скачанный ранее. Список запущенных контейнеров можно увидеть с помощью команды docker ps.
  • Docker Daemon (демон Докера) — Фоновый сервис, запущенный на хост-машине, который отвечает за создание, запуск и уничтожение Докер-контейнеров. Демон — это процесс, который запущен на операционной системе, с которой взаимодействует клиент.
  • Docker Client (клиент Докера) — Утилита командной строки, которая позволяет пользователю взаимодействовать с демоном. Существуют другие формы клиента, например, Kitematic, с графическим интерфейсом.
  • Docker Hub — Регистр Докер-образов. Грубо говоря, архив всех доступных образов. Если нужно, то можно содержать собственный регистр и использовать его для получения образов.

2.0 Веб-приложения и Докер

Супер! Теперь мы научились работать с  docker run, поиграли с несколькими контейнерами и разобрались в терминологии. Вооруженные этими знаниями, мы готовы переходить к реальным штукам: деплою веб-приложений с Докером!

2.1 Статические сайты

Давайте начнем с малого. Вначале рассмотрим самый простой статический веб-сайт. Скачаем образ из Docker Hub, запустим контейнер и посмотрим, насколько легко будет запустить веб-сервер.

Поехали. Для одностраничного сайта нам понадобится образ, который я заранее создал для этого пособия и разместил в регистре — prakhar1989/static-site. Можно скачать образ напрямую командой docker run.

$ docker run prakhar1989/static-site

Так как образа не существует локально, клиент сначала скачает образ из регистра, а потом запустит его. Если все без проблем, то вы увидите сообщение Nginx is running... в терминале. Теперь сервер запущен. Как увидеть сайт в действии? На каком порту работает сервер? И, что самое важное, как напрямую достучаться до контейнера из хост-контейнера?

В нашем случае клиент не открывает никакие порты, так что нужно будет перезапустить команду  docker run чтобы сделать порты публичными. Заодно давайте сделаем так, чтобы терминал не был прикреплен к запущенному контейнеру. В таком случае можно будет спокойно закрыть терминал, а контейнер продолжит работу. Это называется detached mode.

$ docker run -d -P --name static-site prakhar1989/static-site
e61d12292d69556eabe2a44c16cbd54486b2527e2ce4f95438e504afb7b02810

Флаг -d открепит (detach) терминал, флаг -P сделает все открытые порты публичными и случайными, и, наконец, флаг --name это имя, которое мы хотим дать контейнеру. Теперь можно увидеть порты с помощью команды docker port [CONTAINER].

$ docker port static-site
80/tcp -> 0.0.0.0:32769
443/tcp -> 0.0.0.0:32768

Откройте http://localhost:32769 в своем браузере.

Замечание: Если вы используете docker-toolbox, то, возможно, нужно будет использовать docker-machine ip default чтобы получить IP-адрес.

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

$ docker run -p 8888:80 prakhar1989/static-site
Nginx is running...

static

Чтобы остановить контейнер запустите docker stop и укажите идентификатор (ID) контейнера.

Согласитесь, все было очень просто. Чтобы задеплоить это на реальный сервер, нужно просто установить Докер и запустить команду выше. Теперь, когда вы увидели, как запускать веб-сервер внутри образа, вам, наверное, интересно — а как создать свой Докер-образ? Мы будем изучать эту тему в следующем разделе.

2.2 Образы

Мы касались образов ранее, но в этом разделе мы заглянем глубже: что такое Докер-образы и как создавать собственные образы. Наконец, мы используем собственный образ чтобы запустить приложение локально, а потом задеплоим его на AWS, чтобы показать друзьям. Круто? Круто! Давайте начнем.

Образы это основы для контейнеров. В прошлом примере мы скачали (pull) образ под названием Busybox из регистра, и попросили клиент Докера запустить контейнер, основанный на этом образе. Чтобы увидеть список доступных локально образов, используйте команду docker images.

$ docker images
REPOSITORY                      TAG                 IMAGE ID            CREATED             VIRTUAL SIZE
prakhar1989/catnip              latest              c7ffb5626a50        2 hours ago         697.9 MB
prakhar1989/static-site         latest              b270625a1631        21 hours ago        133.9 MB
python                          3-onbuild           cf4002b2c383        5 days ago          688.8 MB
martin/docker-cleanup-volumes   latest              b42990daaca2        7 weeks ago         22.14 MB
ubuntu                          latest              e9ae3c220b23        7 weeks ago         187.9 MB
busybox                         latest              c51f86c28340        9 weeks ago         1.109 MB
hello-world                     latest              0a6ba66e537a        11 weeks ago        960 B

Это список образов, которые я скачал из регистра, а также тех, что я сделал сам (скоро увидим, как это делать). TAG — это конкретный снимок или снэпшот (snapshot) образа, а IMAGE ID — это соответствующий уникальный идентификатор образа.

Для простоты, можно относиться к образу как к git-репозиторию. Образы можно коммитить с изменениями, и можно иметь несколько версий. Если не указывать конкретную версию, то клиент по умолчанию использует latest. Например, можно скачать определенную версию образа ubuntu:

$ docker pull ubuntu:12.04

Чтобы получить новый Докер-образ, можно скачать его из регистра (такого, как Docker Hub) или создать собственный. На Docker Hub есть десятки тысяч образов. Можно искать напрямую из командной строки с помощью docker search.

Важно понимать разницу между базовыми и дочерними образами:

  • Base images (базовые образы) — это образы, которые не имеют родительского образа. Обычно это образы с операционной системой, такие как ubuntu, busybox или debian.
  • Child images (дочерние образы) — это образы, построенные на базовых образах и обладающие дополнительной функциональностью.

Существуют официальные и пользовательские образы, и любые из них могут быть базовыми и дочерними.

  • Официальные образы — это образы, которые официально поддерживаются командой Docker. Обычно в их названии одно слово. В списке выше pythonubuntubusybox и hello-world — базовые образы.
  • Пользовательские образы — образы, созданные простыми пользователями вроде меня и вас. Они построены на базовых образах. Обычно, они называются по формату user/image-name.

2.3 Наш первый образ

Теперь, когда мы лучше понимаем, что такое образы и какие они бывают, самое время создать собственный образ. Цель этого раздела — создать образ с простым приложением на Flask. Для этого пособия я сделал маленькое приложение, которое выводит случайную гифку с кошкой. Ну, потому что, кто не любит кошек? Склонируйте этот репозиторий к себе на локальную машину.

Вначале давайте проверим, что приложение работает локально. Войдите в директорию flask-app командой cd и установите зависимости.

$ cd flask-app
$ pip install -r requirements.txt
$ python app.py
 * Running on http://0.0.0.0:5000/ (Press CTRL+C to quit)

 

Если все хорошо, то вы увидите вывод как в примере выше. Зайдите на http://localhost:5000 чтобы увидеть приложение в действии.

Замечание: Если команда pip install падает с ошибками «permission denied», то попробуйте запустить ее с sudo. Если не хотите устанавливать пользовательские пакеты на уровне системы, то используйте команду pip install --user -r requirements.txt.

Выглядит отлично, правда? Теперь нужно создать образ с приложением. Как говорилось выше, все пользовательские образы основаны на базовом образе. Так как наше приложение написано на Питоне, нам нужен базовый образ Python 3. В частности, нам нужна версия python:3-onbuild базового образа с Питоном.

Что за версия onbuild, спросите вы?

Эти образы включают несколько триггеров ONBUILD, которых обычно достаточно чтобы быстро развернуть приложение. При сборке будет скопирован файл requirements.txt, будет запущен pip install с этим файлом, а потом текущая директория будет скопирована в /usr/src/app.

Другими словами, версия onbuild включает хелперы, которые автоматизируют скучные процессы запуска приложения. Вместо того, чтобы вручную выполнять эти задачи (или писать скрипты), образы делают все за вас. Теперь у нас есть все ингредиенты для создания своего образа: работающее веб-приложение и базовый образ. Как это сделать? Ответ: использовать Dockerfile.

2.4 Dockerfile

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

В директории с приложением есть Dockerfile, но так как мы делаем все впервые, нам нужно создать его с нуля. Создайте новый пустой файл в любимом текстовом редакторе, и сохраните его в той же директории, где находится flask-приложение. Назовите файл Dockerfile.

Для начала укажем базовый образ. Для этого нужно использовать ключевое слово FROM.

FROM python:3-onbuild

Дальше обычно указывают команды для копирования файлов и установки зависимостей. Но к счастью, onbuild-версия базового образа берет эти задачи на себя. Дальше нам нужно указать порт, который следует открыть. Наше приложение работает на порту 5000, поэтому укажем его:

EXPOSE 5000

Последний шаг — указать команду для запуска приложения. Это просто python ./app.py. Для этого используем команду CMD:

CMD ["python", "./app.py"]

Главное предназначение CMD — это сообщить контейнеру какие команды нужно выполнить при старте. Теперь наш Dockerfile готов. Вот как он выглядит:

# our base image
FROM python:3-onbuild

# specify the port number the container should expose
EXPOSE 5000

# run the application
CMD ["python", "./app.py"]

Теперь можно создать образ. Команда docker build занимается сложной задачей создания образа на основе Dockerfile.

Листинг ниже демонстрирует процесс. Перед тем, как запустите команду сами (не забудьте точку в конце), проверьте, чтобы там был ваш username вместо моего. Username должен соответствовать тому, что использовался при регистрации на Docker hub. Если вы еще не регистрировались, то сделайте это до выполнения команды. Команда docker build довольно проста: она принимает опциональный тег с флагом -t и путь до директории, в которой лежит Dockerfile.

$ docker build -t prakhar1989/catnip .
Sending build context to Docker daemon 8.704 kB
Step 1 : FROM python:3-onbuild
# Executing 3 build triggers...
Step 1 : COPY requirements.txt /usr/src/app/
 ---> Using cache
Step 1 : RUN pip install --no-cache-dir -r requirements.txt
 ---> Using cache
Step 1 : COPY . /usr/src/app
 ---> 1d61f639ef9e
Removing intermediate container 4de6ddf5528c
Step 2 : EXPOSE 5000
 ---> Running in 12cfcf6d67ee
 ---> f423c2f179d1
Removing intermediate container 12cfcf6d67ee
Step 3 : CMD python ./app.py
 ---> Running in f01401a5ace9
 ---> 13e87ed1fbc2
Removing intermediate container f01401a5ace9
Successfully built 13e87ed1fbc2

Если у вас нет образа python:3-onbuild, то клиент сначала скачает его, а потом возьмется за создание вашего образа. Так что, вывод на экран может отличаться от моего. Посмотрите внимательно, и найдете триггеры onbuild. Если все прошло хорошо, то образ готов! Запустите docker images и увидите свой образ в списке.

Последний шаг — запустить образ и проверить его работоспособность (замените username на свой):

$ docker run -p 8888:5000 prakhar1989/catnip
 * Running on http://0.0.0.0:5000/ (Press CTRL+C to quit)

 

Зайдите на указанный URL и увидите приложение в работе.

static

Поздравляю! Вы успешно создали свой первый образ Докера!

2.5 Docker на AWS

Что хорошего в приложении, которое нельзя показать друзьям, правда? Так что в этом разделе мы научимся деплоить наше офигенное приложение в облако. Будем использовать AWS Elastic Beanstalk чтобы решить эту задачу за пару кликов. Мы увидим, как с помощью Beanstalk легко управлять и масштабировать наше приложение.

Docker push

Первое, что нужно сделать перед деплоем на AWS это опубликовать наш образ в регистре, чтобы можно было скачивать его из AWS. Есть несколько Docker-регистров (или можно создать собственный). Для начала, давайте используем Docker Hub. Просто выполните:

$ docker push prakhar1989/catnip

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

$ docker login
Username: prakhar1989
WARNING: login credentials saved in /Users/prakhar/.docker/config.json
Login Succeeded

Не забудьте заменить название образа на свое. Очень важно сохранить формат username/image_name, чтобы клиент понимал, куда публиковать образ.

После этого можете посмотреть на свой образ на Docker Hub. Например, вот страница моего образа.

Замечание: один важный момент, который стоит прояснить перед тем, как продолжить — не обязательно хранить образ в публичном регистре (или в любом другом регистре вообще) чтобы деплоить на AWS. Если вы пишете код для следующего многомиллионного стартапа-единорога, то можно пропустить этот шаг. Мы публикуем свой образ чтобы упростить деплой, пропустив несколько конфигурационных шагов.

Теперь наш образ онлайн, и любой докер-клиент может поиграться с ним с помощью простой команды:

$ docker run -p 8888:5000 prakhar1989/catnip

Если в прошлом вы мучались с установкой локального рабочего окружения и попытками поделиться своей конфигурацией с коллегами, то понимаете, как круто это звучит. Вот почему Докер — это сила!

Beanstalk

AWS Elastic Beanstalk (EB) это PaaS (Platform as a Service — платформа как сервис) от Amazon Web Services. Если вы использовали Heroku, Google App Engine и т.д., то все будет привычно. Как разработчик, вы сообщаете EB как запускать ваше приложение, а EB занимается всем остальным, в том числе масштабированием, мониторингом и даже апдейтами. В апреле 2014 в EB добавили возможность запускать Докер-контейнеры, и мы будем использовать именно эту возможность для деплоя. У EB очень понятный интерфейс командной строки, но он требует небольшой конфигурации, поэтому для простоты давайте используем веб-интерфейс для запуска нашего приложения.

Чтобы продолжать, вам потребуется работающий аккаунт на AWS. Если у вас его нет, то создайте его. Для этого потребуется ввести данные кредитной карты. Но не волнуйтесь, эта услуга бесплатна, и все, что будет происходить в рамках этого пособия тоже бесплатно.

Давайте начнем:

  • Войдите в свою консоль AWS.
  • Нажмите на Elastic Beanstalk. Ссылка находится в секции compute, в левом верхнем углу. Или просто перейдите сюда.

static

  • Нажмите на «Create New Application» в верхнем правом углу.
  • Дайте своему приложению запоминающееся (но уникальное) имя и, если хотите, добавьте описание.
  • на экране New Environment выберите Web Server Environment.
  • Следующий экран показан ниже. Выберите Docker из готовых вариантов конфигурации. Можно оставить Environment type как есть. Нажмите Next.

static

  • Тут мы будем сообщать системе EB о нашем образе. Откройте файл Dockerrun.aws.json в директории flask-app и измените Name образа, чтобы оно соответствовало названию вашего образа. Не волнуйтесь, я опишу содержание файла попозже. Потом выберите вариант «upload your own» и выберите файл.
  • Далее, выберите название окружения и URL. Этот URL как раз можно будет давать друзьям, так что постарайтесь придумать что-нибудь попроще.
  • Пока не будем вносить никаких правок в секцию Additional Resources. Нажмите Next и переходите к Configuration Details.
  • В этой секции вам нужно выбрать тип инстанса t1.micro. Это очень важно, потому что это бесплатный тип от AWS. Если хотите, можно выбрать пару ключей для входа. Если вы не знаете, что это значит, то не волнуйтесь и просто пропустите эту часть. Все остальное можно оставить по умолчанию и продолжать.
  • Также не нужно указывать никакие Environment Tags and Permissions, так что просто жмите Next два раза подряд. В конце будет экран Review. Если все выглядит нормально, то нажимайте кнопку Launch.
  • На последнем экране будет несколько спиннеров. Это поднимается и настраивается ваше окружение. Обычно, нужно около пяти минут для первой настройки.

Пока ждем, давайте быстренько взглянем на файл Dockerrun.aws.json. Это файл для AWS, в котором находится информация о приложении конфигурации Докера. EB получает информацию из этого файла.

{
  "AWSEBDockerrunVersion": "1",
  "Image": {
    "Name": "prakhar1989/catnip",
    "Update": "true"
  },
  "Ports": [
    {
      "ContainerPort": "5000"
    }
  ],
  "Logging": "/var/log/nginx"
}

Файл довольно понятный, но всегда можно обратиться к официальной документации. Мы указываем название образа, и EB будет использовать его заодно с портом.

К этому моменту инстанс уже должен быть готов. Зайдите на страницу EB и увидите зеленый индикатор успешного запуска приложения.

static

Зайдите на указанный URL в браузере и увидите приложение во все красе. Пошлите адрес своим друзьям, чтобы все могли насладиться гифками с кошками.

Поздравляю! Вы задеплоили свое первое Докер-приложение! Может показаться, что было очень много шагов, но с командной утилитой EB можно имитировать функциональность Хероку несколькими нажатиями клавиш. Надеюсь, вы согласитесь, что Докер сильно упрощает процесс и минимизирует болезненные моменты деплоя в облако. Я советую вам почитать документацию AWS про single-container Docker environment чтобы понимать, какие существуют возможности в EB.

В следующей, последней части пособия, мы пойдем немного дальше и задеплоим приложение, приближенное к реальному миру. В нем будет постоянное бэкэнд-хранилище. Поехали!

3.0 Многоконтейнерные окружения

В прошлом разделе мы увидели, как легко и просто запускать приложения с помощью Докера. Мы начали с простого статического сайта, а потом запустили Flask-приложение. Оба варианта можно было запускать локально или в облаке, несколькими командами. Общая черта этих приложений: каждое из них работало в одном контейнере.

Если у вас есть опыт управления сервисами в продакшене, то вы знаете, что современные приложения обычно не такие простые. Почти всегда есть база данных (или другой тип постоянного хранилища). Системы вроде Redis и Memcached стали практически обязательной частью архитектуры веб-приложений. Поэтому, в этом разделе мы научимся «докеризировать» приложения, которым требуется несколько запущенных сервисов.

В частности, мы увидим, как запускать и управлять многоконтейнерными Докер-окружениями. Почему нужно несколько контейнеров, спросите вы? Ну, одна из главных идей Докера в том, что он предоставляет изоляцию. Идея совмещения процесса и его зависимостей в одной песочнице (называемой контейнером) и делает Докер мощным инструментом.

Аналогично тому, как приложение разбивают на части, стоит содержать отдельные сервисы в отдельных контейнерах. Разным частям скорее всего требуются разные ресурсы, и требования могут расти с разной скоростью. Если мы разделим эти части и поместим в разные контейнеры, то каждую часть приложения можно строить, используя наиболее подходящий тип ресурсов. Это также хорошо совмещается с идеей микро сервисов. Это одна из причин, по которой Докер (и любая другая технология контейнеризации) находится на передовой современных микро сервисных архитектур.

3.1 SF Food Trucks

Приложение, которое мы переведем в Докер, называется SF Food Trucks (к сожалению, сейчас приложение уже не работает публично — прим. пер.). Моя цель была сделать что-то полезное (и похожее на настоящее приложение из реального мира), что-то, что использует как минимум один сервис, но не слишком сложное для этого пособия. Вот что я придумал.

sf food trucks

Бэкэнд приложения написано на Питоне (Flask), а для поиска используется Elasticsearch. Как и все остальное в этом пособии, код находится на Github. Мы используем это приложение, чтобы научиться запускать и деплоить много-контейнерное окружение.

Теперь, когда вы завелись (надеюсь), давайте подумаем, как будет выглядеть этот процесс. В нашем приложении есть бэкэнд на Flask и сервис Elasticsearch. Очевидно, что можно поделить приложение на два контейнера: один для Flask, другой для Elasticsearch (ES). Если приложение станет популярным, то можно будет добавлять новые контейнеры в нужном месте, смотря где будет узкое место.

Отлично, значит нужно два контейнера. Это не сложно, правда? Мы уже создавали Flask-контейнер в прошлом разделе. А для Elasticsearch… давайте посмотрим, есть ли что-нибудь в хабе:

$ docker search elasticsearch
NAME                              DESCRIPTION                                     STARS     OFFICIAL   AUTOMATED
elasticsearch                     Elasticsearch is a powerful open source se...   697       [OK]
itzg/elasticsearch                Provides an easily configurable Elasticsea...   17                   [OK]
tutum/elasticsearch               Elasticsearch image - listens in port 9200.     15                   [OK]
barnybug/elasticsearch            Latest Elasticsearch 1.7.2 and previous re...   15                   [OK]
digitalwonderland/elasticsearch   Latest Elasticsearch with Marvel & Kibana       12                   [OK]
monsantoco/elasticsearch          ElasticSearch Docker image                      9                    [OK]

Не удивительно, но существуют официальный образ для Elasticsearch. Чтобы запустить ES, нужно всего лишь выполнить docker run, и вскоре у нас будет локальный, работающий контейнер с одним узлом ES.

$ docker run -dp 9200:9200 elasticsearch
d582e031a005f41eea704cdc6b21e62e7a8a42021297ce7ce123b945ae3d3763

$ curl 0.0.0.0:9200
{
  "name" : "Ultra-Marine",
  "cluster_name" : "elasticsearch",
  "version" : {
    "number" : "2.1.1",
    "build_hash" : "40e2c53a6b6c2972b3d13846e450e66f4375bd71",
    "build_timestamp" : "2015-12-15T13:05:55Z",
    "build_snapshot" : false,
    "lucene_version" : "5.3.1"
  },
  "tagline" : "You Know, for Search"
}

Заодно давайте запустим контейнер с Flask. Но вначале нужен Dockerfile. В прошлой секции мы использовали образ python:3-onbuild в качестве базового. Однако, в этом раз, кроме установки зависимостей через pip, нам нужно, чтобы приложение генерировало минимизированный Javascript-файл для продакшена. Для этого понадобится Nodejs. Так что нужен свой билд с нуля, поэтому начнем с базового образа ubuntu.

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

Наш Dockerfile для Flask-приложения выглядит следующим образом:

# start from base
FROM ubuntu:14.04
MAINTAINER Prakhar Srivastav <prakhar@prakhar.me>

# install system-wide deps for python and node
RUN apt-get -yqq update
RUN apt-get -yqq install python-pip python-dev
RUN apt-get -yqq install nodejs npm
RUN ln -s /usr/bin/nodejs /usr/bin/node

# copy our application code
ADD flask-app /opt/flask-app
WORKDIR /opt/flask-app

# fetch app specific deps
RUN npm install
RUN npm run build
RUN pip install -r requirements.txt

# expose port
EXPOSE 5000

# start app
CMD [ "python", "./app.py" ]

Тут много всего нового. Вначале указан базовый образ Ubuntu LTS, потом используется пакетный менеджер apt-get для установки зависимостей, в частности — Python и Node. Флаг yqq нужен для игнорирования вывода и автоматического выбора «Yes» во всех местах. Также создается символическая ссылка для бинарного файла node. Это нужно для решения проблем обратной совместимости.

Потом мы используем команду ADD для копирования приложения в нужную директорию в контейнере — /opt/flask-app. Здесь будет находиться весь наш код. Мы также устанавливаем эту директорию в качестве рабочей, так что следующие команды будут выполняться в контексте этой локации. Теперь, когда наши системные зависимости установлены, пора установить зависимости уровня приложения. Начнем с Node, установки пакетов из npm и запуска команды сборки, как указано в нашем файле package.json. В конце устанавливаем пакеты Python, открываем порт и определяем запуск приложения с помощь CMD, как в предыдущем разделе.

Наконец, можно собрать образ и запустить контейнер (замените prakhar1989 на свой username ниже).

$ docker build -t prakhar1989/foodtrucks-web .

При первом запуске нужно будет больше времени, так как клиент Докера будет скачивать образ ubuntu, запускать все команды и готовить образ. Повторный запуск docker build после последующих изменений будет практически моментальным. Давайте попробуем запустить приложение

$ docker run -P prakhar1989/foodtrucks-web
Unable to connect to ES. Retying in 5 secs...
Unable to connect to ES. Retying in 5 secs...
Unable to connect to ES. Retying in 5 secs...
Out of retries. Bailing out...

Упс! Наше приложение не смогло запуститься, потому что оно не может подключиться к Elasticsearch. Как сообщить одному контейнеру о другом и как заставить их взаимодействовать друг с другом? Ответ — в следующей секции.

3.2 Сети Docker

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

Ладно, давайте запустим docker ps, что тут у нас:

$ docker ps
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                              NAMES
e931ab24dedc        elasticsearch       "/docker-entrypoint.s"   2 seconds ago       Up 2 seconds        0.0.0.0:9200->9200/tcp, 9300/tcp   cocky_spence

Итак, у нас есть контейнер ES по адресу и порту 0.0.0.0:9200, и мы можем напрямую обращаться к нему. Если можно было бы сообщить нашему приложению подключаться к этому адресу, то оно сможет общаться с ES, верно? Давайте взглянем на код на Питоне, туда, где описано подключение.

es = Elasticsearch(host='es')

Нужно сообщить Flask-контейнеру, что контейнер ES запущен на хосте 0.0.0.0 (порт по умолчанию 9200), и все заработает, да? К сожалению, нет, потому что IP 0.0.0.0 это адрес для доступа к контейнеру с  хост-машины, то есть с моего Мака. Другой контейнер не сможет обратиться по этому адресу. Ладно, если не этот адрес, то какой другой адрес нужно использовать для работы с контейнером ES? Рад, что вы спросили.

Это хороший момент, чтобы изучить работу сети в Докере. После установки, Докер автоматически создает три сети:

$ docker network ls
NETWORK ID          NAME                DRIVER
075b9f628ccc        none                null
be0f7178486c        host                host
8022115322ec        bridge              bridge

Сеть bridge — это сеть, в которой контейнеры запущены по умолчанию. Это значит, что когда я запускаю контейнер ES, он работает в этой сети bridge. Чтобы удостовериться, давайте проверим:

$ docker network inspect bridge
[
    {
        "Name": "bridge",
        "Id": "8022115322ec80613421b0282e7ee158ec41e16f565a3e86fa53496105deb2d7",
        "Scope": "local",
        "Driver": "bridge",
        "IPAM": {
            "Driver": "default",
            "Config": [
                {
                    "Subnet": "172.17.0.0/16"
                }
            ]
        },
        "Containers": {
            "e931ab24dedc1640cddf6286d08f115a83897c88223058305460d7bd793c1947": {
                "EndpointID": "66965e83bf7171daeb8652b39590b1f8c23d066ded16522daeb0128c9c25c189",
                "MacAddress": "02:42:ac:11:00:02",
                "IPv4Address": "172.17.0.2/16",
                "IPv6Address": ""
            }
        },
        "Options": {
            "com.docker.network.bridge.default_bridge": "true",
            "com.docker.network.bridge.enable_icc": "true",
            "com.docker.network.bridge.enable_ip_masquerade": "true",
            "com.docker.network.bridge.host_binding_ipv4": "0.0.0.0",
            "com.docker.network.bridge.name": "docker0",
            "com.docker.network.driver.mtu": "1500"
        }
    }
]

Видно, что контейнер e931ab24dedc находится в секции Containers. Также виден IP-адрес, выданный этому контейнеру — 172.17.0.2. Именно этот адрес мы и искали? Давайте проверим: запустим Flask-приложение и попробуем обратиться к нему по IP:

$ docker run -it --rm prakhar1989/foodtrucks-web bash
root@35180ccc206a:/opt/flask-app# curl 172.17.0.2:9200
bash: curl: command not found
root@35180ccc206a:/opt/flask-app# apt-get -yqq install curl
root@35180ccc206a:/opt/flask-app# curl 172.17.0.2:9200
{
  "name" : "Jane Foster",
  "cluster_name" : "elasticsearch",
  "version" : {
    "number" : "2.1.1",
    "build_hash" : "40e2c53a6b6c2972b3d13846e450e66f4375bd71",
    "build_timestamp" : "2015-12-15T13:05:55Z",
    "build_snapshot" : false,
    "lucene_version" : "5.3.1"
  },
  "tagline" : "You Know, for Search"
}
root@35180ccc206a:/opt/flask-app# exit

Сейчас все должно быть понятно. Мы запустили контейнер в интерактивном режиме с процессом bash. Флаг --rm нужен для удобства, благодаря нему контейнер автоматически удаляется после выхода. Мы попробуем curl, но нужно сначала установить его. После этого можно удостовериться, что по адресу 172.17.0.2:9200 на самом деле можно обращаться к ES! Супер!

Не смотря на то, что мы нашли способ наладить связь между контейнерами, существует несколько проблем с этим подходом:

  1. Придется добавлять записи в файл /etc/hosts внутри Flask-контейнера, чтобы приложение понимало, что имя хоста es означает 172.17.0.2. Если IP-адрес меняется, то придется вручную менять запись.
  2. Так как сеть bridge используется всеми контейнерами по умолчанию, этот метод не безопасен.

Но есть хорошие новости: в Докере есть отличное решение этой проблемы. Докер позволяет создавать собственные изолированные сети. Это решение также помогает справиться с проблемой /etc/hosts, сейчас увидим как.

Во-первых, давайте создадим свою сеть:

$ docker network create foodtrucks
1a3386375797001999732cb4c4e97b88172d983b08cd0addfcb161eed0c18d89

$ docker network ls
NETWORK ID          NAME                DRIVER
1a3386375797        foodtrucks          bridge
8022115322ec        bridge              bridge
075b9f628ccc        none                null
be0f7178486c        host                host

Команда network create создает новую сеть bridge. Нам сейчас нужен именно такой тип. Существуют другие типы сетей, и вы можете почитать о них в официальной документации.

Теперь у нас есть сеть. Можно запустить наши контейнеры внутри сети с помощью флага --net. Давайте так и сделаем, но сначала остановим контейнер с ElasticSearch, который был запущен в сети bridge по умолчанию.

$ docker ps
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                              NAMES
e931ab24dedc        elasticsearch       "/docker-entrypoint.s"   4 hours ago         Up 4 hours          0.0.0.0:9200->9200/tcp, 9300/tcp   cocky_spence

$ docker stop e931ab24dedc
e931ab24dedc

$ docker run -dp 9200:9200 --net foodtrucks --name es elasticsearch
2c0b96f9b8030f038e40abea44c2d17b0a8edda1354a08166c33e6d351d0c651

$ docker network inspect foodtrucks
[
    {
        "Name": "foodtrucks",
        "Id": "1a3386375797001999732cb4c4e97b88172d983b08cd0addfcb161eed0c18d89",
        "Scope": "local",
        "Driver": "bridge",
        "IPAM": {
            "Driver": "default",
            "Config": [
                {}
            ]
        },
        "Containers": {
            "2c0b96f9b8030f038e40abea44c2d17b0a8edda1354a08166c33e6d351d0c651": {
                "EndpointID": "15eabc7989ef78952fb577d0013243dae5199e8f5c55f1661606077d5b78e72a",
                "MacAddress": "02:42:ac:12:00:02",
                "IPv4Address": "172.18.0.2/16",
                "IPv6Address": ""
            }
        },
        "Options": {}
    }
]

Мы сделали то же, что и раньше, но на этот раз дали контейнеру название es. Перед тем, как запускать контейнер с приложением, давайте проверим что происходит, когда запуск происходит в сети.

$ docker run -it --rm --net foodtrucks prakhar1989/foodtrucks-web bash
root@53af252b771a:/opt/flask-app# cat /etc/hosts
172.18.0.3  53af252b771a
127.0.0.1   localhost
::1 localhost ip6-localhost ip6-loopback
fe00::0 ip6-localnet
ff00::0 ip6-mcastprefix
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters
172.18.0.2  es
172.18.0.2  es.foodtrucks

root@53af252b771a:/opt/flask-app# curl es:9200
bash: curl: command not found
root@53af252b771a:/opt/flask-app# apt-get -yqq install curl
root@53af252b771a:/opt/flask-app# curl es:9200
{
  "name" : "Doctor Leery",
  "cluster_name" : "elasticsearch",
  "version" : {
    "number" : "2.1.1",
    "build_hash" : "40e2c53a6b6c2972b3d13846e450e66f4375bd71",
    "build_timestamp" : "2015-12-15T13:05:55Z",
    "build_snapshot" : false,
    "lucene_version" : "5.3.1"
  },
  "tagline" : "You Know, for Search"
}
root@53af252b771a:/opt/flask-app# ls
app.py  node_modules  package.json  requirements.txt  static  templates  webpack.config.js
root@53af252b771a:/opt/flask-app# python app.py
Index not found...
Loading data in elasticsearch ...
Total trucks loaded:  733
 * Running on http://0.0.0.0:5000/ (Press CTRL+C to quit)
root@53af252b771a:/opt/flask-app# exit

Ура! Работает! Магическим образом Докер внес нужные правки в файл /etc/hosts, и поэтому es:9200 можно использовать в приложении — этот адрес корректно направляет запросы в контейнер ES. Отлично! Давайте теперь запустим Flask-контейнер по-настоящему:

$ docker run -d --net foodtrucks -p 5000:5000 --name foodtrucks-web prakhar1989/foodtrucks-web
2a1b77e066e646686f669bab4759ec1611db359362a031667cacbe45c3ddb413

$ docker ps
CONTAINER ID        IMAGE                        COMMAND                  CREATED             STATUS              PORTS                              NAMES
2a1b77e066e6        prakhar1989/foodtrucks-web   "python ./app.py"        2 seconds ago       Up 1 seconds        0.0.0.0:5000->5000/tcp             foodtrucks-web
2c0b96f9b803        elasticsearch                "/docker-entrypoint.s"   21 minutes ago      Up 21 minutes       0.0.0.0:9200->9200/tcp, 9300/tcp   es

$ curl -I 0.0.0.0:5000
HTTP/1.0 200 OK
Content-Type: text/html; charset=utf-8
Content-Length: 3697
Server: Werkzeug/0.11.2 Python/2.7.6
Date: Sun, 10 Jan 2016 23:58:53 GMT

Зайдите на http://0.0.0.0:5000, и увидите приложение в работе. Опять же, может показаться, что было много работы, но на самом деле мы ввели всего 4 команды чтобы с нуля дойти до работающего приложения. Я собрал эти команды в bash-скрипт.

#!/bin/bash

# build the flask container
docker build -t prakhar1989/foodtrucks-web .

# create the network
docker network create foodtrucks

# start the ES container
docker run -d --net foodtrucks -p 9200:9200 -p 9300:9300 --name es elasticsearch

# start the flask app container
docker run -d --net foodtrucks -p 5000:5000 --name foodtrucks-web prakhar1989/foodtrucks-web

Теперь представьте, что хотите поделиться приложением с другом. Или хотите запустить на сервере, где установлен Докер. Можно запустить всю систему с помощью одной команды!

$ git clone https://github.com/prakhar1989/FoodTrucks
$ cd FoodTrucks
$ ./setup-docker.sh

Вот и все! По-моему, это невероятно крутой и мощный способ распространять и запускать приложения!

Docker Links

Перед тем, как завершить этот раздел, стоит отметить, что docker network это относительно новая фича, она входит в релиз Docker 1.9 .

До того, как появился network, ссылки были допустимым способом настройки взаимодействия между контейнерами. В соответствии с официальной документацией, linking вскоре будет переведены в статус deprecated. Если вам попадется туториал или статья, где используется link для соединения контейнеров, то просто не забывайте использовать вместо этого network (на момент публикации перевода links является legacy, — прим. пер.)

3.3 Docker Compose

До этого момента мы изучали клиент Докера. Но в экосистеме Докера есть несколько других инструментов с открытым исходным кодом, которые хорошо взаимодействуют с Докером. Некоторые из них это:

  1. Docker Machine позволяет создавать Докер-хосты на своем компьютере, облачном провайдере или внутри дата-центра.
  2. Docker Compose — инструмент для определения и запуска много-контейнерных приложений.
  3. Docker Swarm — нативное решение для кластеризации.

В этом разделе мы поговорим об одном из этих инструментов — Docker Compose, и узнаем, как он может упростить работу с несколькими контейнерами.

У Docker Compose довольно интересная предыстория. Примерно два года назад компания OrchardUp запустила инструмент под названием Fig. Идея была в том, чтобы создавать изолированные рабочие окружения с помощью Докера. Проект очень хорошо восприняли на Hacker News — я смутно помню, что читал о нем, но не особо понял его смысла.

Первый комментарий на самом деле неплохо объясняет, зачем нужен Fig и что он делает:

На самом деле, смысл Докера в следующем: запускать процессы. Сегодня у Докера есть неплохое API для запуска процессов: расшаренные между контейнерами (иными словами, запущенными образами) разделы или директории (shared volumes), перенаправление портов с хост-машины в контейнер, вывод логов, и так далее. Но больше ничего: Докер сейчас работает только на уровне процессов.
Не смотря на то, что в нем содержатся некоторые возможности оркестрации нескольких контейнеров для создания единого «приложения», в Докере нет ничего, что помогало бы с управлением такими группами контейнеров как одной сущностью. И вот зачем нужен инструмент вроде Fig: чтобы обращаться с группой контейнеров как с единой сущностью. Чтобы думать о «запуске приложений» (иными словами, «запуске оркестрированного кластера контейнеров») вместо «запуска контейнеров».

Оказалось, что многие пользователи Докера согласны с такими мыслями. Постепенно, Fig набрал популярность, Docker Inc. заметили, купили компанию и назвали проект Docker Compose.

Итак, зачем используется Compose? Это инструмент для простого определения и запуска многоконтейнерных Докер-приложений. В нем есть файл docker-compose.yml, и с его помощью можно одной командой поднять приложение с набором сервисов.

Давайте посмотрим, сможем ли мы создать файл docker-compose.yml для нашего приложения SF-Foodtrucks и проверим, способен ли он на то, что обещает.

Но вначале нужно установить Docker Compose. Есть у вас Windows или Mac, то Docker Compose уже установлен — он идет в комплекте с Docker Toolbox. На Linux можно установить Docker Compose следуя простым инструкциям на сайте документации. Compose написан на Python, поэтому можно сделать просто pip install docker-compose. Проверить работоспособность так:

$ docker-compose version
docker-compose version 1.7.1, build 0a9ab35
docker-py version: 1.8.1
CPython version: 2.7.9
OpenSSL version: OpenSSL 1.0.1j 15 Oct 2014

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

version: "2"
services:
  es:
    image: elasticsearch
  web:
    image: prakhar1989/foodtrucks-web
    command: python app.py
    ports:
      - "5000:5000"
    volumes:
      - .:/code

      

Давайте я разберу это подробнее. На родительском уровне мы задали название неймспейса для наших сервисов: es и web. К каждому сервису можно добавить дополнительные параметры, среди которых image — обязательный. Для es мы указываем доступный на Docker Hub образ elasticsearch. Для Flask-приложения — тот образ, который мы создали самостоятельно в начале этого раздела.

С помощью других параметров вроде command и ports можно предоставить информацию о контейнере. volumes отвечает за локацию монтирования, где будет находиться код в контейнере web. Это опциональный параметр, он полезен, если нужно обращаться к логам и так далее. Подробнее о параметрах и возможных значениях можно прочитать в документации.

Замечание: Нужно находиться в директории с файлом docker-compose.yml чтобы запускать большую часть команд Compose.

Отлично! Файл готов, давайте посмотрим на docker-compose в действии. Но вначале нужно удостовериться, что порты свободны. Так что если у вас запущены контейнеры Flask и ES, то пора их остановить:

$ docker stop $(docker ps -q)
39a2f5df14ef
2a1b77e066e6

Теперь можно запускать docker-compose. Перейдите в директорию с приложением Foodtrucks и выполните команду docker-compose up.

$ docker-compose up
Creating network "foodtrucks_default" with the default driver
Creating foodtrucks_es_1
Creating foodtrucks_web_1
Attaching to foodtrucks_es_1, foodtrucks_web_1
es_1  | [2016-01-11 03:43:50,300][INFO ][node                     ] [Comet] version[2.1.1], pid[1], build[40e2c53/2015-12-15T13:05:55Z]
es_1  | [2016-01-11 03:43:50,307][INFO ][node                     ] [Comet] initializing ...
es_1  | [2016-01-11 03:43:50,366][INFO ][plugins                  ] [Comet] loaded [], sites []
es_1  | [2016-01-11 03:43:50,421][INFO ][env                      ] [Comet] using [1] data paths, mounts [[/usr/share/elasticsearch/data (/dev/sda1)]], net usable_space [16gb], net total_space [18.1gb], spins? [possibly], types [ext4]
es_1  | [2016-01-11 03:43:52,626][INFO ][node                     ] [Comet] initialized
es_1  | [2016-01-11 03:43:52,632][INFO ][node                     ] [Comet] starting ...
es_1  | [2016-01-11 03:43:52,703][WARN ][common.network           ] [Comet] publish address: {0.0.0.0} is a wildcard address, falling back to first non-loopback: {172.17.0.2}
es_1  | [2016-01-11 03:43:52,704][INFO ][transport                ] [Comet] publish_address {172.17.0.2:9300}, bound_addresses {[::]:9300}
es_1  | [2016-01-11 03:43:52,721][INFO ][discovery                ] [Comet] elasticsearch/cEk4s7pdQ-evRc9MqS2wqw
es_1  | [2016-01-11 03:43:55,785][INFO ][cluster.service          ] [Comet] new_master {Comet}{cEk4s7pdQ-evRc9MqS2wqw}{172.17.0.2}{172.17.0.2:9300}, reason: zen-disco-join(elected_as_master, [0] joins received)
es_1  | [2016-01-11 03:43:55,818][WARN ][common.network           ] [Comet] publish address: {0.0.0.0} is a wildcard address, falling back to first non-loopback: {172.17.0.2}
es_1  | [2016-01-11 03:43:55,819][INFO ][http                     ] [Comet] publish_address {172.17.0.2:9200}, bound_addresses {[::]:9200}
es_1  | [2016-01-11 03:43:55,819][INFO ][node                     ] [Comet] started
es_1  | [2016-01-11 03:43:55,826][INFO ][gateway                  ] [Comet] recovered [0] indices into cluster_state
es_1  | [2016-01-11 03:44:01,825][INFO ][cluster.metadata         ] [Comet] [sfdata] creating index, cause [auto(index api)], templates [], shards [5]/[1], mappings [truck]
es_1  | [2016-01-11 03:44:02,373][INFO ][cluster.metadata         ] [Comet] [sfdata] update_mapping [truck]
es_1  | [2016-01-11 03:44:02,510][INFO ][cluster.metadata         ] [Comet] [sfdata] update_mapping [truck]
es_1  | [2016-01-11 03:44:02,593][INFO ][cluster.metadata         ] [Comet] [sfdata] update_mapping [truck]
es_1  | [2016-01-11 03:44:02,708][INFO ][cluster.metadata         ] [Comet] [sfdata] update_mapping [truck]
es_1  | [2016-01-11 03:44:03,047][INFO ][cluster.metadata         ] [Comet] [sfdata] update_mapping [truck]
web_1 |  * Running on http://0.0.0.0:5000/ (Press CTRL+C to quit)

Перейдите по IP чтобы увидеть приложение. Круто, да? Всего лишь пара строк конфигурации и несколько Докер-контейнеров работают в унисон. Давайте остановим сервисы и перезапустим в detached mode:

web_1 |  * Running on http://0.0.0.0:5000/ (Press CTRL+C to quit)
Killing foodtrucks_web_1 ... done
Killing foodtrucks_es_1 ... done

$ docker-compose up -d
Starting foodtrucks_es_1
Starting foodtrucks_web_1

$ docker-compose ps
      Name                    Command               State           Ports
----------------------------------------------------------------------------------
foodtrucks_es_1    /docker-entrypoint.sh elas ...   Up      9200/tcp, 9300/tcp
foodtrucks_web_1   python app.py                    Up      0.0.0.0:5000->5000/tcp

Не удивительно, но оба контейнера успешно запущены. Откуда берутся имена? Их Compose придумал сам. Но что насчет сети? Его Compose тоже делаем сам? Хороший вопрос, давайте выясним.

Для начала, остановим запущенные сервисы. Их всегда можно вернуть одной командой:

$ docker-compose stop
Stopping foodtrucks_web_1 ... done
Stopping foodtrucks_es_1 ... done

Заодно, давайте удалим сеть foodtrucks, которую создали в прошлый раз. Эта сеть нам не потребуется, потому что Compose автоматически сделает все за нас.

$ docker network rm foodtrucks
$ docker network ls
NETWORK ID          NAME                DRIVER
4eec273c054e        bridge              bridge
9347ae8783bd        none                null
54df57d7f493        host                host

Класс! Теперь в этом чистом состоянии можно проверить, способен ли Compose на волшебство.

$ docker-compose up -d
Recreating foodtrucks_es_1
Recreating foodtrucks_web_1
$ docker ps
CONTAINER ID        IMAGE                        COMMAND                  CREATED             STATUS              PORTS                    NAMES
f50bb33a3242        prakhar1989/foodtrucks-web   "python app.py"          14 seconds ago      Up 13 seconds       0.0.0.0:5000->5000/tcp   foodtrucks_web_1
e299ceeb4caa        elasticsearch                "/docker-entrypoint.s"   14 seconds ago      Up 14 seconds       9200/tcp, 9300/tcp       foodtrucks_es_1

Пока все хорошо. Проверим, создались ли какие-нибудь сети:

$ docker network ls
NETWORK ID          NAME                 DRIVER
0c8b474a9241        bridge               bridge              
293a141faac3        foodtrucks_default   bridge              
b44db703cd69        host                 host                
0474c9517805        none                 null  

Видно, что Compose самостоятельно создал сеть foodtrucks_default и подсоединил оба сервиса в эту сеть, так, чтобы они могли общаться друг с другом. Каждый контейнер для сервиса подключен к сети, и оба контейнера доступны другим контейнерам в сети. Они доступны по hostname, который совпадает с названием контейнера. Давайте проверим, находится ли эта информация в /etc/hosts.

$ docker ps
CONTAINER ID        IMAGE                        COMMAND                  CREATED             STATUS              PORTS                    NAMES
bb72dcebd379        prakhar1989/foodtrucks-web   "python app.py"          20 hours ago        Up 19 hours         0.0.0.0:5000->5000/tcp   foodtrucks_web_1
3338fc79be4b        elasticsearch                "/docker-entrypoint.s"   20 hours ago        Up 19 hours         9200/tcp, 9300/tcp       foodtrucks_es_1

$ docker exec -it bb72dcebd379 bash
root@bb72dcebd379:/opt/flask-app# cat /etc/hosts
127.0.0.1   localhost
::1 localhost ip6-localhost ip6-loopback
fe00::0 ip6-localnet
ff00::0 ip6-mcastprefix
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters
172.18.0.2  bb72dcebd379

Упс! Оказывается, файл понятия не имеет о es. Как же наше приложение работает? Давайте попингуем его по названию хоста:

root@bb72dcebd379:/opt/flask-app# ping es
PING es (172.18.0.3) 56(84) bytes of data.
64 bytes from foodtrucks_es_1.foodtrucks_default (172.18.0.3): icmp_seq=1 ttl=64 time=0.049 ms
64 bytes from foodtrucks_es_1.foodtrucks_default (172.18.0.3): icmp_seq=2 ttl=64 time=0.064 ms
^C
--- es ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 999ms
rtt min/avg/max/mdev = 0.049/0.056/0.064/0.010 ms

Вуаля! Работает! Каким-то магическим образом контейнер смог сделать пинг хоста es. Оказывается, Docker 1.10 добавили новую сетевую систему, которая производит обнаружение сервисов через DNS-сервер. Если интересно, то почитайте подробнее о предложении и release notes.

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

Надеюсь, я продемонстрировал как на самом деле просто управлять многоконтейнерной средой с Compose. В последнем разделе мы задеплоим все на AWS!

3.4 AWS Elastic Container Service

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

Если вы дочитали до этого места, то скорее всего убедились, что Docker — довольно крутая технология. И вы не одиноки. Облачные провайдеры заметили взрывной рост популярности Докера и стали добавлять поддержку в свои сервисы. Сегодня, Докер-приложения можно деплоить на AWS, Azure,Rackspace, DigitalOcean и много других. Мы уже умеем деплоить приложение с одним контейнером на Elastic Beanstalk, а в этом разделе мы изучим AWS Elastic Container Service (или ECS).

AWS ECS — это масштабируемый и гибкий сервис по управлению контейнерами, и он поддерживает Докер. С его помощью можно управлять кластером на EC2 через простой API. В Beanstalk были нормальные настройки по умолчанию, но ECS позволяет настроить каждый аспект окружения по вашим потребностям. По этой причине ECS — не самый простой инструмент в начале пути.

К счастью, у ECS есть удобный инструмент командной строки (CLI) с поддержкой Docker Compose и автоматической провизией на ECS! Так как у нас уже есть рабочий файл docker-compose.yml, настройка и запуск на AWS должна быть достаточно легкой. Начнем!

Вначале нужно установить CLI. На момент написания этого пособия CLI-утилита не доступна на Windows. Инструкции по установке CLI на Mac и Linux хорошо описаны на сайте с официальной документацией. Установите утилиту, а потом проверьте ее работоспособность так:

$ ecs-cli --version
ecs-cli version 0.1.0 (*cbdc2d5)

Первый шаг — задать пару ключей для авторизации на инстансах. Зайдите на страницу EC2 Console и создайте новый keypair. Скачайте файл и держите его в безопасном месте. Еще один момент — имя региона. Я назвал свой ключ ecs и указал регион us-east-1. Я продолжу повествование с этим допущением.

keypair.png

Теперь настройте CLI:

$ ecs-cli configure --region us-east-1 --cluster foodtrucks
INFO[0000] Saved ECS CLI configuration for cluster (foodtrucks)

Команда configure с именем региона, в котором хотим разместить наш кластер, и название кластера. Нужно указать тот же регион, что использовался прри создании ключей. Если у вас не настроен AWS CLI, то следуйте руководству, которое подробно описывает все шаги.

Следующий шаг позволяет утилите создавать шаблон CloudFormation.

$ ecs-cli up --keypair ecs --capability-iam --size 2 --instance-type t2.micro
INFO[0000] Created cluster                               cluster=foodtrucks
INFO[0001] Waiting for your cluster resources to be created
INFO[0001] Cloudformation stack status                   stackStatus=CREATE_IN_PROGRESS
INFO[0061] Cloudformation stack status                   stackStatus=CREATE_IN_PROGRESS
INFO[0122] Cloudformation stack status                   stackStatus=CREATE_IN_PROGRESS
INFO[0182] Cloudformation stack status                   stackStatus=CREATE_IN_PROGRESS
INFO[0242] Cloudformation stack status                   stackStatus=CREATE_IN_PROGRESS

Здесь мы указываем названия ключей, которые мы скачали (в моем случае ecs), количество инстансов (--size) и тип инстансов, на которых хотим запускать контейнеры. Флаг --capability-iam говорит утилите, что мы понимаем, что эта команда может создать ресурсы IAM.

В последнем шаге мы используем файл docker-compose.yml. Требуется небольшое изменение, так что вместо модификации файла, давайте сделаем копию и назовем ее aws-compose.yml. Содержание этого файла (после изменений):

es:
  image: elasticsearch
  cpu_shares: 100
  mem_limit: 262144000
web:
  image: prakhar1989/foodtrucks-web
  cpu_shares: 100
  mem_limit: 262144000
  ports:
    - "80:5000"
  links:
    - es

    

Единственные отличия от оригинального файла docker-compose.yml это параметры mem_limit и cpu_shares для каждого контейнера.

Также, мы убрали version и services, так как AWS еще не поддерживает версию 2 файлового формата Compose. Так как наше приложение будет работать на инстансах типа t2.micro, мы задали 250 мегабайт памяти. Теперь нам нужно опубликовать образ на Docker Hub. На момент написания этого пособия, ecs-cli не поддерживает команду build. Но Docker Compose поддерживает ее без проблем.

$ docker push prakhar1989/foodtrucks-web

Красота! Давайте запустим финальную команду, которая произведет деплой на ECS!

$ ecs-cli compose --file aws-compose.yml up
INFO[0000] Using ECS task definition                     TaskDefinition=ecscompose-foodtrucks:2
INFO[0000] Starting container...                         container=845e2368-170d-44a7-bf9f-84c7fcd9ae29/es
INFO[0000] Starting container...                         container=845e2368-170d-44a7-bf9f-84c7fcd9ae29/web
INFO[0000] Describe ECS container status                 container=845e2368-170d-44a7-bf9f-84c7fcd9ae29/web desiredStatus=RUNNING lastStatus=PENDING taskDefinition=ecscompose-foodtrucks:2
INFO[0000] Describe ECS container status                 container=845e2368-170d-44a7-bf9f-84c7fcd9ae29/es desiredStatus=RUNNING lastStatus=PENDING taskDefinition=ecscompose-foodtrucks:2
INFO[0036] Describe ECS container status                 container=845e2368-170d-44a7-bf9f-84c7fcd9ae29/es desiredStatus=RUNNING lastStatus=PENDING taskDefinition=ecscompose-foodtrucks:2
INFO[0048] Describe ECS container status                 container=845e2368-170d-44a7-bf9f-84c7fcd9ae29/web desiredStatus=RUNNING lastStatus=PENDING taskDefinition=ecscompose-foodtrucks:2
INFO[0048] Describe ECS container status                 container=845e2368-170d-44a7-bf9f-84c7fcd9ae29/es desiredStatus=RUNNING lastStatus=PENDING taskDefinition=ecscompose-foodtrucks:2
INFO[0060] Started container...                          container=845e2368-170d-44a7-bf9f-84c7fcd9ae29/web desiredStatus=RUNNING lastStatus=RUNNING taskDefinition=ecscompose-foodtrucks:2
INFO[0060] Started container...                          container=845e2368-170d-44a7-bf9f-84c7fcd9ae29/es desiredStatus=RUNNING lastStatus=RUNNING taskDefinition=ecscompose-foodtrucks:2

То, что вывод похож на вывод Docker Compose — не совпадение. Аргумент --file используется для переопределения файла по умолчанию (docker-compose.yml). Если все прошло хорошо, то вы увидите строку desiredStatus=RUNNING lastStatus=RUNNING в самом конце.

Круто! Теперь приложение запущено. Как к нему обратиться?

ecs-cli ps
Name                                      State    Ports                     TaskDefinition
845e2368-170d-44a7-bf9f-84c7fcd9ae29/web  RUNNING  54.86.14.14:80->5000/tcp  ecscompose-foodtrucks:2
845e2368-170d-44a7-bf9f-84c7fcd9ae29/es   RUNNING                            ecscompose-foodtrucks:2

Откройте http://54.86.14.14 в браузере, и увидите Food Trucks во всей своей желто-черной красе! Заодно, давайте взглянем на консоль AWS ECS.

ECS cluster

ECS cluster

Видно, что был создан ECS-кластер ‘foodtrucks’, и в нем выполняется одна задача с двумя инстансами. Советую поковыряться в этой консоли и изучить разные ее части и опции.

Вот и все. Всего несколько команд — и приложение работает на AWS!

4.0 Заключение

Мы подошли к концу. После длинного, изматывающего, но интересного пособия вы готовы захватить мир контейнеров! Если вы следовали пособию до самого конца, то можете заслуженно гордиться собой. Вы научились устанавливать Докер, запускать свои контейнеры, запускать статические и динамические веб-сайты и, самое главное, получили опыт деплоя приложений в облако.

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

4.1 Следующие шаги

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

Ниже — список дополнительных полезных ресурсов. Советую использовать Докер в вашем следующем проекте. И не забывайте — практика приводит к совершенству.

Дополнительные ресурсы

  • Awesome Docker
  • Hello Docker Workshop
  • Building a microservice with Node.js and Docker
  • Why Docker
  • Docker Weekly and archives
  • Codeship Blog

Удачи, юный падаван!

4.2 Фидбек автору

Теперь моя очередь задавать вопросы. Вам понравилось пособие? Оно показалось вам запутанным, или вам удалось научиться чему-то?

Напишите мне (автору оригинального пособия, — прим. пер.) напрямую на prakhar@prakhar.me или просто создайте issue. Я есть в Твиттере, так что если хотите, то можете писать туда.

(Автор оригинального пособия говорит по-английски, — прим. пер.).

Буду рад услышать ваши отзывы. Не стесняйтесь предлагать улучшения или указывать на мои ошибки. Я хочу, чтобы это пособие стало одним из лучших стартовых руководств в интернете. У меня не получится это без вашей помощи.

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

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

Когда я наконец-то понял все тонкости работы с Docker (на полное изучение которого ушло несколько месяцев), и начал правильно применять его при разработке (а он как раз и нужен для разработки, в большей степени), то почувствовал, как будто обрёл какую-то сверхспособоность. Смотря на свой опыт изучения Докера, я понял, что мне есть что рассказать, и чем поделиться. В этой статье я постарался создать максимально понятную для новичков инструкцию, благодаря которой вы сможете полностью изучить Docker за 30 минут. Я долго думал о том, чтобы написать туториал, и наконец-то осилил эту задачу, и, как мне кажется, получилось неплохо :)

Эта инструкция так же подходит для тех, кто не имеет никаких знаний, или опыта работы с докером, или аналогичным программным обеспечением. Вы получите все важные знания, необходимые для работы. Статья построена по принципу от простого к сложному. В итоге статьи вы будете чётко понимать, что такое Docker, зачем нужен, как с ним работать, и применять его для разработки: создавать окружение, необходимое для создания вашего приложения.

Эта статья, в больше мере, нацелена на получение практических знаний, и только немного теории, построенной на аналогиях из жизни. Потому, эта статья имеет окрас веселья и лайтовости, в большей мере, чем супер-конкретики и теоретических нюансов.

В этом туториале я показываю всё на примере ОС Windows 10, делая все команды из консоли винды, и демонстрируя процесс установки Docker на Windows 10. Но, все команды будут работать аналогично и на Linux и Mac. Эта статья — это продолжение ряда статей, посвященных настройке рабочего окружения. В прошлой статье мы рассматривали работу с Vagrant, что не менее интересно, чем Docker. И Docker и Vagrant преследуют цель — упростить жизнь разработчикам, но с Докером открывается больше возможностей.

Так же, прошу заметить, если вы используете Vagrant, и решите установить Docker, то Vagrant перестанет работать. Такая жизнь, но с этим можно смириться, тем более, субъективно, Docker круче ^^.

Что вы узнаете из этой статьи

  • Как работает Docker?
  • Как установить Docker на Windows?
  • Что такое Docker Image (образ)?
  • Что такое Docker контейнер?
  • Что такое Docker Volumes?
  • Что такое Dockerfile?
  • Как пробрасывать локальную папку в контейнер Докера (монтирование папки)?
  • Как работают и пробрасываются Docker порты?
  • Слои Docker образа, особенности создания образов.
  • Что такое Docker-compose?
  • Что такое микросервисы и микросервисная архитектура?

Что такое Docker

О том, как появился Docker:

Docker — это программное обеспечение, которое начинало с того, что зародилось в одной компании, как внутренний проект platform-as-a-service в компании dotCloud.

В процессе развития Докера, он вырос из масштабов внутреннего проекта, стал доступен для широких масс, и затмил своей популярностью своего родителя dotCloud, из-за чего было принято решение создать новую отдельную компанию под названием Docker Incorporated. Направление новосозданной компании было только в разработке Докера, и развитию его экосистемы.

На сайте Докера можно найти статью, в которой подробно рассказывается, что такое Docker. Из их слов — это стандартизированное ПО для разработки и развёртывания проектов.

Но, что это на самом деле значит?

Давайте на секунду забудем про Докер, и вспомним про такую ностальгическую штуку, как GameBoy Color:game-boy-coloe

Если вы помните, игры для этой приставки поставлялись в виде картриджей:cartrige

И я уверен в том, что производители видео игр пользуются успехом из-за своей простоты:

  1. Когда ты хочешь поиграть, ты просто вставляешь картридж в приставку, и игра сразу же работает.
  2. Ты можешь поделиться своей игрой с друзьями, передав всего лишь картридж, который они вставят в приставку, и сразу же смогут играть.

Docker следует похожему принципу — позволяет запускать своё ПО настолько просто, что это соизмеримо с вставкой картриджа и нажатием кнопки ON на приставке.

Это основная суть, почему Docker настолько полезен — теперь кто угодно, у кого установлен Docker может запустить ваше приложение, выполнив для этого всего несколько команд.

Раньше, вы, создавая приложения, к примеру на PHP, устанавливали локально PHP, MySql, возможно, NodeJs, при этом устанавливая зависимости в виде нужных расширений и библиотек. И, в случае передачи вашего скрипта какому-то знакомому, ему требовалось настраивать аналогичное окружение, аналогичных версий, иметь аналогичные расширения и конфигурацию, чтобы успешно запустить ваше приложение.

Сейчас же, при использовании Докера, такой проблемы не возникнет впринципе. Теперь вам достаточно иметь установленную программу Docker, которая по одной вашей команде установит окружение, описанное в конфиге для запуска вашего приложения.

Какое программное обеспечение можно запустить с помощью докера? В техническом плане, Docker чем-то похож на виртуальную машину:

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

Docker позволяет запустить ОС Linux в изолированной среде очень быстро, в течение нескольких минут.

Зачем использовать Docker?

Кошмар при установке ПО, с которым приходится сталкиваться. У вас когда-нибудь было такое, что вы пытаетесь установить ПО на ваш компьютер, а оно отказывается работать? Вы получаете несколько непонятных вам ошибок, из-за которых ничего не запускается. И после нескольких часов гугления, на десятой странице гугла…и на каком-то форуме, до этого неизвестного вам, вы наконец-то находите случайный комментарий, который помогает исправить вашу проблему.

Аналогично, что делает написание PC игр более сложным, чем написание Game Boy игр — это то, что приходится проектировать систему с учётом большого множества существующих PC девайсов и спецификаций. Так как разные компьютеры имеют различные операционные системы, драйвера, процессоры, графические карты, и т.д.
И потому задача разработчика — написать приложение совместимое со всеми популярными системами, является достаточно затруднительной и трудоёмкой.

Docker спасёт нас. Docker, как и Game Boy приставка, берёт стандартизированные части программного обеспечения и запускает их так, как Game Boy запускал бы игру.

В этом случае вы не должны беспокоиться об операционной системе, на которой пользователь будет запускать ваше приложение. Теперь, когда пользователи будут запускать приложение через Docker — конфигурация будет собрана автоматически, и код будет выполняться ВСЕГДА.

Как разработчик, теперь вы не должны волноваться о том, на какой системе будет запущено ваше приложение.
Как пользователь, вам не нужно волноваться о том, что вы скачаете неподходящую версию ПО (нужного для работы программы). В Докере эта программа будет запущена в аналогичных условиях, при которых это приложение было разработано, потому, исключается факт получить какую-то новую, непредвиденную ошибку.

Для пользователя все действия сводятся к принципу подключи и играй.

Установка Docker

Docker доступен для любой из операционных систем: Windows, Linux, Max. Для скачивания установочного файла — перейдите по ссылке и выберите подходящую вам версию. Я же, как и писал ранее, выбираю версию docker для Windows 10.

Docker предоставляет 2 сборки:

  • Community Edition (полностью бесплатная версия)
  • Enterprise Edition (платно). Enterprise Edition содержит в себе дополнительные свистелки-перделки функции, которые, на данном этапе, точно не нужны. Функциональность, которую мы будем использовать совершенно не отличается в этих двух сборках.

После установки потребуется перезагрузка системы, и уже можно начинать полноценно работать с Докером.

Для того, чтобы проверить, запущен ли Docker, откроем командную строку (на Windows 10 — Нажмите кнопку windows, и начните писать командная строка)command-call
Где, напишем команду docker, и в случае успешно работающего докера, получим ответ command-docker
Дальше, нужно удостовериться, что вместе с докером, доступен так же, docker-compose, для этого, выполним команду:

docker-compose (вывод обеих команд будет примерно одинакового содержания).

Если вы используете Linux, то, docker-compose нужно будет устанавливать отдельно по инструкции.

Что такое Docker Image?

Docker образ (он же Docker Image), похож на Game Boy картридж — это просто программное обеспечение. Это стандартизированное программное обеспечение, которое запускается на любой приставке Game Boy. Вы можете дать игру вашему другу, и он сможет просто вставить картридж в приставку, и играть.

Как в случае с картриджами, бывают различные игры, так и Docker имеет различные образы ПО: ubuntu, php (который наследуется от оригинального образа Ubuntu), nodejs, и т.д.

Рассмотрим пример скачивания нашего первого образа.

Для этого, существует команда:
docker pull <IMAGE_NAME>, где <IMAGE_NAME> — имя скачиваемого образа

Зная эту команду, скачаем образ Ubuntu 18.10:

docker pull ubuntu:18.10

docker-pull-ubuntu-18

Эта команда сообщает Докеру о том, что нужно скачать образ Ubuntu 18.10 с Dockerhub.com — основной репозиторий Docker-образов, на котором вы и можете посмотреть весь их список и подобрать нужный образ для вашей программы.

Это как поездка за новым картриджем в магазин, только намного быстрее :).

Теперь, для того, чтобы посмотреть список всех загруженных образов, нужно выполнить:

docker images

docke-images

У вас, как и на скрине, должен появиться только что скачанный образ Ubuntu 18.10.
Как и обсуждалось выше, по поводу маленького размера образов, чистый образ Ubuntu при установке из Docker-образа, весит всего 74 МБ. Не чудо ли?

Проводя аналогии, команда docker images выглядит как коллекция картриджей от приставки, которые у вас есть сейчас:Depositphotos_194136098_xl-2015

Что такое Docker контейнер?

Теперь представьте, что мы обновили нашу приставку с Game Boy на GameCube. Игры хранятся на диске, который предназначен только для чтения самого образа игры. А прочие файлы (сохранения, кеш и т.д.) сохраняются внутри самой приставки, локально.

Так же, как и игра на диске, исходный Docker Image (образ) — неизменяемый.

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

А сам образ игры никак не модифицируется, все файлы, содержащие изменения хранятся где-то локально на приставке.

Depositphotos_194135642_xl-2015

Запуск Docker контейнера соответствует тому, что вы играете в свою Gamecube игру. Docker запускает ваш образ в своей среде, аналогично тому, как Gamecube запускает игру с диска, не модифицируя оригинальный образ, а лишь сохраняя изменения и весь прогресс в какой-то песочнице.

Для запуска контейнера существует команда:

docker run <image> <опциональная команды, которая выполнится внутри контейнера>

Давайте запустим наш первый контейнер Ubuntu:

docker run ubuntu:18.10 echo 'hello from ubuntu'

docker-run

Команда echo 'hello from ubuntu' была выполнена внутри среды Ubuntu. Другими словами, эта команда была выполнена в контейнере ubuntu:18.10.

Теперь выполним команду для проверки списка запущенных контейнеров:

docker ps

docker-ps

Здесь пустота… это потому что docker ps показывает только список контейнеров, которые запущены в данный момент (наш же контейнер выполнил одну команду echo 'hello from ubuntu' и завершил свою работу).

А для того, чтобы посмотреть список всех контейнеров без исключения, нужно добавить флаг -a, выполним:

docker ps -a

docker-ps-a

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

Каждый раз, когда вы будете выполнять команду docker run, будет создаваться новый контейнер, на каждую из выполненных команд.

Выполнение неограниченное количество команда внутри контейнера

Давайте добавим немного интерактивности в наше обучение. Мы можем подключиться к консоли виртуальной ОС (Ubuntu 18.10), и выполнять любое количество команд без завершения работы контейнера, для этого, запустим команду:

docker run -it ubuntu:18.10 /bin/bash

Опция -it вместе с /bin/bash даёт доступ к выполнению команд в терминале внутри контейнера Ubuntu.

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

Узнаём ID контейнера

Иногда является очень полезным узнать ID контейнера, с которым мы работаем. И как раз-таки, при выполнении команды docker run -it <IMAGE> /bin/bash, мы окажемся в терминале, где все команды будут выполняться от имени пользователя root@<containerid>.

Теперь, все команды буду выполняться внутри операционной системы Ubuntu. Попробуем, например, выполнить команду ls, и посмотрим, список директорий, внутри этого образа Ubuntu.docker-ubuntu-ls

Docker контейнер является полностью независимым от системы хоста, из которой он запускался. Как изолированная виртуальная машина. И в ней вы можете производить любые изменения, которые никак не повлияют на основную операционную систему.

Это аналогично тому, как, если бы вы играли в Mario Kart на приставке Gamecube, и неважно, что вы делаете в игре, вы никак не сможете изменить само ядро игры, или изменить информацию, записанную на диске.

Контейнер является полностью независимым и изолированным от основной операционной системы, аналогично виртуальной операционной системе. Вы можете вносить любые изменения внутри виртуалки, и никакие из этих изменений не повлияют на основную операционную систему.

Теперь откройте новое окно терминала (не закрывая и не отключаясь от текущего), и выполните команду docker ps
docker-ps-new-window

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

Теперь вернёмся назад к первому окну терминала (который находится внутри контейнера), и выполним:

mkdir /truedir  #создаст папку truedir
exit #выйдет из контейнера, и вернётся в основную ОС

Выполнив команду exit, контейнер будет остановлен (чтобы убедиться, можете проверить командой docker ps). Теперь, вы так же знаете, как выйти из Docker контейнера.

Теперь, попробуем ещё раз просмотреть список всех контейнеров, и убедимся, что новый контейнер был создан docker ps -adocker-ps--a2

Так же, для того, чтобы запустить ранее созданный контейнер, можно выполнить команду docker start <CONTAINER_ID>,

где CONTAINER_ID — id контейнера, который можно посмотреть, выполнив команду docker ps -a (и увидеть в столбце CONTAINER_ID)

В моём случае, CONTAINER_ID последнего контейнера = 7579c85c8b7e (у вас же, он будет отличаться)

Запустим контейнер командой:

docker start 7579c85c8b7e    #ваш CONTAINER_ID
docker ps
docker exec -it 7579c85c8b7e /bin/bash #ваш CONTAINER_ID

И теперь, если внутри контейнера выполнить команду ls, то можно увидеть, что ранее созданная папка truedir существует в этом контейнереdocker-exex-truedir

Команда exec позволяет выполнить команду внутри запущенного контейнера. В нашем случае, мы выполнили /bin/bash, что позволило нам подключиться к терминалу внутри контейнера.

Для выхода, как обычно, выполним exit.

Теперь остановим и удалим Docker контейнеры командами:
docker stop <CONTAINER_ID>
docker rm <CONTAINER_ID>

docker ps a   # просмотрим список активных контейнеров 
docker stop aa1463167766   # остановим активный контейнер
docker rm aa1463167766     # удалим контейнер
docker rm bb597feb7fbe     # удалим второй контейнер

В основном, нам не нужно, чтобы в системе плодилось большое количество контейнеров. Потому, команду docker run очень часто запускают с дополнительным флагом —rm, который удаляет запущенный контейнер после работы:

docker run -it --rm ubuntu:18.10 /bin/bash

Что такое DockerFile?

Docker позволяет вам делиться с другими средой, в которой ваш код запускался и помогает в её простом воссоздании на других машинах.

Dockerfile — это обычный конфигурационный файл, описывающий пошаговое создание среды вашего приложения. В этом файле подробно описывается, какие команды будут выполнены, какие образы задействованы, и какие настройки будут применены. А движок Docker-а при запуске уже распарсит этот файл (именуемый как Dockerfile), и создаст из него соответствующий образ (Image), который был описан.

К примеру, если вы разрабатывали приложение на php7.2, и использовали ElasticSearch 9 версии, и сохранили это в Dockerfile-е, то другие пользователи, которые запустят образ используя ваш Dockerfile, получат ту же среду с php7.2 и ElasticSearch 9.

С Dockerfile вы сможете подробно описать инструкцию, по которой будет воссоздано конкретное состояние. И делается это довольно-таки просто и интуитивно понятно.

Представьте, что вы играете в покемонов

Вы пытаетесь пройти первый уровень, но безрезультатно. И я, как ваш друг, хочу с этим помочь. У меня есть 2 таблетки варианта:

  1. Я дам вам файл сохранений, в котором игра ничинается со второго уровня. Всё что вам нужно — это загрузить файл.
  2. Я могу написать инструкцию, в которой опишу шаг за шагом процесс прохождения уровня. Это как рецепт, которому нужно будет следовать в точности, как описано. Эта инструкция могла бы выглядеть как-то так:

Инструкция прохождения первого уровня

  • Выбрать покемона Squirtle
  • Направляйтесь к лесу, к северу от города
  • Тренируйтесь, пока покемон не достигнет 10 уровня
  • Направляйтесь в Оловянный город
  • Подойдите к боссу, и победите его заклинанием Watergun

Что является более полезным? Я склоняюсь, что это второй вариант. Потому что он демонстрирует, как добиться желаемого состояния. Это не просто чёрный ящик, который переносит игру на второй уровень.

С докером вы так же имеете два варианта при создании образа:

  1. Вы можете запаковать ваш контейнер, создать из него образ (аналогично тому, что вы запишите на диск новую игру с собственными модификациями). Это похоже на способ, когда вы делитесь сохранениями напрямую.
  2. Или же, можно описать Dockerfile — подробную инструкцию, которая приведёт среду к нужному состоянию.

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

Пришло время попрактиковаться на реальном примере. Для начала, создадим файл cli.php в корне проекта с содержимым:

<?php
$n = $i = 5;

while ($i--) {
    echo str_repeat(' ', $i).str_repeat('* ', $n - $i)."n";
}

И файл под названием Dockerfile, с содержимым:

FROM php:7.2-cli
COPY cli.php /cli.php
RUN chmod +x /cli.php
CMD php /cli.php

Имена команд в Dockerfile (выделенные красным) — это синтаксис разметки Dockerfile. Эти команды означают:

  • FROM — это как буд-то вы выбираете движок для вашей игры (Unity, Unreal, CryEngine). Хоть вы и могли бы начать писать движок с нуля, но больше смысла было бы в использовании готового. Можно было бы использовать, к примеру, ubuntu:18.10, в нашем коде используется образ php:7.2-cli, потому весь код будет запускаться внутри образа с предустановленным php 7.2-cli.
  • COPY — Копирует файл с основной системы в контейнер (копируем файл cli.php внутрь контейнера, с одноимённым названием)
  • RUN — Выполнение shell-команды из терминала контейнера (в текущем случае, присвоим права на выполнение скрипта /cli.php
  • CMD — Выполняет эту команду каждый раз, при новом запуске контейнера

Для просмотра полного списка команд можете перейти по ссылке

При написании Dockerfile, начинать следует с наиболее актуального существующего образа, дополняя его в соответствии с потребностями вашего приложения.
К примеру, мы могли не использовать образ php:7.2-cli, а могли взять ubuntu:18.10, последовательно выполняя команды в RUN одна за одной, устанавливая нужное ПО. Однако, в этом мало смысла, когда уже есть готовые сборки.

Для создания образа из Dockerfile нужно выполнить:
docker build <DOCKERFILE_PATH> --tag <IMAGE_NAME>
<DOCKERFILE_PATH> — путь к файлу Dockerfile (. — текущая директория),
<IMAGE_NAME> — имя, под которым образ будет создан

Выполним:

docker build . --tag pyramid

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

build-image-1

После того, как команда выполнилась, мы можем обращаться к образу по его имени, которое было указано в <IMAGE_NAME>, проверим список образов: docker images
images-piramyd

Теперь, запустим контейнер из нашего образа командой docker run pyramid
run-pyramid

Круто! Shell скрипт был успешно скопирован, и выполнен благодаря указанному в Dockerfile параметру CMD.

Сначала мы скопировали файл cli.php в Docker образ, который создался с помощью Dockerfile. Для того, чтобы удостовериться в том, что файл действительно был проброшен внутрь контейнера, можно выполнить команду docker run pyramid ls, которая в списке файлов покажет и cli.php.

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

Для этого, отредактируем файл cli.php, и изменим, чтобы количество аргументов принималось из командной строки. Отредактируем вторую строку на:

$n = $i = $argv[1] ?? 5; //а было $n = $i = 5
// это значит, что мы принимаем аргумент из консоли, а если он не получен, то используем по-умолчанию 5

После чего, пересоберём образ: docker build . --tag pyramid
И запустим контейнер: docker run pyramid php /cli.php 9, получив вывод ёлки пирамиды в 9 строк
cli_arg

Почему это работает?
Когда контейнер запускается, вы можете переопределить команду записанную в Dockerfile в поле CMD.

Наша оригинальная CMD команда, записанная в Dockerfile php /cli.php — будет переопределена новой php /cli.php 9.
Но, было бы неплохо передавать этот аргумент самому контейнеру, вместо переписывания всей команды. Перепишем так, чтобы вместо команды php /cli.php 7 можно было передавать просто аргумент-число.

Для этого, дополним Dockerfile:

FROM php:7.2-cli
COPY cli.php /cli.php
RUN chmod +x /cli.php
ENTRYPOINT ["php", "/cli.php"]
## аргумент, который передаётся в командную строку
CMD  ["9"]

Мы немного поменяли формат записи. В таком случае, CMD будет добавлена к тому, что выполнится в ENTRYPOINT.

["php", "/cli.php"] на самом деле запускается, как php /cli.php. И, учитывая то, что CMD будет добавлена после выполнения текущей, то итоговая команда будет выглядеть как: php /cli.php 9 — и пользователь сможет переопределить этот аргумент, передавая его в командную строку, во время запуска контейнера.

Теперь, заново пересоберём образ

docker build . --tag pyramid

И запустим контейнер с желаемым аргументом

docker run pyramid 3

result-3

Монтирование локальной директории в Docker-контейнер

Монтирование директории в Docker контейнер — это предоставление доступа контейнеру на чтение содержимого вашей папки из основной операционной системы. Помимо чтения из этой папки, так же, контейнер может её изменять, и такая связь является двусторонней: при изменении файлов в основной ОС изменения будут видны в контейнере, и наоборот.

Когда игра читает файлы сохранений, файловая система Game Cube внедряет их в текущий сеанс игры (представим это, даже если это не так). Игра может изменять файл сохранений, и это изменение отразится на файловой системе Game Cube, т.е. возникает двусторонняя связь.

Монтирование директории в контейнер позволяет ему читать и писать данные в эту директорию, изменяя её состояние.

Для того, чтобы смонтировать папку из основной системы в контейнер, можно воспользоваться командой
docker run -v <DIRECTORY>:<CONTAINER_DIRECTORY> ...,
где DIRECTORY — это путь к папке, которую нужно смонтировать,
CONTAINER_DIRECTORY — путь внутри контейнера.

Только путь к монтируемой папке должен быть прописан полностью: C:projectsdocker-example, или на *nix-системах можно воспользоваться конструкцией $(pwd)

Выполним команду:

docker run -it -v C:projectsdocker-examplecli:/mounted  ubuntu:18.10 /bin/bash
ls
ls mounted
touch mounted/testfile

При выполнении этой команды, указанная папка смонтируется в папку /mounted, внутри файловой системы контейнера, а команда touch mounted/testfile создаст новый файл под названием testfile, который вы можете увидеть из основной ОС.

Теперь вы можете увидеть, что после выполнения этой команды в текущей директории появился новый файл testfile. И это говорит о том, что двусторонняя связь работает — при изменении директории на основной ОС всё отразится на смонтированную папку внутри контейнера, а при изменениях изнутри контейнера всё отразится на основную ОС.

Монтирование папки позволяет вам изменять файлы вашей основной системы прямо во время работы внутри Docker контейнера.

Это удобная особенность, которая позволяет нам редактировать код в редакторе на основной ОС, а изменения будут сразу же применяться внутри контейнера.

Что такое Docker Volumes?

Docker Volumes — что-то похоже на карты памяти для Game Cube. Эта карта памяти содержит данные для игры. Эти карты съемные, и могу работать, когда Gamecube приставка выключается. Вы так же можете подключить различные карты памяти, содержащие разные данные, а так же, подключать к разным приставкам.

Вы можете вставить вашу карту внутрь приставки, точно так же, как и Docker Volume может быть прикреплён к любому из контейнеров.

С Docker Volum-ами мы имеем контейнер, который хранит постоянные данные где-то на нашем компьютере (это актуально, потому что после завершения работы контейнер удаляет все пользовательские данные, не входящие в образ). Вы можете прикрепить Volume-данные к любому из запущенных контейнеров.

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

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

Порты контейнеров

Docker позволяет нам получить доступ к какому-то из портов контейнера, пробросив его наружу (в основную операционную систему). По умолчанию, мы не можем достучаться к каким-либо из портов контейнера. Однако, в Dockerfile опция EXPOSE позволяет нам объявить, к какому из портов мы можем обратиться из основной ОС.

Для этого, на по-быстрому, запустим Docker-образ php-apache, который работает на 80 порту.

Для начала, создадим новую папку apache (перейдём в неё cd apache), в которой создадим файл index.php, на основе которого мы и поймём, что всё работает.

<?php
echo 'Hello from apache. We have PHP version = ' . phpversion() . PHP_EOL;

А так же, в этой папке создадим файл Dockerfile:

FROM php:7.2-apache
# Указываем рабочую папку
WORKDIR /var/www/html
# Копируем все файлы проекта в контейнер
COPY . /var/www/html
EXPOSE 80

Пробежимся по командам:
FROM: это вам уже знакомо, это образ с уже установленным php и apache
WORKDIR: создаст папку если она не создана, и перейдёт в неё. Аналогично выполнению команд mkdir /var/www/html && cd /var/www/html
EXPOSE: Apache по-умолчанию запускается на 80 порту, попробуем «прокинуть» его в нашу основную ОС (посмотрим как это работает через несколько секунд)

Для работы с сетью в Docker, нужно проделать 2 шага:

  • Прокинуть системный порт (Expose).
  • Привязать порт основной ОС к порту контейнера (выполнить соответствие).

Это что-то похоже на подключение вашей PS4 приставки к телевизору по HDMI кабелю. При подключении кабеля, вы явно указываете, какой HDMI-канал будет отображать видео.

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

EXPOSE в Докерфайле разрешает подключение к 80 порту контейнера — как разрешение HDMI подключения к PS4.

Выполним первый шаг прокидывания порт. Сбилдим контейнер:

docker build . --tag own_php_apache

И после этого, запустим контейнер:

docker run own_php_apache

apache_call

После чего, попробуем перейти по адресу localhost:80

Но, это не сработало, потому что мы ещё не выполнили 2 шаг по маппингу портов.

Выйдите из контейнера, нажав CTRL+C.

Если у вас проблемы с остановкой контейнера, в новом окне откройте терминал, выполните docker ps, найдите ID контейнера, который сейчас запущен, и выполните docker stop {CONTAINER_ID} (указав ваш ID контейнера)

Теперь, осталось сообщить нашему компьютеру, какой порт контейнера ему нужно слушать, и для этого формат записи будет такой:

docker run -p <HOST_PORT>:<CONTAINER_PORT>

И мы можем указать любое соответствие портов, но сейчас просто укажем, что порт системы 80 будет слушать 80 порт контейнера:

docker run -p 80:80 own_php_apache

Здесь, вы уже наверное заметили, что добавился новый параметр -p 80:80, который говорит Docker-у: я хочу, чтобы порт 80 из apache был привязан к моему локальному порту 80.

И теперь, если перейти по адресу localhost:80, то должны увидеть успешный ответ: apache_result

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

docker run -p 8080:80 own_php_apache

apache_result_8080

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

docker ps
docker stop <CONTAINER_ID> ...
docker rm <CONTAINER_ID> ...

Для *nix пользователей есть небольшой хак, который позволит остановить и удалить все контейнеры Docker:

docker stop $(docker ps -a -q)   # Остановит все контейнеры
docker rm $(docker ps -a -q)     # Удалит все остановленные контейнеры

Запомните, что любой, кто будет запускать этот код на своём компьютере, не должен иметь установленный PHP, всё что ему нужно — один только Docker.

Docker образ: прослойка данных и кеширование

Docker умнее, чем вы могли бы подумать :).

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

Каждая команда в Dockerfile сохраняется как отельный слой образа.

Рассмотрим это на примере нашего прошлого Dockerfile-а:

FROM php:7.2-apache
# Копирует код ядра
COPY . /var/www/html
WORKDIR /var/www/html
EXPOSE 80

Когда вы пишите свой Dockerfile, вы добавляете слои поверх существующего основного образа (указанного в FROM), и создаёте свой собственный образ (Image).

FROM: говорит Докеру взять за основу этот существующий образ. А все новые команды будут добавлены слоями поверх этого основного образа.
COPY: копирует файлы с основной ОС в образ
WORKDIR: устанавливает текущую папку образа в /var/www/html

Слой Образа Докера это как точка сохранения в игре Super Mario. Если вы хотите изменить какие-то вещи, произошедшие до этой точки сохранения, то вам придётся перезапустить этот уровень полностью. Если вы хотите продолжить прогресс прохождения, вы можете начать с того места, где остановились.

Docker начинает кешировать с «того места, где остановился» во время билдинга Dockerfile. Если в Докерфайле не было никаких изменений с момента последнего билдинга, то образ будет взят полностью из кеша. Если же вы измените какую-то строку в Dockerfile — кеш будет взят только тех слоёв команд, которые находятся выше изменённой команды.

Для иллюстрации этого, добавим новые строки в Dockerfile:

FROM php:7.2-apache
WORKDIR /var/www/html
# Copy the app code
COPY . /var/www/html
RUN apt-get update && apt-get upgrade -y && apt-get install -y curl php7.2-mbstring php7.2-zip php7.2-intl php7.2-xml php7.2-json php7.2-curl
RUN echo "Hello, Docker Tutorial"
EXPOSE 80

После чего, пересоберём образ:

docker build . --tag own_php_apache

cache
Выполнив эту команду, из вывода в консоль можете увидеть, что некоторые слои были взяты из кеша. Это как раз те команды, выше которых в Dockerfile не было добавлено/изменено содержимого.

И можно заметить, что в случае изменения Dockerfile, билдинг занимает больше времени, потому что не используется кеш. Где бы вы не написали команду, все закешированные команды, которые находятся ниже в Dockerfile, будут перебилжены заново. А те, что находятся выше, будут по-прежнему браться из кеша.

Когда вы используете команду COPY, она копирует указанную директорию в контейнер. И, в случае изменения содержимого любого из файлов этой директории, кеш команды COPY будет сброшен. Docker сверяет изменения во время билдинга в каждом из файлов. Если они были изменены, кеш будет сброшен, как и для всех последующих слоёв.

Если честно, то это действительно крутая функция. Docker следит за изменениями в файлах и использует кеш всегда, когда это нужно (когда были произведены изменения в каких-то из файлов). Изменение ваших файлов потенциально может затрагивать будущие команды, из-за чего, и все последующие слои билдятся заново, а не берутся из кеша.

Какие выводы из этого можно сделать:

  1. Команды, которые вероятнее всего не будут меняться в будущем, нужно помещать как можно выше в Dockerfile.
  2. Команды копирования данных нужно помещать ниже, потому что файлы при разработке изменяются довольно часто.
  3. Команды, которые требуют много времени на билдинг, нужно помещать выше.

В заключение, так же хочу сказать, как можно уменьшить размер слоёв Docker образов.
В Dockerfile вы можете иметь несколько команд (RUN) на выполнение:

RUN apt-get update
RUN apt-get install -y wget
RUN apt-get install -y curl

В результате выполнения этой команды, будет создано 3 разных слоя в образе. Вместо этого, все команды стараются объединить в одну строку:

RUN apt-get update && apt-get install -y wget curl

Если команда становится длинной, и нечитаемой, то для переноса на следующую строку делаем так:

RUN apt-get update && apt-get install -y wget curl && 
    && apt-get clean -y 
    && docker-php-ext-install soap mcrypt pdo_mysql zip bcmath

Если же команда становится слишком большой, и неудобной для чтения, то можно создать новый shell скрипт, в который поместить длинную команду, и запускать этот скрипт одной простой командой RUN.

Технически, только команды ADD, COPY, и RUN создают новый слой в Docker образе, остальные команды кешируются по-другому

Что такое Docker-Compose?

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

Docker Compose управляет контейнерами, запускает их вместе, в нужной последовательности, необходимой для вашего приложения.
Его можно назвать дирижёром в мире Docker-а.

Docker-compose организовывает совместных запуск контейнеров, как инструменты в групповой игре в определённых участках песни.

Каждый инструмент имеет конкретную задачу в группе оркестра. Труба создаёт основную мелодию песни; фортепиано, гитара дополняют основную мелодию; барабаны задают ритм; саксофоны добавляют больше гармонии и т.д.
Каждый из инструментов имеет свою конкретную работу и задачу, как и наши контейнеры.

Docker-compose написан в формате YAML который по своей сути похож на JSON или XML. Но YAML имеет более удобный формат для его чтения, чем вышеперечисленные. В формате YAML имеют значения пробелы и табуляции, именно пробелами отделяются названия параметров от их значений.

Создадим новый файл docker-compose.yml, для рассмотрения синтаксиса Docker Compose:

version: '3'

services:
  app:
    build:
      context: .
    ports:
      - 8080:80

Теперь, построчно разберёмся с заданными параметрами, и что они значат:
version: какая версия docker-compose используется (3 версия — самая последняя на даный момент).
services: контейнеры которые мы хотим запустить.
app: имя сервиса, может быть любым, но желательно, чтобы оно описывало суть этого контейнера.
build: шаги, описывающие процесс билдинга.
context: где находится Dockerfile, из которого будем билдить образ для контейнера.
ports: маппинг портов основной ОС к контейнеру.

Мы можем использовать этот файл для билдинга нашего предыдущего образа apache:

docker-compose build

После выполнения этой команды, Docker спарсит файл docker-compose и создаст описанные сервисы на основе инструкций во вкладке build.

А context говорит о том, из какой директории мы берём Dockerfile для создания образа сервиса (в текущем случае — это означает текущую директорию ., но могло быть и /php-cli, /nginx, и т.д.).

И теперь, запустим эти сервисы, которые создали:

docker-compose up

В результате чего, сервер должен был запуститься, и стать доступным по адресу localhost:8080.

Теперь, отключитесь от консоли, нажав CTRL+C.

Когда контейнер под названием app запускается, docker-compose автоматически связывает указанные порты во вкладке ports. Вместо того, как мы делали ранее, выполняя -v 8080:80, docker-compose делает это за нас, получив информацию параметра ports. Docker-compose избавляет нас боли, связанной с указанием параметров в командной строке напрямую.

С docker-compose.yml мы переносим все параметры, ранее записываемые в командной строке при запуске контейнера в конфигурационный YAML файл.

В этом примере мы записали BUILD и RUN шаги для нашего сервиса в docker-compose.yml. И преимущество такого подхода ещё в том, что теперь для билдинга и для запуска этих сервисов нам нужно запомнить только 2 команды: docker-compose build и docker-compose up. При таком подходе не нужно помнить, какие аргументы нужно указывать, какие опции нужно задавать при запуске контейнера.

Теперь давайте сделаем нашу разработку немного легче. Сделаем, чтобы вместо постоянного перестроения образа при каждом изменении файлов, мы можем примонтировать нашу рабочую папку в контейнер.
Для этого, удалите строку COPY . /var/www/html с Dockerfile — теперь все файлы будут прокинуты из основной ОС. Новый Dockerfile будет иметь вид:

FROM php:7.2-apache
WORKDIR /var/www/html
RUN apt-get update && apt-get install -y wget
EXPOSE 80

Ранее мы рассматривали, как примонтировать папку в контейнер, для этого мы запускали контейнер с аргументом -v <HOST_DIRECTORY>:<CONTAINER_DIRECTORY>.
С Docker-compose мы можем указать напрямую в docker-compose.yml:

version: '3'
services:
  app:
    build:
      context: .
    ports:
      - 8080:80
    volumes:
      - .:/var/www/html

Добавленная строка примонтирует текущую директорию основой операционной системы к директории /var/www/html контейнера.

В отличие от указания путь в консоли, здесь можно указывать относительный путь (.), не обязательно указывать полный путь (C:projectsdocker-exampleapache), как было ранее при ручном запуске контейнера.

Теперь, выполните по очереди команды:

docker-compose stop
docker-compose rm

При удалении, вас спросят, действительно ли удалять, напишите y и нажмите кнопку enter. Эти команды остановят и удалят все контейнеры, описанные в файле docker-compose.yml (то же самое, как мы ранее запускали docker stop <CONTAINER_ID> и docker rm <CONTAINER_ID>)

Теперь перебилдим сервисы, потому что мы изменили Dockerfile:

docker-compose build

И заново запустим:

docker-compose up

И опять, по адресу localhost:8080 поднимется наш сервер.

Вместо того, чтобы копировать каждый раз файлы в образ, мы просто примонтировали папку, содержащую исходный код приложения. И теперь, каждый раз не придётся делать ребилд образа, когда файлы изменяются, теперь изменения происходят в лайв режиме, и будут доступны без перестройки образа.

Чтобы в этом убедиться, изменим файл index.php, добавим в него скрипт нами любимой пирамиды:

<?php
$n = $i = $_GET['count'] ?? 4;
echo '<pre>';
while ($i--) {
    echo str_repeat(' ', $i).str_repeat('* ', $n - $i)."n";
}
echo '</pre>';

И теперь, если перейти по адресу localhost:8080?count=10, то увидим, что пирамида выводится: apache_index_count

Монтирование вашей локальной папки как Docker Volume это основной метод как разрабатывать приложения в контейнере.

Так же, как мы ранее выполняли команды внутри контейнера, указывая аргументы -it ... /bin/bash. Docker-compose так же предоставляет интерфейс по удобному выполнению команд внутри конкретного контейнера. Для этого нужно выполнить команду:

docker-compose exec {CONTAINER_NAME} {COMMAND}

где, вместо {CONTAINER_NAME} нужно записать имя контейнера, под которым он записан в сервисах;
а вместо {COMMAND} — желаемую команду.

К примеру, эта команда может выглядеть так:

docker-compose exec php-cli php -v

Но, сделаем это на основе текущего Dockerfile:

docker-compose down # остановим контейнеры
docker-compose up -d # здесь используется опция -d которая сообщает, что контейнер должен висеть в режиме демона
docker-compose exec app apache2 -v

И в результате должны получить exec

Пока что, в docker-compose.yml описан только один сервис, потому разворачиваем мы только один контейнер. Но реальный файл docker-compose выглядит больше. К примеру, для Laravel он такой:

version: '3'
services:
  nginx:
    build:
      context: ./
      dockerfile: docker/nginx.docker
    volumes:
      - ./:/var/www
    ports:
      - "8080:80"
    depends_on:
      - php-fpm
  php-fpm:
    build:
      context: ./
      dockerfile: docker/php-fpm.docker
    volumes:
      - ./:/var/www
    depends_on:
      - mysql
      - redis
    environment:
      - "DB_PORT=3306"
      - "DB_HOST=mysql"
      - "REDIS_PORT=6379"
      - "REDIS_HOST=redis"
  php-cli:
    build:
      context: ./
      dockerfile: docker/php-cli.docker
    volumes:
      - ./:/var/www
    depends_on:
      - mysql
      - redis
    environment:
      - "DB_PORT=3306"
      - "DB_HOST=mysql"
      - "REDIS_PORT=6379"
      - "REDIS_HOST=redis"
    tty: true
  mysql:
    image: mysql:5.7
    volumes:
      - ./storage/docker/mysql:/var/lib/mysql
    environment:
      - "MYSQL_ROOT_PASSWORD=secret"
      - "MYSQL_USER=app"
      - "MYSQL_PASSWORD=secret"
      - "MYSQL_DATABASE=app"
    ports:
      - "33061:3306"
  redis:
    image: redis:3.0
    ports:
      - "6379:6379"

И при выполнении одной только команды docker-compose up, поднимутся 5 сервисов. В сравнении с тем, что мы бы вручную выполняли 5 раз команду docker run .... Так что, использование docker-compose в этом случае — очевидно. Так что, теперь, ещё один шаг позадчи, теперь вы знаете, что такое docker и docker compose, и для чего нужен каждый из них.

Как писать Микро Сервисы с Docker? Что такое микросервисы?

Docker найболее часто используемый инструмент для написания Микросервисов. Микросервисы — это архитектурный шаблон проектирования который следует философии «разделения ответственности».

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

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

Идея разделения по ответственности предоставляет преимущество в том, что команда разработчиков может работать параллельно, фокусируясь над разными компонентами.

В основном, микросервисы имеют канал коммуникации мужду собой, в виде REST API, который возвращает данные в JSON, или что-то типа того.

Иногда бывает неясно, насколько большой, или маленькой должна быть задача микросервиса, которую он должен решать. Это решение лежит на плечах разработчика, здесь нет чёткого правила.

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

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

Резюме

Я попытался написать эту статью максимально просто, построив всё объяснение на аналогиях и примерах их жизни. Эта статью можно считать простой инструкцией по работе с Docker. Помимо того, что я описал, как пользоваться Docker-ом, добавив несколько рабочих примеров, которые вы можете попробовать у себя на компьютере, я добавил много дополнительной информации, и некоторых тонкостей работы с Docker-ом. Надеюсь, что эта статья показала вам, что такое Docker, и с чем его едят. В следующей статья я затрону более продвинутые темы и приведу примеры.

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

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

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

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

При этом контейнеры легковесны. Они не требуют дополнительной загрузки гипервизора. Гипервизор — это гостевая операционная система вроде VMWare или VirtualBox. Так вот, для запуска контейнеров гостевая ОС не требуется, они запускаются прямо в ядре хоста.

От редакции Techrocks. Также рекомендуем статью «Контейнеры Docker: простое объяснение на примере аренды офиса».

Когда использовать Docker?

Изучение новых технологий

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

Многие проекты имеют готовые образы Docker, где продвигаемое приложение уже установлено и настроено.

Базовое использование

Если речь идет о каком-то базовом или достаточно стандартном приложении, способном работать с дефолтным образом Docker, загрузка образов из Docker Hub — тоже хорошее решение.

Например, на DockerHub доступны и хорошо поддерживаются официальные образы node и mongodb. Если дефолтная настройка этого ПО приемлема для ваших нужд, просто вытянуть себе готовый образ будет гораздо быстрее, чем самостоятельно настраивать среду и устанавливать необходимые инструменты.

Изоляция приложений

Если вы хотите запускать несколько приложений на одном сервере, будет полезным содержать их компоненты в разных контейнерах. Это избавит вас от проблем с управлением зависимостями.

Работа в команде

«На моей машине это работает!» Мы, разработчики, знаем, что одна из самых заковыристых проблем в разработке — необходимость учитывать разные машины и платформы.

Docker позволяет запускать контейнеры локально, что снимает вопрос несоответствия между средой разработки и продакшена (и всеми прочими средами).

Нет нужды устанавливать какие-либо пакеты. Все, что вам нужно для среды разработки, может просто запускаться в движке Docker в виде контейнеров.

О каких бы инструментах и языках ни шла речь — вы всегда можете контейнеризовать вашу локальную среду.

Система с ограниченными ресурсами

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

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

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

Виртуальные машины vs Docker

И контейнеры Docker, и виртуальные машины — это средства для развертывания приложений в окружении, изолированном от железа хоста. Ключевая разница между ними в уровне изоляции.

Если речь идет о виртуальной машине (VM), то все, что находится внутри нее, не зависит от операционной системы хоста. VM-платформа запускает процесс (virtual machine monitor или VMM) для управления процессом виртаулизации отдельной виртуальной машины. Система хоста выделяет некоторое количество ресурсов машины для этой VM.

VM кардинально отличается тем, что при ее запуске загружается новое выделенное ядро для ее среды и запускается набор процессов операционной системы (часто довольно большой). Это делает размер виртуальной машины намного больше размера типичного контейнера, содержащего только приложение.

А вот в контейнерной среде запуска вроде Docker ваше приложение помещается в песочницу с изолированными функциями, предоставляемыми контейнером. При этом оно делит ресурсы ядра с другими приложениями в контейнерах на этом же хосте.

В результате процессы, происходящие внутри контейнеров, видимы из системы хоста. Конечно, если у вас достаточно прав, чтобы их видеть.

То, что несколько контейнеров делят одно ядро, позволяет конечному пользователю иметь на одной машине сколь угодно много контейнеров. Причем загружаться они будут практически моментально.

Ну и поскольку контейнеры не нуждаются в отдельной операционной системе, они очень легковесны, обычно это 5-100 MB.

От редакции Techrocks. Также рекомендуем статью «В чём разница между Docker и Kubernetes?» и «Почему Docker на macOS намного хуже, чем на Linux?»

Что такое контейнер?

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

По умолчанию контейнер относительно хорошо изолирован от других контейнеров и машины-хоста. Степень изоляции вы можете контролировать.

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

Что такое образ Docker?

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

Например, вы можете создать образ, основанный на образе ubuntu, но установить поверх него веб-сервер Apache и ваше приложение, а также добавить детали конфигурации, необходимые для запуска вашего приложения.

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

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

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

Что такое Docker Hub?

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

При помощи Docker Hub пользователь может получить доступ к публичным репозиториям образов с открытым кодом. Также он может использовать пространство хаба для создания собственных приватных репозиториев, функций автоматизированной сборки, веб-хуков и т. п.

Пишем простой Dockerfile

Предположим, у нас есть простое приложение на node JS. В нем есть файл server.js, который прослушивает порт 3040 и выводит ‘Hello World!’ при переходе по адресу ‘localhost:3040/’.

Файловая структура приложения следующая:

simpleNodeApplication

  • Dockerfile
  • package-lock.json
  • package.json
  • server.js
//Initializes a new build stage and sets the Base Image for subsequent instructions
FROM node:14-alpine

//Defining working directory for our application and 
it will be the default directory for our further steps
WORKDIR /app

//Copy package.json file to our created workdir
COPY package.json .

//Does npm install
RUN npm install

//Copy entire code from local to our workdir
COPY . .

//Exposing application on port 3040
EXPOSE 3040

//Command to run our application
CMD ["node", "server.js"]

Чтобы поиграться с этим dockerfile:

  • Собрать образ => docker build -t myApp:V1 .
  • Создать контейнер и нацелить его на порт 3000 => docker run -p 3000:3040 --name myContainer myApp:V1
  • Вывести запущенные контейнеры => docker ps
  • Остановить контейнер => docker stop myContainer
  • Запустить контейнер заново => docker start myContainer

Примечание. Вероятно, вам интересно, в чем разница между RUN и CMD. Команда RUN может быть выполнена при сборке контейнера. Инструкция CMD должна использоваться для запуска программ, содержащихся в вашем образе.

Команды Docker

В этом разделе мы рассмотрим несколько консольных команд для работы с Docker. Этими командами разработчики пользуются постоянно.

Допустим, у нас есть образ с ImageId myApp:V1 и ContainerName myContainer.

Образ

docker build [OPTIONS] PATH | URL | -
docker build -t myApp:V1 .

При помощи этих команд, используя dockerfile, можно создать образ приложения. Имя образу можно задать самостоятельно, для этого нужно использовать опцию -t: docker build -t name:tag .

docker tag SOURCE_IMAGE[:TAG] TARGET_IMAGE[:TAG]
docker tag myApp:V1 myNewApp:V1

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

docker images

Вывод всех образов, доступных локально.

docker image inspect Name|ImageId
docker image inspect myApp:V1

Вывод подробной информации об образе, по умолчанию — в формате JSON.

docker rmi [OPTIONS] IMAGE [IMAGE...]
docker rmi myApp:V1

С помощью этой команды можно удалить один или несколько образов.

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

docker system prune [OPTIONS]

Удаление всех неиспользуемых контейнеров, сетей, образов и, опционально, разделов.

Контейнеры

docker run [OPTIONS] IMAGE [COMMAND] [ARG...]
docker run -p 3000:3040 -it -rm --name myContainer myApp:V1

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

По умолчанию команда ищет образ локально, а если не находит, обращается к репозиториям.

Чтобы дать контейнеру имя, можно использовать опцию --name: docker run --name string Name|ImageId.

Для запуска приложения в интерактивном режиме (чтение входящих данных из консоли и т. п.) используйте опцию -it.

Опция -rm говорит docker удалить контейнер, как только он будет остановлен.

docker stop [OPTIONS] CONTAINER [CONTAINER...]
docker stop myContainer

С помощью этих команд можно остановить один или несколько контейнеров.

docker start [OPTIONS] CONTAINER [CONTAINER...]
docker start myContainer

Эти команды запускают остановленные контейнеры. По умолчанию это происходит в фоновом режиме.

docker restart [OPTIONS] CONTAINER [CONTAINER...]
docker restart myContainer

Перезапуск одного или нескольких контейнеров.

docker rename CONTAINER NEW_NAME
docker rename myContainer myNewContainer

Смена имени уже созданного контейнера.

docker ps [OPTIONS]

Вывод списка всех запущенных контейнеров (по умолчанию). Для вывода вообще всех контейнеров используйте опцию -a.

docker rm [OPTIONS] CONTAINER [CONTAINER...]
docker rm myContainer

С помощью этой команды можно удалить один или несколько контейнеров.

docker logs [OPTIONS] CONTAINER
docker logs myContainer

Получение логов контейнера.

docker cp [OPTIONS] CONTAINER:SRC_PATH DEST_PATH|-

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

docker login [OPTIONS] [SERVER]
docker login localhost:8080

Вход в реестр Docker.

docker logout [SERVER]
docker logout localhost:8080

Выход из реестра Docker.

docker push [OPTIONS] NAME[:TAG]
docker image push myApp:V1

Используйте эту команду, когда хотите поделиться вашими образами в реестре Docker Hub.

docker pull [OPTIONS] NAME[:TAG|@DIGEST]
docker pull ubuntu:20.04

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

Перевод статьи «Beginner’s guide to Docker(Part 1)- Dockerfile and Docker CLI commands».

Докер – Обзор

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

Первоначальный выпуск Docker состоялся в марте 2013 года, и с тех пор он стал модным словом для развития современного мира, особенно перед лицом Agile-проектов.

Обзор докера

Особенности Docker

  • Docker имеет возможность уменьшить размер разработки, предоставляя меньшую площадь операционной системы через контейнеры.

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

  • Контейнеры Docker можно развернуть где угодно, на любых физических и виртуальных машинах и даже в облаке.

  • Поскольку контейнеры Docker довольно легкие, их очень легко масштабировать.

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

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

Контейнеры Docker можно развернуть где угодно, на любых физических и виртуальных машинах и даже в облаке.

Поскольку контейнеры Docker довольно легкие, их очень легко масштабировать.

Компоненты Docker

Докер имеет следующие компоненты

  • Docker для Mac – позволяет запускать контейнеры Docker в Mac OS.

  • Docker для Linux – позволяет запускать Docker-контейнеры в ОС Linux.

  • Docker для Windows – позволяет запускать Docker-контейнеры в ОС Windows.

  • Docker Engine – используется для создания образов Docker и создания контейнеров Docker.

  • Docker Hub – это реестр, который используется для размещения различных образов Docker.

  • Docker Compose – используется для определения приложений с использованием нескольких контейнеров Docker.

Docker для Mac – позволяет запускать контейнеры Docker в Mac OS.

Docker для Linux – позволяет запускать Docker-контейнеры в ОС Linux.

Docker для Windows – позволяет запускать Docker-контейнеры в ОС Windows.

Docker Engine – используется для создания образов Docker и создания контейнеров Docker.

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

Docker Compose – используется для определения приложений с использованием нескольких контейнеров Docker.

Мы обсудим все эти компоненты подробно в следующих главах.

Официальный сайт Docker: https://www.docker.com/ На сайте есть вся информация и документация о программном обеспечении Docker. Он также имеет ссылки для загрузки различных операционных систем.

Установка Docker в Linux

Чтобы начать установку Docker, мы собираемся использовать экземпляр Ubuntu. Вы можете использовать Oracle Virtual Box для настройки виртуального экземпляра Linux, если у вас его еще нет.

На следующем снимке экрана показан простой сервер Ubuntu, установленный в Oracle Virtual Box. Существует пользователь ОС с именем demo, который был определен в системе с полным корневым доступом к серверу.

Демо-кнопка

Чтобы установить Docker, нам нужно выполнить шаги, указанные ниже.

Шаг 1 – Перед установкой Docker вы должны убедиться, что у вас установлена ​​правильная версия ядра Linux. Docker предназначен только для работы с ядром Linux версии 3.8 и выше. Мы можем сделать это, выполнив следующую команду.

uname

Этот метод возвращает системную информацию о системе Linux.

Синтаксис

uname -a

Опции

a – Это используется, чтобы гарантировать, что системная информация возвращается.

Возвращаемое значение

Этот метод возвращает следующую информацию о системе Linux –

  • имя ядра
  • имя узла
  • выпуск ядра
  • версия ядра
  • машина
  • процессор
  • аппаратная платформа
  • операционная система

пример

uname –a

Выход

Когда мы запустим вышеуказанную команду, мы получим следующий результат –

Выход

Из результатов видно, что версия ядра Linux – 4.2.0-27, что выше, чем версия 3.8, так что мы готовы идти дальше.

Шаг 2 – Вам необходимо обновить ОС последними пакетами, что можно сделать с помощью следующей команды:

apt-get

Этот метод устанавливает пакеты из Интернета в систему Linux.

Синтаксис

sudo apt-get update

Опции

  • sudo – команда sudo используется для обеспечения выполнения команды с правами root.

  • update – опция обновления используется, чтобы гарантировать, что все пакеты обновлены в системе Linux.

sudo – команда sudo используется для обеспечения выполнения команды с правами root.

update – опция обновления используется, чтобы гарантировать, что все пакеты обновлены в системе Linux.

Возвращаемое значение

Никто

пример

sudo apt-get update

Выход

Когда мы запустим указанную выше команду, мы получим следующий результат –

Пример вывода

Эта команда подключится к Интернету и загрузит последние системные пакеты для Ubuntu.

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

sudo apt-get install apt-transport-https ca-certificates

Необходимые пакеты Docker

Шаг 4 – Следующий шаг – добавить новый ключ GPG. Этот ключ необходим для обеспечения шифрования всех данных при загрузке необходимых пакетов для Docker.

Следующая команда загрузит ключ с идентификатором 58118E89F3A912897C070ADBF76221572C52609D с сервера ключей hkp: //ha.pool.sks-keyservers.net: 80 и добавит его в цепочку ключей adv . Обратите внимание, что этот конкретный ключ необходим для загрузки необходимых пакетов Docker.

Новый ключ PGP

Шаг 5 – Далее, в зависимости от версии Ubuntu, вам нужно будет добавить соответствующий сайт в список docker.list для менеджера пакетов apt , чтобы он мог обнаружить пакеты Docker с сайта Docker и загрузить их соответственно.

  • Precise 12.04 (LTS) ─ deb https://apt.dockerproject.org/repo ubuntu-Precision Main

  • Trusty 14.04 (LTS) ─ deb https://apt.dockerproject.org/repo/ ubuntu-trusty main

  • Хитрый 15.10 ─ deb https://apt.dockerproject.org/repo ubuntu-wily main

  • Xenial 16.04 (LTS) – https://apt.dockerproject.org/repo ubuntu-xenial main

Precise 12.04 (LTS) ─ deb https://apt.dockerproject.org/repo ubuntu-Precision Main

Trusty 14.04 (LTS) ─ deb https://apt.dockerproject.org/repo/ ubuntu-trusty main

Хитрый 15.10 ─ deb https://apt.dockerproject.org/repo ubuntu-wily main

Xenial 16.04 (LTS) – https://apt.dockerproject.org/repo ubuntu-xenial main

Поскольку нашей операционной системой является Ubuntu 14.04, мы будем использовать имя репозитория как «deb https://apt.dockerproject.org/repo ubuntu-trusty main».

И затем нам нужно будет добавить этот репозиторий в список docker.list, как упоминалось выше.

echo "deb https://apt.dockerproject.org/repo ubuntu-trusty main” 
   | sudo tee /etc/apt/sources.list.d/docker.list

Список докеров

Шаг 6 – Затем мы запускаем команду apt-get update для обновления пакетов в системе Ubuntu.

Команда обновления APT-GET

Шаг 7 – Если вы хотите убедиться, что менеджер пакетов указывает на правильный репозиторий, вы можете сделать это, выполнив команду apt-cache .

apt-cache policy docker-engine

В результате вы получите ссылку на https://apt.dockerproject.org/repo/

Команда обновления APT-GET

Шаг 8 – Введите команду apt-get update, чтобы убедиться, что все пакеты в локальной системе обновлены.

Обновление пакетов APT-GET

Шаг 9 – Для Ubuntu Trusty, Wily и Xenial мы должны установить пакеты ядра linux-image-extra- *, которые позволяют использовать драйвер хранилища aufs . Этот драйвер используется более новыми версиями Docker.

Это можно сделать с помощью следующей команды.

sudo apt-get install linux-image-extra-$(uname -r) 
   linux-image-extra-virtual

Aufs Storage Driver

Шаг 10 – Последний шаг – установить Docker, и мы можем сделать это с помощью следующей команды:

sudo apt-get install –y docker-engine

Здесь apt-get использует опцию установки для загрузки образа движка Docker с веб-сайта Docker и установки Docker.

Docker-engine – это официальный пакет от Docker Corporation для систем на основе Ubuntu.

Докер-двигатель

В следующем разделе мы увидим, как проверить версию установленного Docker.

Версия Docker

Чтобы увидеть версию Docker, вы можете выполнить следующую команду:

Синтаксис

docker version 

Опции

  • версия – используется для гарантии того, что команда Docker возвращает установленную версию Docker.

версия – используется для гарантии того, что команда Docker возвращает установленную версию Docker.

Возвращаемое значение

Выходные данные будут содержать различные сведения о версии Docker, установленной в системе.

пример

sudo docker version 

Выход

Когда мы запустим вышеуказанную программу, мы получим следующий результат –

Вывод версии Docker

Информация о докере

Чтобы увидеть больше информации о Docker, работающем в системе, вы можете выполнить следующую команду:

Синтаксис

docker info

Опции

  • info – используется для того, чтобы команда Docker возвращала подробную информацию об установленной службе Docker.

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

Возвращаемое значение

Выходные данные предоставят различные детали Docker, установленного в системе, такие как –

  • Количество контейнеров
  • Количество изображений
  • Драйвер хранилища, используемый Docker
  • Корневой каталог, используемый Docker
  • Драйвер выполнения, используемый Docker

пример

sudo docker info

Выход

Когда мы запустим указанную выше команду, мы получим следующий результат –

Пример вывода информации Docker

Докер для Windows

Docker имеет встроенную поддержку Windows, но для установки Docker для Windows необходимо иметь следующую конфигурацию.

Системные Требования

ОС Windows Windows 10 64 бит
объем памяти 2 ГБ ОЗУ (рекомендуется)

Вы можете скачать Docker для Windows с – https://docs.docker.com/docker-for-windows/

Докер для Windows

Docker ToolBox

Docker ToolBox был разработан для более старых версий Windows, таких как Windows 8.1 и Windows 7. Для установки Docker для Windows необходимо иметь следующую конфигурацию.

Системные Требования

ОС Windows Windows 7, 8, 8.1
объем памяти 2 ГБ ОЗУ (рекомендуется)
Виртуализация Это должно быть включено.

Вы можете скачать Docker ToolBox с – https://www.docker.com/products/docker-toolbox

Панель инструментов Docker

Докер – Установка

Давайте пройдемся по установке каждого продукта.

Докер для Windows

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

Шаг 1 – Нажмите на условия соглашения, а затем на кнопку «Установить», чтобы продолжить установку.

Настройка Docker

Шаг 2 – После завершения нажмите кнопку Готово, чтобы завершить установку.

Конец

Docker ToolBox

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

Шаг 1 – Нажмите кнопку Далее на начальном экране.

Docker ToolBox Next

Шаг 2. Сохраните местоположение по умолчанию на следующем экране и нажмите кнопку «Далее».

Место назначения

Шаг 3 – Оставьте компоненты по умолчанию и нажмите кнопку Далее, чтобы продолжить.

Выберите компоненты

Шаг 4. Сохраните дополнительные задачи такими, какие они есть, и нажмите кнопку «Далее».

Дополнительные задачи

Шаг 5 – На последнем экране нажмите кнопку Установить.

устанавливать

Работа с Docker Toolbox

Давайте теперь посмотрим, как можно использовать Docker Toolbox для работы с контейнерами Docker в Windows. Первым шагом является запуск приложения Docker Toolbox, для которого создается ярлык на рабочем столе при установке панели инструментов Docker.

Быстрый старт Терминал

Далее вы увидите настройку, выполняемую при запуске Docker.

Docker Toolbox Terminal

После этого вы увидите, что Docker настроен и запущен. Вы получите интерактивную оболочку для Docker.

Интерактивная оболочка

Чтобы проверить, правильно ли работает Docker, мы можем использовать команду Docker run для загрузки и запуска простого контейнера HelloWorld Docker .

Работа команды запуска Docker приведена ниже –

docker run 

Эта команда используется для запуска команды в контейнере Docker.

Синтаксис

docker run image

Опции

  • Изображение – это имя изображения, которое используется для запуска контейнера.

Изображение – это имя изображения, которое используется для запуска контейнера.

Возвращаемое значение

Вывод выполнит команду в нужном контейнере.

пример

sudo docker run hello-world

Эта команда загрузит образ hello-world , если его еще нет, и запустит hello-world в качестве контейнера.

Выход

Когда мы запустим указанную выше команду, мы получим следующий результат –

Докер Контейнер

Если вы хотите запустить ОС Ubuntu в Windows, вы можете загрузить образ Ubuntu, используя следующую команду:

Docker run –it Ubuntu bash

Здесь вы говорите Docker запускать команду в интерактивном режиме через опцию –it .

Ubuntu Image

В выводе вы видите, что образ Ubuntu загружен и запущен, а затем вы войдете в систему как пользователь root в контейнере Ubuntu.

Докер – хаб

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

Официальный сайт Docker Hub – https://www.docker.com/community-edition#/add_ons

Шаг 1 – Сначала вам нужно сделать простую регистрацию в Docker-хабе.

Docker Hub Singup

Шаг 2 – Как только вы зарегистрируетесь, вы войдете в Docker Hub.

Войти в Docker Hub

Шаг 3 – Далее, давайте посмотрим и найдем изображение Дженкинса.

Дженкинс изображение

Шаг 4 – Если вы прокрутите вниз на той же странице, вы увидите команду Docker pull . Это будет использоваться для загрузки образа Jenkins на локальный сервер Ubuntu.

Команда Pull

Шаг 5 – Теперь перейдите на сервер Ubuntu и выполните следующую команду –

sudo docker pull jenkins 

Сервер Ubuntu

Чтобы запустить Jenkins, вам нужно выполнить следующую команду –

sudo docker run -p 8080:8080 -p 50000:50000 jenkins 

Обратите внимание на следующие моменты о приведенной выше команде sudo

  • Мы используем команду sudo, чтобы убедиться, что она работает с правами root.

  • Здесь jenkins – это имя образа, который мы хотим загрузить из центра Docker и установить на наш компьютер с Ubuntu.

  • -p используется для сопоставления номера порта внутреннего образа Docker с нашим основным сервером Ubuntu, чтобы мы могли соответствующим образом получить доступ к контейнеру.

Мы используем команду sudo, чтобы убедиться, что она работает с правами root.

Здесь jenkins – это имя образа, который мы хотим загрузить из центра Docker и установить на наш компьютер с Ubuntu.

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

Судо командование

После этого Jenkins будет успешно работать в качестве контейнера на компьютере с Ubuntu.

Докер – Изображения

В Docker все основано на изображениях. Изображение представляет собой комбинацию файловой системы и параметров. Давайте рассмотрим пример следующей команды в Docker.

docker run hello-world 
  • Команда Docker специфична и сообщает программе Docker в операционной системе, что нужно что-то делать.

  • Команда run используется для упоминания того, что мы хотим создать экземпляр изображения, который затем называется контейнером .

  • Наконец, «hello-world» представляет изображение, из которого сделан контейнер.

Команда Docker специфична и сообщает программе Docker в операционной системе, что нужно что-то делать.

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

Наконец, «hello-world» представляет изображение, из которого сделан контейнер.

Теперь давайте посмотрим, как мы можем использовать образ CentOS, доступный в Docker Hub, для запуска CentOS на нашей машине с Ubuntu. Мы можем сделать это, выполнив следующую команду на нашем компьютере с Ubuntu:

sudo docker run centos –it /bin/bash

Обратите внимание на следующие моменты о приведенной выше команде sudo

  • Мы используем команду sudo, чтобы убедиться, что она работает с правами root .

  • Здесь centos – это имя образа, который мы хотим загрузить с Docker Hub и установить на наш компьютер с Ubuntu.

  • упоминается, что мы хотим работать в интерактивном режиме .

  • / bin / bash используется для запуска оболочки bash после запуска и запуска CentOS.

Мы используем команду sudo, чтобы убедиться, что она работает с правами root .

Здесь centos – это имя образа, который мы хотим загрузить с Docker Hub и установить на наш компьютер с Ubuntu.

упоминается, что мы хотим работать в интерактивном режиме .

/ bin / bash используется для запуска оболочки bash после запуска и запуска CentOS.

Отображение изображений Docker

Чтобы просмотреть список образов Docker в системе, вы можете выполнить следующую команду.

docker images

Эта команда используется для отображения всех изображений, установленных в данный момент в системе.

Синтаксис

docker images 

Опции

Никто

Возвращаемое значение

Вывод предоставит список изображений в системе.

пример

sudo docker images

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Отображение изображений Docker

Из приведенного выше вывода видно, что на сервере есть три изображения: centos, newcentos и jenkins . Каждое изображение имеет следующие атрибуты –

  • TAG – используется для логической маркировки изображений.

  • Идентификатор изображения – используется для уникальной идентификации изображения.

  • Создано – количество дней с момента создания изображения.

  • Виртуальный размер – размер изображения.

TAG – используется для логической маркировки изображений.

Идентификатор изображения – используется для уникальной идентификации изображения.

Создано – количество дней с момента создания изображения.

Виртуальный размер – размер изображения.

Загрузка изображений Docker

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

Синтаксис

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

docker run image 

Опции

  • Изображение – это имя изображения, которое используется для запуска контейнера.

Изображение – это имя изображения, которое используется для запуска контейнера.

Возвращаемое значение

Вывод выполнит команду в нужном контейнере.

пример

sudo docker run centos

Эта команда загрузит изображение centos , если оно еще не создано, и запустит ОС в качестве контейнера.

Выход

Когда мы запустим указанную выше команду, мы получим следующий результат –

Загрузка изображений Docker

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

Centos

Удаление изображений Docker

Образы Docker в системе можно удалить с помощью команды docker rmi . Давайте посмотрим на эту команду более подробно.

docker rmi

Эта команда используется для удаления образов Docker.

Синтаксис

docker rmi ImageID

Опции

  • ImageID – это идентификатор изображения, которое необходимо удалить.

ImageID – это идентификатор изображения, которое необходимо удалить.

Возвращаемое значение

Выходные данные будут содержать идентификатор изображения удаленного изображения.

пример

sudo docker rmi 7a86f8ffcb25 

Здесь 7a86f8ffcb25 – это идентификатор изображения newcentos .

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Удаление изображений Docker

Давайте посмотрим еще несколько команд Docker на изображениях.

докер изображения -q

Эта команда используется для возврата только идентификаторов изображений изображений.

Синтаксис

docker images 

Опции

  • q – Указывает команде Docker возвращать только ID изображения.

q – Указывает команде Docker возвращать только ID изображения.

Возвращаемое значение

Выходные данные будут отображать только идентификаторы изображений на хосте Docker.

пример

sudo docker images -q 

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Docker Images Q

докер проверяет

Эта команда используется для просмотра деталей изображения или контейнера.

Синтаксис

docker inspect Repository 

Опции

  • Репозиторий – это название образа.

Репозиторий – это название образа.

Возвращаемое значение

На выходе будет показана подробная информация об изображении.

пример

sudo docker inspect jenkins 

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Докер Инспекция

Докер – Контейнеры

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

Запуск контейнера

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

sudo docker run –it centos /bin/bash 

Затем нажмите Crtl + p, и вы вернетесь в свою оболочку ОС.

Контейнеры

Затем вы будете работать в экземпляре системы CentOS на сервере Ubuntu.

Распечатка контейнеров

Можно перечислить все контейнеры на машине с помощью команды docker ps . Эта команда используется для возврата текущих запущенных контейнеров.

docker ps

Синтаксис

docker ps 

Опции

Никто

Возвращаемое значение

Вывод покажет работающие в данный момент контейнеры.

пример

sudo docker ps

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Распечатка контейнеров

Давайте посмотрим еще несколько вариантов команды docker ps .

докер ps -a

Эта команда используется для вывода списка всех контейнеров в системе

Синтаксис

docker ps -a 

Опции

  • ─a – сообщает команде docker ps перечислить все контейнеры в системе.

─a – сообщает команде docker ps перечислить все контейнеры в системе.

Возвращаемое значение

Вывод покажет все контейнеры.

пример

sudo docker ps -a 

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Докер PS A

история докера

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

Синтаксис

docker history ImageID 

Опции

  • ImageID – это идентификатор изображения, для которого вы хотите увидеть все команды, которые были запущены для него.

ImageID – это идентификатор изображения, для которого вы хотите увидеть все команды, которые были запущены для него.

Возвращаемое значение

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

пример

sudo docker history centos

Приведенная выше команда покажет все команды, которые были запущены для изображения centos .

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

История докеров

Докер – Работа с контейнерами

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

верх докера

С помощью этой команды вы можете увидеть основные процессы в контейнере.

Синтаксис

docker top ContainerID 

Опции

  • ContainerID – это идентификатор контейнера, для которого вы хотите увидеть топовые процессы.

ContainerID – это идентификатор контейнера, для которого вы хотите увидеть топовые процессы.

Возвращаемое значение

Вывод покажет процессы верхнего уровня в контейнере.

пример

sudo docker top 9f215ed0b0d3 

Приведенная выше команда покажет процессы верхнего уровня в контейнере.

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Docker Top

остановка докера

Эта команда используется для остановки работающего контейнера.

Синтаксис

docker stop ContainerID 

Опции

  • ContainerID – это идентификатор контейнера, который необходимо остановить.

ContainerID – это идентификатор контейнера, который необходимо остановить.

Возвращаемое значение

Вывод выдаст идентификатор остановленного контейнера.

пример

sudo docker stop 9f215ed0b0d3 

Приведенная выше команда остановит контейнер Docker 9f215ed0b0d3 .

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Докер Стоп

Докер Р.М.

Эта команда используется для удаления контейнера.

Синтаксис

docker rm ContainerID 

Опции

  • ContainerID – это идентификатор контейнера, который необходимо удалить.

ContainerID – это идентификатор контейнера, который необходимо удалить.

Возвращаемое значение

Вывод даст идентификатор удаленного контейнера.

пример

sudo docker rm 9f215ed0b0d3 

Приведенная выше команда удалит Docker-контейнер 9f215ed0b0d3 .

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Докер РМ

статистика докера

Эта команда используется для предоставления статистики работающего контейнера.

Синтаксис

docker stats ContainerID 

Опции

  • ContainerID – это идентификатор контейнера, для которого должна быть предоставлена ​​статистика.

ContainerID – это идентификатор контейнера, для которого должна быть предоставлена ​​статистика.

Возвращаемое значение

Выходные данные будут отображать использование процессора и памяти контейнера.

пример

sudo docker stats 9f215ed0b0d3 

Приведенная выше команда обеспечит использование ЦП и памяти Контейнера 9f215ed0b0d3 .

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Docker Stats

присоединение докера

Эта команда используется для подключения к работающему контейнеру.

Синтаксис

docker attach ContainerID 

Опции

  • ContainerID – это идентификатор контейнера, к которому вам нужно присоединиться.

ContainerID – это идентификатор контейнера, к которому вам нужно присоединиться.

Возвращаемое значение

Никто

пример

sudo docker attach 07b0b6f434fe 

Приведенная выше команда будет прикреплена к Docker-контейнеру 07b0b6f434fe .

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Docker Attach

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

Docker Attach Container

докер пауза

Эта команда используется для приостановки процессов в работающем контейнере.

Синтаксис

docker pause ContainerID 

Опции

  • ContainerID – это идентификатор контейнера, для которого необходимо приостановить процессы в контейнере.

ContainerID – это идентификатор контейнера, для которого необходимо приостановить процессы в контейнере.

Возвращаемое значение

ContainerID приостановленного контейнера.

пример

sudo docker pause 07b0b6f434fe 

Приведенная выше команда приостановит процессы в работающем контейнере 07b0b6f434fe .

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Докер Пауза

докер, пауза

Эта команда используется для приостановки процессов в работающем контейнере.

Синтаксис

docker unpause ContainerID

Опции

  • ContainerID – это идентификатор контейнера, для которого необходимо приостановить процессы в контейнере.

ContainerID – это идентификатор контейнера, для которого необходимо приостановить процессы в контейнере.

Возвращаемое значение

ContainerID запущенного контейнера.

пример

sudo docker unpause 07b0b6f434fe 

Приведенная выше команда отключит процессы в работающем контейнере: 07b0b6f434fe

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Docker Unpause

докер убить

Эта команда используется для уничтожения процессов в работающем контейнере.

Синтаксис

docker kill ContainerID

Опции

  • ContainerID – это идентификатор контейнера, для которого вам нужно убить процессы в контейнере.

ContainerID – это идентификатор контейнера, для которого вам нужно убить процессы в контейнере.

Возвращаемое значение

ContainerID запущенного контейнера.

пример

sudo docker kill 07b0b6f434fe 

Приведенная выше команда уничтожит процессы в работающем контейнере 07b0b6f434fe .

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Docker Kill

Docker – жизненный цикл контейнера

На следующем рисунке показан весь жизненный цикл контейнера Docker.

Жизненный цикл контейнера

  • Изначально контейнер Docker будет в созданном состоянии.

  • Затем контейнер Docker переходит в состояние выполнения при использовании команды Docker run .

  • Команда Docker kill используется для уничтожения существующего контейнера Docker.

  • Команда Docker pause используется для приостановки существующего контейнера Docker.

  • Команда остановки Docker используется для приостановки существующего контейнера Docker.

  • Команда запуска Docker используется для перевода контейнера из остановленного состояния в рабочее состояние.

Изначально контейнер Docker будет в созданном состоянии.

Затем контейнер Docker переходит в состояние выполнения при использовании команды Docker run .

Команда Docker kill используется для уничтожения существующего контейнера Docker.

Команда Docker pause используется для приостановки существующего контейнера Docker.

Команда остановки Docker используется для приостановки существующего контейнера Docker.

Команда запуска Docker используется для перевода контейнера из остановленного состояния в рабочее состояние.

Докер – Архитектура

На следующем рисунке показана стандартная и традиционная архитектура виртуализации .

Виртуализация

  • Сервер – это физический сервер, который используется для размещения нескольких виртуальных машин.

  • Хост-ОС является базовой машиной, такой как Linux или Windows.

  • Гипервизор – это VMWare или Windows Hyper V, который используется для размещения виртуальных машин.

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

  • Затем вы размещаете свои приложения поверх каждой гостевой ОС.

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

Хост-ОС является базовой машиной, такой как Linux или Windows.

Гипервизор – это VMWare или Windows Hyper V, который используется для размещения виртуальных машин.

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

Затем вы размещаете свои приложения поверх каждой гостевой ОС.

На следующем рисунке показано виртуализация нового поколения, которая включена через докеры. Давайте посмотрим на различные слои.

Различные слои

  • Сервер – это физический сервер, который используется для размещения нескольких виртуальных машин. Так что этот слой остается прежним.

  • Хост-ОС является базовой машиной, такой как Linux или Windows. Так что этот слой остается прежним.

  • Теперь приходит новое поколение, которое является двигателем Docker. Это используется для запуска операционной системы, которая раньше была виртуальными машинами в качестве контейнеров Docker.

  • Все приложения теперь работают как контейнеры Docker.

Сервер – это физический сервер, который используется для размещения нескольких виртуальных машин. Так что этот слой остается прежним.

Хост-ОС является базовой машиной, такой как Linux или Windows. Так что этот слой остается прежним.

Теперь приходит новое поколение, которое является двигателем Docker. Это используется для запуска операционной системы, которая раньше была виртуальными машинами в качестве контейнеров Docker.

Все приложения теперь работают как контейнеры Docker.

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

Докер – Контейнер и Хосты

Преимущество движка Docker заключается в том, что он предназначен для работы в различных операционных системах. Мы уже видели установку в Windows и видели все команды Docker в системах Linux. Теперь давайте посмотрим на различные команды Docker в ОС Windows.

Docker Images

Давайте запустим команду Docker images на хосте Windows.

Docker Images

Отсюда мы видим, что у нас есть два изображения – Ubuntu и Hello-World .

Запуск контейнера

Теперь давайте запустим контейнер в хосте Windows Docker.

Запуск контейнера

Мы видим, что, запустив контейнер, мы теперь можем запустить контейнер Ubuntu на хосте Windows.

Список всех контейнеров

Давайте перечислим все контейнеры на хосте Windows.

Список контейнеров

Остановка контейнера

Давайте теперь остановим работающий контейнер на хосте Windows.

Остановка контейнера

Итак, вы можете видеть, что движок Docker довольно последовательный, когда речь идет о разных хостах Docker, и он работает в Windows так же, как и в Linux.

Докер – Настройка

В этой главе мы рассмотрим различные варианты настройки Docker.

остановка сервисного докера

Эта команда используется для остановки процесса демона Docker.

Синтаксис

service docker stop 

Опции

Никто

Возвращаемое значение

Сообщение, показывающее, что процесс Docker остановлен.

пример

sudo service docker stop 

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Сервис Докер Стоп

запуск сервисного докера

Эта команда используется для запуска процесса демона Docker.

Синтаксис

service docker start 

Опции

Никто

Возвращаемое значение

Сообщение, показывающее, что процесс Docker запущен.

пример

sudo service docker start

Выход

Когда мы запустим указанную выше команду, она выдаст следующий результат:

Сервис Docker Start

Докер – Контейнеры и снаряды

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

Shell Shell

На приведенном выше снимке экрана вы можете заметить, что мы выполнили следующую команду:

sudo docker run –it centos /bin/bash 

Мы использовали эту команду для создания нового контейнера, а затем использовали команду Ctrl + P + Q для выхода из контейнера. Это гарантирует, что контейнер все еще существует даже после того, как мы выйдем из контейнера.

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

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

Прежде чем мы запустим команду nsenter , вам нужно сначала установить образ nsenter . Это можно сделать с помощью следующей команды –

docker run --rm -v /usr/local/bin:/target jpetazzo/nsenter

Nsenter Image

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

Проверьте команду

Как видно на скриншоте выше, мы сначала использовали команду docker ps, чтобы увидеть запущенные контейнеры. Мы видим, что существует один работающий контейнер с идентификатором ef42a4c5e663.

Затем мы используем команду Docker inspect для проверки конфигурации этого контейнера, а затем используем команду grep, чтобы просто отфильтровать ID процесса. И из вывода мы видим, что идентификатор процесса равен 2978.

Теперь, когда у нас есть идентификатор процесса, мы можем продолжить и использовать команду nsenter для подключения к контейнеру Docker.

nsenter

Этот метод позволяет присоединиться к контейнеру, не выходя из контейнера.

Синтаксис

Команда nsenter –m –u –n –p –i –t containerID

Опции

  • -u используется для упоминания пространства имен Uts

  • -m используется для упоминания пространства имен монтирования

  • -n используется для упоминания пространства имен сети

  • -p используется для упоминания пространства имен процесса

  • -i s, чтобы контейнер работал в интерактивном режиме.

  • -t используется для подключения потоков ввода-вывода контейнера к операционной системе хоста.

  • containerID – это идентификатор контейнера.

  • Команда – это команда для запуска в контейнере.

-u используется для упоминания пространства имен Uts

-m используется для упоминания пространства имен монтирования

-n используется для упоминания пространства имен сети

-p используется для упоминания пространства имен процесса

-i s, чтобы контейнер работал в интерактивном режиме.

-t используется для подключения потоков ввода-вывода контейнера к операционной системе хоста.

containerID – это идентификатор контейнера.

Команда – это команда для запуска в контейнере.

Возвращаемое значение

Никто

пример

sudo nsenter m u n p i t 2978 /bin/bash

Выход

Nsenter

Из вывода мы можем наблюдать следующие моменты –

  • Приглашение изменяется непосредственно в оболочке bash, когда мы запускаем команду nsenter .

  • Затем мы запускаем команду выхода . Теперь обычно, если вы не используете команду nsenter , контейнер будет уничтожен. Но вы заметите, что когда мы запускаем команду nsenter , контейнер все еще работает.

Приглашение изменяется непосредственно в оболочке bash, когда мы запускаем команду nsenter .

Затем мы запускаем команду выхода . Теперь обычно, если вы не используете команду nsenter , контейнер будет уничтожен. Но вы заметите, что когда мы запускаем команду nsenter , контейнер все еще работает.

Докер – Файл

В предыдущих главах мы видели различные файлы изображений, такие как Centos, которые загружаются из Docker-концентратора, из которого вы можете раскрутить контейнеры. Пример снова показан ниже.

Docker File

Если мы используем команду Docker images , мы можем видеть существующие образы в нашей системе. Из приведенного выше скриншота видно, что есть два изображения: centos и nsenter .

Но Docker также дает вам возможность создавать свои собственные изображения Docker, и это можно сделать с помощью Docker Files . Docker File – это простой текстовый файл с инструкциями по созданию ваших изображений.

Следующие шаги объясняют, как вам следует создать файл Docker.

Шаг 1 – Создайте файл с именем Docker File и отредактируйте его с помощью vim . Обратите внимание, что имя файла должно быть «Dockerfile» с «D» в качестве заглавной.

Редактировать Vim

Шаг 2 – Создайте свой файл Docker, используя следующие инструкции.

#This is a sample Image 
FROM ubuntu 
MAINTAINER demousr@gmail.com 

RUN apt-get update 
RUN apt-get install –y nginx 
CMD [“echo”,”Image created”] 

Следующие пункты должны быть отмечены о вышеупомянутом файле –

  • Первая строка «# Это образец изображения» – это комментарий. Вы можете добавить комментарии в Docker File с помощью команды #

  • Следующая строка должна начинаться с ключевого слова FROM . Он сообщает докеру, из какого базового изображения вы хотите основать свое изображение. В нашем примере мы создаем образ из образа Ubuntu .

  • Следующая команда – это человек, который собирается сохранить этот образ. Здесь вы указываете ключевое слово MAINTAINER и просто упоминаете идентификатор электронной почты.

  • Команда RUN используется для запуска инструкций для образа. В нашем случае мы сначала обновляем нашу систему Ubuntu, а затем устанавливаем сервер nginx на наш образ Ubuntu .

  • Последняя команда используется для отображения сообщения пользователю.

Первая строка «# Это образец изображения» – это комментарий. Вы можете добавить комментарии в Docker File с помощью команды #

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

Следующая команда – это человек, который собирается сохранить этот образ. Здесь вы указываете ключевое слово MAINTAINER и просто упоминаете идентификатор электронной почты.

Команда RUN используется для запуска инструкций для образа. В нашем случае мы сначала обновляем нашу систему Ubuntu, а затем устанавливаем сервер nginx на наш образ Ubuntu .

Последняя команда используется для отображения сообщения пользователю.

Шаг 3 – Сохраните файл. В следующей главе мы обсудим, как создать изображение.

Постройте изображение

Докер – Создание файлов

Мы создали файл Docker в последней главе. Пришло время создать файл Docker. Файл Docker может быть собран с помощью следующей команды –

docker build 

Давайте узнаем больше об этой команде.

сборка докера

Этот метод позволяет пользователям создавать свои собственные образы Docker.

Синтаксис

docker build  -t ImageName:TagName dir

Опции

  • -t – упомянуть тег к изображению

  • ImageName – это имя, которое вы хотите дать своему изображению.

  • TagName – это тег, который вы хотите присвоить своему изображению.

  • Dir – каталог, в котором находится файл Docker.

-t – упомянуть тег к изображению

ImageName – это имя, которое вы хотите дать своему изображению.

TagName – это тег, который вы хотите присвоить своему изображению.

Dir – каталог, в котором находится файл Docker.

Возвращаемое значение

Никто

пример

sudo docker build t myimage:0.1. 

Здесь myimage – это имя, которое мы даем изображению, а 0.1 – это номер тега, который мы даем нашему изображению.

Поскольку файл Docker находится в текущем рабочем каталоге, мы использовали “.” в конце команды указать текущий рабочий каталог.

Выход

Из выходных данных вы сначала увидите, что образ Ubuntu будет загружен из Docker Hub, поскольку на машине нет локального образа.

Нет изображения

Наконец, когда сборка будет завершена, все необходимые команды будут запущены на образе.

команды запускаются над изображением

После этого вы увидите успешно построенное сообщение и идентификатор нового изображения. Когда вы запустите команду Docker images , вы сможете увидеть новое изображение.

Встроенное сообщение и идентификатор

Теперь вы можете создавать контейнеры из вашего нового изображения.

Докер – публичные репозитории

Общедоступные репозитории могут использоваться для размещения образов Docker, которые могут использоваться всеми остальными. Примером являются изображения, которые доступны в Docker Hub. Большинство изображений, таких как Centos, Ubuntu и Jenkins, являются общедоступными для всех. Мы также можем сделать наши изображения доступными, опубликовав их в общедоступном репозитории на Docker Hub.

В нашем примере мы будем использовать репозиторий myimage, встроенный в главу «Создание файлов Docker», и загрузить это изображение в Docker Hub. Давайте сначала рассмотрим изображения на нашем хосте Docker, чтобы увидеть, что мы можем отправить в реестр Docker.

Myimage

Здесь у нас есть изображение myimage: 0.1, которое было создано как часть главы «Создание файлов Docker». Давайте использовать это для загрузки в публичный репозиторий Docker.

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

Шаг 1 – Войдите в Docker Hub и создайте свой репозиторий. Это хранилище, где будет храниться ваше изображение. Перейдите на https://hub.docker.com/ и войдите в систему, используя свои учетные данные.

Docker Hub

Шаг 2 – Нажмите кнопку «Создать репозиторий» на приведенном выше экране и создайте репозиторий с именем demorep . Убедитесь, что видимость хранилища общедоступна.

Demorep

Как только репозиторий создан, запишите команду pull, которая прикреплена к репозиторию.

вместилище

Команда pull, которая будет использоваться в нашем репозитории, выглядит следующим образом:

docker pull demousr/demorep

Шаг 3 – Теперь вернитесь к Docker Host. Здесь нам нужно пометить наше изображение новым репозиторием, созданным в Docker Hub. Мы можем сделать это с помощью команды тега Docker.

Мы узнаем больше об этой команде тегов позже в этой главе.

Шаг 4 – Введите команду Docker login для входа в репозиторий Docker Hub из командной строки. Команда входа в Docker запросит у вас имя пользователя и пароль для хранилища Docker Hub.

Команда входа в Docker

Шаг 5 – После того, как изображение было помечено, пришло время отправить изображение в хранилище Docker Hub. Мы можем сделать это с помощью команды Docker push . Мы узнаем больше об этой команде позже в этой главе.

тег докера

Этот метод позволяет пометить изображение в соответствующем хранилище.

Синтаксис

docker tag imageID Repositoryname 

Опции

  • imageID – это ImageID, который необходимо пометить в хранилище.

  • Имя репозитория – это имя репозитория, к которому должен быть привязан ImageID.

imageID – это ImageID, который необходимо пометить в хранилище.

Имя репозитория – это имя репозитория, к которому должен быть привязан ImageID.

Возвращаемое значение

Никто

пример

sudo docker tag ab0c1d3744dd demousr/demorep:1.0

Выход

Пример вывода приведенного выше примера приведен ниже.

Docker Tag

толчок докера

Этот метод позволяет передавать изображения в Docker Hub.

Синтаксис

docker push Repositoryname 

Опции

  • Имя репозитория – это имя репозитория, которое необходимо отправить в Docker Hub.

Имя репозитория – это имя репозитория, которое необходимо отправить в Docker Hub.

Возвращаемое значение

Длинный идентификатор хранилища отправляется в Docker Hub.

пример

sudo docker push demousr/demorep:1.0 

Выход

Docker Push

Если вы вернетесь на страницу Docker Hub и зайдете в свой репозиторий, вы увидите имя тега в репозитории.

Имя тега в репозитории

Теперь давайте попробуем выгрузить репозиторий, который мы загрузили, на наш хост Docker. Давайте сначала удалим изображения, myimage: 0.1 и demousr / demorep: 1.0 , с локального хоста Docker. Давайте используем команду Pucker Docker, чтобы извлечь хранилище из Docker Hub.

Команда Docker Pull

На приведенном выше снимке экрана видно, что команда Pucker Docker взяла наш новый репозиторий из Docker Hub и разместила его на нашей машине.

Docker – Управление портами

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

В нашем примере мы собираемся загрузить контейнер Jenkins из Docker Hub. Затем мы сопоставим номер порта Jenkins с номером порта на хосте Docker.

Шаг 1 – Во-первых, вам нужно выполнить простую регистрацию в Docker Hub.

просто подписаться

Шаг 2 – Как только вы зарегистрируетесь, вы войдете в Docker Hub.

Зарегистрированный Docker Hub

Шаг 3 – Далее, давайте посмотрим и найдем изображение Дженкинса.

Команда запуска

Шаг 4 – Если вы прокрутите вниз на той же странице, вы увидите команду Docker pull . Это будет использоваться для загрузки образа Jenkins на локальный сервер Ubuntu.

Локальный сервер Ubuntu

Шаг 5 – Теперь перейдите на сервер Ubuntu и выполните команду –

sudo docker pull jenkins 

Проверьте изображение

Шаг 6 – Чтобы понять, какие порты открываются контейнером, вы должны использовать команду Docker inspect для проверки образа.

Давайте теперь узнаем больше об этой команде осмотра .

докер проверяет

Этот метод позволяет возвращать низкоуровневую информацию о контейнере или изображении.

Синтаксис

docker inspect Container/Image 

Опции

  • Контейнер / Изображение – Контейнер или изображение для проверки

Контейнер / Изображение – Контейнер или изображение для проверки

Возвращаемое значение

Низкоуровневая информация об изображении или контейнере в формате JSON.

пример

sudo docker inspect jenkins 

Выход

Докер проверяет вывод

Вывод команды inspect дает вывод JSON. Если мы наблюдаем вывод, мы видим, что есть раздел «ExposedPorts» и видим, что упоминаются два порта. Один – это порт данных 8080, а другой – порт управления 50000.

Чтобы запустить Jenkins и отобразить порты, вам нужно изменить команду запуска Docker и добавить опцию «p», которая определяет отображение портов. Итак, вам нужно выполнить следующую команду –

sudo docker run -p 8080:8080 -p 50000:50000 jenkins 

Левая часть сопоставления номеров портов – это порт хоста Docker для сопоставления, а правая часть – номер порта контейнера Docker.

Когда вы откроете браузер и перейдете к хосту Docker через порт 8080, вы увидите, что Jenkins запущен и работает.

Разблокировать дженкинс

Докер – Частные Реестры

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

Шаг 1 – Используйте команду Docker run для загрузки частного реестра. Это можно сделать с помощью следующей команды.

sudo docker run –d –p 5000:5000 –-name registry registry:2

Следующие пункты должны быть отмечены о вышеупомянутой команде –

  • Реестр – это контейнер, управляемый Docker, который может использоваться для размещения частных репозиториев.

  • Номер порта, предоставляемый контейнером, равен 5000. Следовательно, с помощью команды –p мы сопоставляем этот номер порта с номером порта 5000 на нашем локальном хосте.

  • Мы просто помечаем контейнер реестра как «2», чтобы дифференцировать его на хосте Docker.

  • Опция –d используется для запуска контейнера в отдельном режиме. Это так, что контейнер может работать в фоновом режиме

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

Номер порта, предоставляемый контейнером, равен 5000. Следовательно, с помощью команды –p мы сопоставляем этот номер порта с номером порта 5000 на нашем локальном хосте.

Мы просто помечаем контейнер реестра как «2», чтобы дифференцировать его на хосте Docker.

Опция –d используется для запуска контейнера в отдельном режиме. Это так, что контейнер может работать в фоновом режиме

Отдельный режим

Шаг 2 – Давайте сделаем докер ps, чтобы увидеть, что контейнер реестра действительно работает.

Докер PS

Теперь мы подтвердили, что контейнер реестра действительно работает.

Шаг 3 – Теперь давайте пометим одно из наших существующих изображений, чтобы мы могли отправить его в наш локальный репозиторий. В нашем примере, поскольку у нас есть изображение centos, доступное локально, мы собираемся пометить его в нашем частном репозитории и добавить имя тега centos .

sudo docker tag 67591570dd29 localhost:5000/centos 

Следующие пункты должны быть отмечены о вышеупомянутой команде –

  • 67591570dd29 относится к идентификатору изображения для изображения centos .

  • localhost: 5000 – это местоположение нашего частного хранилища.

  • Мы помечаем имя хранилища как centos в нашем личном хранилище.

67591570dd29 относится к идентификатору изображения для изображения centos .

localhost: 5000 – это местоположение нашего частного хранилища.

Мы помечаем имя хранилища как centos в нашем личном хранилище.

Частный репозиторий

Шаг 4 – Теперь давайте с помощью команды Docker push отправим репозиторий в наш приватный репозиторий.

sudo docker push localhost:5000/centos 

Здесь мы отправляем изображение centos в частный репозиторий, размещенный на localhost: 5000 .

Localhost

Шаг 5 – Теперь давайте удалим локальные изображения, которые мы имеем для centos, используя команды docker rmi . Затем мы можем загрузить необходимое изображение centos из нашего частного репозитория.

sudo docker rmi centos:latest 
sudo docker rmi 67591570dd29

Команды Docker RMI

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

sudo docker pull localhost:5000/centos

Здесь мы переносим изображение centos в частный репозиторий, размещенный на localhost: 5000 .

Потянув Centos Image

Если вы теперь видите изображения в вашей системе, вы также увидите изображение centos .

Docker – Создание файла Docker веб-сервера

Мы уже узнали, как использовать Docker File для создания наших собственных пользовательских образов. Теперь давайте посмотрим, как мы можем создать образ веб-сервера, который можно использовать для создания контейнеров.

В нашем примере мы собираемся использовать веб-сервер Apache в Ubuntu для создания нашего образа. Давайте выполним шаги, приведенные ниже, чтобы создать файл Docker нашего веб-сервера.

Шаг 1 – Первый шаг – создать файл Docker. Давайте использовать vim и создадим файл Docker со следующей информацией.

FROM ubuntu 
RUN apt-get update 
RUN apt-get install –y apache2 
RUN apt-get install –y apache2-utils 
RUN apt-get clean 
EXPOSE 80 CMD [“apache2ctl”, “-D”, “FOREGROUND”]

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

  • Сначала мы создаем наш образ из базового образа Ubuntu.

  • Далее мы собираемся использовать команду RUN для обновления всех пакетов в системе Ubuntu.

  • Далее мы используем команду RUN для установки apache2 на наш образ.

  • Далее мы используем команду RUN для установки необходимых пакетов apache2 для нашего образа.

  • Далее мы используем команду RUN для очистки любых ненужных файлов из системы.

  • Команда EXPOSE используется для предоставления порта 80 Apache в контейнере хосту Docker.

  • Наконец, команда CMD используется для запуска apache2 в фоновом режиме.

Сначала мы создаем наш образ из базового образа Ubuntu.

Далее мы собираемся использовать команду RUN для обновления всех пакетов в системе Ubuntu.

Далее мы используем команду RUN для установки apache2 на наш образ.

Далее мы используем команду RUN для установки необходимых пакетов apache2 для нашего образа.

Далее мы используем команду RUN для очистки любых ненужных файлов из системы.

Команда EXPOSE используется для предоставления порта 80 Apache в контейнере хосту Docker.

Наконец, команда CMD используется для запуска apache2 в фоновом режиме.

Apache2

Теперь, когда данные файла введены, просто сохраните файл.

Шаг 2 – Запустите команду сборки Docker, чтобы создать файл Docker. Это можно сделать с помощью следующей команды –

sudo docker build –t=”mywebserver” . 

Мы помечаем наше изображение как mywebserver . Как только изображение будет построено, вы получите успешное сообщение о том, что файл создан.

Mywebservers

Шаг 3 – Теперь, когда файл веб-сервера создан, пришло время создать контейнер из изображения. Мы можем сделать это с помощью команды запуска Docker.

sudo docker run –d –p 80:80 mywebserver 

Команда запуска Docker

Следующие пункты должны быть отмечены о вышеупомянутой команде –

  • Номер порта, предоставляемый контейнером, равен 80. Следовательно, с помощью команды –p мы сопоставляем этот номер порта с номером порта 80 на нашем локальном хосте.

  • Опция –d используется для запуска контейнера в отдельном режиме. Это так, что контейнер может работать в фоновом режиме.

Номер порта, предоставляемый контейнером, равен 80. Следовательно, с помощью команды –p мы сопоставляем этот номер порта с номером порта 80 на нашем локальном хосте.

Опция –d используется для запуска контейнера в отдельном режиме. Это так, что контейнер может работать в фоновом режиме.

Если вы перейдете на порт 80 хоста Docker в своем веб-браузере, вы увидите, что Apache запущен и работает.

Apache работает

Docker – Команды команд

Докер имеет множество команд команд. Это команды, которые помещаются в Docker File. Давайте посмотрим на те, которые доступны.

CMD Инструкция

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

Синтаксис

CMD command param1 

Опции

  • command – это команда, запускаемая при запуске контейнера.

  • param1 – это параметр, введенный в команду.

command – это команда, запускаемая при запуске контейнера.

param1 – это параметр, введенный в команду.

Возвращаемое значение

Команда будет выполнена соответственно.

пример

В нашем примере мы введем простое эхо Hello World в наш файл Docker, создадим изображение и запустим из него контейнер.

Шаг 1 – Создайте файл Docker с помощью следующих команд –

FROM ubuntu 
MAINTAINER demousr@gmail.com 
CMD [“echo” , “hello world”] 

Здесь CMD просто используется для печати Hello World .

CMD

Шаг 2 – Создайте образ с помощью команды сборки Docker.

Команда сборки

Шаг 3 – Запустите контейнер с картинки.

Запустить контейнер

ТОЧКА ВХОДА

Эта команда также может использоваться для выполнения команд во время выполнения для контейнера. Но мы можем быть более гибкими с помощью команды ENTRYPOINT.

Синтаксис

ENTRYPOINT command param1 

Опции

  • command – это команда, запускаемая при запуске контейнера.

  • param1 – это параметр, введенный в команду.

command – это команда, запускаемая при запуске контейнера.

param1 – это параметр, введенный в команду.

Возвращаемое значение

Команда будет выполнена соответственно.

пример

Давайте посмотрим на пример, чтобы понять больше о ENTRYPOINT. В нашем примере мы введем простую команду echo в нашем файле Docker, создадим образ и запустим из него контейнер.

Шаг 1 – Создайте файл Docker с помощью следующих команд –

FROM ubuntu 
MAINTAINER demousr@gmail.com 
ENTRYPOINT [“echo”]

ТОЧКА ВХОДА

Шаг 2 – Создайте образ с помощью команды сборки Docker.

Команда сборки Docker

Шаг 3 – Запустите контейнер с картинки.

Контейнер из изображения

ENV

Эта команда используется для установки переменных среды в контейнере.

Синтаксис

ENV key value 

Опции

  • Ключ – это ключ для переменной среды.

  • значение – это значение для переменной среды.

Ключ – это ключ для переменной среды.

значение – это значение для переменной среды.

Возвращаемое значение

Команда будет выполнена соответственно.

пример

В нашем примере мы введем простую команду echo в нашем файле Docker, создадим образ и запустим из него контейнер.

Шаг 1 – Создайте файл Docker с помощью следующих команд –

FROM ubuntu 
MAINTAINER demousr@gmail.com 
ENV var1=Tutorial var2=point 

ENV

Шаг 2 – Создайте образ с помощью команды сборки Docker.

ENV Build Docker Команда

Шаг 3 – Запустите контейнер с картинки.

ENV запустить контейнер

Шаг 4 – Наконец, выполните команду env, чтобы увидеть переменные среды.

Команда ENV

WORKDIR

Эта команда используется для установки рабочего каталога контейнера.

Синтаксис

WORKDIR dirname 

Опции

  • dirname – новый рабочий каталог. Если каталог не существует, он будет добавлен.

dirname – новый рабочий каталог. Если каталог не существует, он будет добавлен.

Возвращаемое значение

Команда будет выполнена соответственно.

пример

В нашем примере мы введем простую команду echo в нашем файле Docker, создадим образ и запустим из него контейнер.

Шаг 1 – Создайте файл Docker с помощью следующих команд –

FROM ubuntu 
MAINTAINER demousr@gmail.com 
WORKDIR /newtemp 
CMD pwd

WORKDIR

Шаг 2 – Создайте образ с помощью команды сборки Docker.

Workdir Build Command

Шаг 3 – Запустите контейнер с картинки.

WORKDIR Run Command

Докер – Контейнерное соединение

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

Шаг 1. Загрузите изображение Jenkins, если оно еще не создано, с помощью команды Jenkins pull .

Связывание контейнера

Шаг 2 – Как только изображение станет доступным, запустите контейнер, но на этот раз вы можете указать имя контейнера, используя опцию –-name . Это будет наш исходный контейнер .

Вариант имени

Шаг 3 – Затем пришло время запустить контейнер назначения, но на этот раз мы свяжем его с нашим исходным контейнером. Для нашего контейнера назначения мы будем использовать стандартный образ Ubuntu.

Стандартный образ Ubuntu

Когда вы выполните Docker PS , вы увидите, что оба контейнера работают.

Шаг 4 – Теперь прикрепите к принимающему контейнеру.

Прием контейнера

Затем запустите команду env . Вы заметите новые переменные для связи с исходным контейнером.

Новые переменные

Source Continer

Докер – Хранение

Драйверы хранилища

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

Технология Драйвер хранилища
OverlayFS оверлей или оверлей2
AUFS AUFS
Btrfs brtfs
Диспетчер устройств Диспетчер устройств
VFS VFS
ZFS ZFS

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

AUFS

  • Это стабильный драйвер; может быть использован для готовых приложений.

  • Он имеет хорошее использование памяти и обеспечивает бесперебойную работу Docker для контейнеров.

  • Существует высокая активность записи, связанная с этим драйвером, который следует учитывать.

  • Это хорошо для систем, которые имеют Платформу как тип обслуживания.

Это стабильный драйвер; может быть использован для готовых приложений.

Он имеет хорошее использование памяти и обеспечивает бесперебойную работу Docker для контейнеров.

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

Это хорошо для систем, которые имеют Платформу как тип обслуживания.

Devicemapper

  • Это стабильный драйвер; обеспечивает беспроблемное взаимодействие с докером.

  • Этот драйвер хорош для тестирования приложений в лаборатории.

  • Этот драйвер соответствует основным функциональным возможностям ядра Linux.

Это стабильный драйвер; обеспечивает беспроблемное взаимодействие с докером.

Этот драйвер хорош для тестирования приложений в лаборатории.

Этот драйвер соответствует основным функциональным возможностям ядра Linux.

Btrfs

  • Этот драйвер соответствует основным функциональным возможностям ядра Linux.

  • Существует высокая активность записи, связанная с этим драйвером, который следует учитывать.

  • Этот драйвер подходит для случаев, когда вы поддерживаете несколько пулов сборки.

Этот драйвер соответствует основным функциональным возможностям ядра Linux.

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

Этот драйвер подходит для случаев, когда вы поддерживаете несколько пулов сборки.

Ovelay

  • Это стабильный драйвер, который соответствует основным функциям ядра Linux.

  • У него хорошее использование памяти.

  • Этот драйвер хорош для тестирования приложений в лаборатории.

Это стабильный драйвер, который соответствует основным функциям ядра Linux.

У него хорошее использование памяти.

Этот драйвер хорош для тестирования приложений в лаборатории.

ZFS

  • Это стабильный драйвер, и он хорош для тестирования приложений в лаборатории.

  • Это хорошо для систем, работающих по типу «платформа как услуга».

Это стабильный драйвер, и он хорош для тестирования приложений в лаборатории.

Это хорошо для систем, работающих по типу «платформа как услуга».

Чтобы увидеть используемый драйвер хранилища, введите команду docker info .

Синтаксис

docker info 

Опции

Никто

Возвращаемое значение

Команда предоставит всю относительную информацию о компоненте Docker, установленном на Docker Host.

пример

sudo docker info 

Выход

Следующий вывод показывает, что основным драйвером является драйвер aufs и что корневой каталог хранится в / var / lib / docker / aufs .

AUFS Driver

Объемы данных

В Docker у вас есть отдельный том, который можно использовать в разных контейнерах. Они известны как объемы данных . Некоторые особенности объема данных –

  • Они инициализируются при создании контейнера.
  • Они могут быть общими, а также повторно использованы во многих контейнерах.
  • Любые изменения самого тома могут быть сделаны напрямую.
  • Они существуют даже после удаления контейнера.

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

sudo docker inspect Jenkins > tmp.txt

Когда вы просматриваете текстовый файл с помощью команды more , вы увидите запись как JENKINS_HOME = / var / Jenkins_home .

Это отображение, которое выполняется внутри контейнера через изображение Jenkins.

Объемы данных

Теперь предположим, что вы хотите отобразить том в контейнере на локальный том, тогда вам нужно указать опцию –v при запуске контейнера. Пример показан ниже –

sudo docker run d v /home/demo:/var/jenkins_home p 8080:8080 p 50000:50000 jenkins 

Параметр –v используется для сопоставления тома в контейнере, который является / var / jenkins_home, с местоположением на нашем хосте Docker, которое является / home / demo .

V вариант

Теперь, если вы перейдете в каталог / home / demo на вашем Docker Host после запуска вашего контейнера, вы увидите все файлы контейнера, присутствующие там.

Контейнерные Файлы

Изменение драйвера хранилища для контейнера

Если вы хотите перейти на драйвер хранилища, используемый для контейнера, вы можете сделать это при запуске контейнера. Это можно сделать с помощью параметра –volume-driver при использовании команды docker run . Пример приведен ниже –

sudo docker run d volume-driver=flocker 
   v /home/demo:/var/jenkins_home p 8080:8080 p 50000:50000 jenkins

Параметр –volume-driver используется для указания другого драйвера хранилища для контейнера.

Громкость драйвера

Чтобы подтвердить, что драйвер был изменен, сначала давайте воспользуемся командой docker ps, чтобы увидеть запущенные контейнеры и получить идентификатор контейнера. Итак, сначала выполните следующую команду –

sudo docker ps

Затем выполните проверку докера для контейнера и поместите вывод в текстовый файл с помощью команды.

sudo docker inspect 9bffb1bfebee > temp.txt 

Докер против командования

Если вы просмотрите текстовый файл и перейдете к строке с надписью VolumeDriver , вы увидите, что имя драйвера было изменено.

Имя драйвера изменилось

Создание тома

Том можно создать заранее с помощью команды docker . Давайте узнаем больше об этой команде.

Синтаксис

docker volume create –-name=volumename –-opt options

Опции

  • name – это имя тома, который нужно создать.

  • opt – это опции, которые вы можете предоставить при создании тома.

name – это имя тома, который нужно создать.

opt – это опции, которые вы можете предоставить при создании тома.

Возвращаемое значение

Команда выведет имя созданного тома.

пример

sudo docker volume create –-name = demo opt o = size = 100m 

В приведенной выше команде мы создаем том размером 100 МБ с именем demo.

Выход

Вывод вышеуказанной команды показан ниже –

Создание тома

Перечисление всех томов

Вы также можете перечислить все тома докеров на хосте докеров . Более подробная информация об этой команде приведена ниже –

Синтаксис

docker volume ls 

Опции

Никто

Возвращаемое значение

Команда выведет все тома на хост докера .

пример

sudo docker volume ls

Выход

Вывод вышеуказанной команды показан ниже –

Вывод списка всех томов

Докер – Сеть

Docker заботится о сетевых аспектах, чтобы контейнеры могли взаимодействовать с другими контейнерами, а также с Docker Host. Если вы выполните ifconfig на Docker Host, вы увидите Docker Ethernet адаптер. Этот адаптер создается, когда Docker установлен на Docker Host.

IFCONFIG

Это мост между Docker Host и Linux Host. Теперь давайте посмотрим на некоторые команды, связанные с сетью в Docker.

Список всех сетей Docker

Эта команда может быть использована для вывода списка всех сетей, связанных с Docker на хосте.

Синтаксис

docker network ls 

Опции

Никто

Возвращаемое значение

Команда выведет все сети на Docker Host.

пример

sudo docker network ls

Выход

Вывод вышеуказанной команды показан ниже

Docker Networks

Проверка сети Docker

Если вы хотите увидеть более подробную информацию о сети, связанной с Docker, вы можете использовать команду Docker network inspect .

Синтаксис

docker network inspect networkname 

Опции

  • имя сети – это имя сети, которую нужно проверить.

имя сети – это имя сети, которую нужно проверить.

Возвращаемое значение

Команда выведет все подробности о сети.

пример

sudo docker network inspect bridge 

Выход

Вывод вышеуказанной команды показан ниже –

Проверка сети Docker

Теперь давайте запустим контейнер и посмотрим, что произойдет, когда мы снова проверим сеть. Давайте раскрутим контейнер Ubuntu с помощью следующей команды –

sudo docker run –it ubuntu:latest /bin/bash 

Запустить контейнер в сети

Теперь, если мы проверим имя нашей сети с помощью следующей команды, вы увидите, что контейнер подключен к мосту.

sudo docker network inspect bridge

Контейнер прикреплен к мосту

Создание вашей новой сети

Можно создать сеть в Docker перед запуском контейнеров. Это можно сделать с помощью следующей команды –

Синтаксис

docker network create –-driver drivername name 

Опции

  • drivername – это имя, используемое для сетевого драйвера.

  • имя – это имя, данное сети.

drivername – это имя, используемое для сетевого драйвера.

имя – это имя, данное сети.

Возвращаемое значение

Команда выведет длинный идентификатор для новой сети.

пример

sudo docker network create –-driver bridge new_nw 

Выход

Вывод вышеуказанной команды показан ниже –

Длинный идентификатор

Теперь вы можете подключить новую сеть при запуске контейнера. Итак, давайте раскрутим контейнер Ubuntu с помощью следующей команды –

sudo docker run –it –network=new_nw ubuntu:latest /bin/bash

Новая сеть

И теперь, когда вы проверяете сеть с помощью следующей команды, вы увидите контейнер, подключенный к сети.

sudo docker network inspect new_nw 

Новый СЗ

Docker – Настройка Node.js

Node.js – это инфраструктура JavaScript, которая используется для разработки серверных приложений. Это платформа с открытым исходным кодом, разработанная для работы в различных операционных системах. Поскольку Node.js является популярной средой разработки, Docker также обеспечил поддержку приложений Node.js.

Теперь мы увидим различные шаги для запуска и запуска контейнера Docker для Node.js.

Шаг 1 – Первый шаг – извлечь изображение из Docker Hub. Когда вы войдете в Docker Hub, вы сможете найти и увидеть изображение для Node.js, как показано ниже. Просто введите Node в поле поиска и нажмите на ссылку узла (официальную), которая появляется в результатах поиска.

Извлечь изображение из Docker Hub

Шаг 2 – Вы увидите, что команда Docker Pull для узла в деталях хранилища в Docker Hub.

Документация

Шаг 3. На Docker Host используйте команду Docker pull, как показано выше, чтобы загрузить последний образ узла из Docker Hub.

Последнее изображение узла

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

Тяга завершена

Шаг 4 – На Docker Host, давайте воспользуемся редактором vim и создадим один файл примера Node.js. В этом файле мы добавим простую команду для отображения «HelloWorld» в командной строке.

Vim Editor

В файле Node.js добавим следующий оператор:

Console.log(‘Hello World’);

Это выведет фразу «Hello World», когда мы запустим ее через Node.js.

Привет, мир, фраза

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

Шаг 5 – Чтобы запустить наш скрипт Node.js с помощью контейнера Node Docker, нам нужно выполнить следующую инструкцию:

sudo docker run –it –rm –name = HelloWorld –v “$PWD”:/usr/src/app 
   –w /usr/src/app node node HelloWorld.js

Следующие пункты должны быть отмечены о вышеупомянутой команде –

  • Параметр –rm используется для удаления контейнера после его запуска.

  • Мы даем имя контейнеру под названием «HelloWorld».

  • Мы упоминаем о том, чтобы отобразить том в контейнере, который является / usr / src / app, в наш текущий текущий рабочий каталог. Это сделано для того, чтобы контейнер узла взял наш скрипт HelloWorld.js, который присутствует в нашем рабочем каталоге на Docker Host.

  • Опция –w используется для указания рабочего каталога, используемого Node.js.

  • Первый параметр узла используется для указания запуска образа узла.

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

  • И, наконец, мы упоминаем название нашего сценария.

Параметр –rm используется для удаления контейнера после его запуска.

Мы даем имя контейнеру под названием «HelloWorld».

Мы упоминаем о том, чтобы отобразить том в контейнере, который является / usr / src / app, в наш текущий текущий рабочий каталог. Это сделано для того, чтобы контейнер узла взял наш скрипт HelloWorld.js, который присутствует в нашем рабочем каталоге на Docker Host.

Опция –w используется для указания рабочего каталога, используемого Node.js.

Первый параметр узла используется для указания запуска образа узла.

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

И, наконец, мы упоминаем название нашего сценария.

Затем мы получим следующий вывод. И из результатов мы можем ясно видеть, что контейнер Node работал как контейнер и выполнял скрипт HelloWorld.js.

HelloWorld JS Script

Докер – Настройка MongoDB

MongoDB – известная документно-ориентированная база данных, используемая многими современными веб-приложениями. Поскольку MongoDB является популярной базой данных для разработки, Docker также обеспечил поддержку MongoDB.

Теперь мы увидим различные шаги для запуска и запуска контейнера Docker для MongoDB.

Шаг 1 – Первый шаг – извлечь изображение из Docker Hub. Когда вы войдете в Docker Hub, вы сможете искать и видеть изображение для Mongo, как показано ниже. Просто введите Mongo в поле поиска и нажмите на официальную ссылку Mongo, которая появляется в результатах поиска.

Монго БД

Шаг 2 – Вы увидите, что Docker вытягивает команду для Mongo в деталях хранилища в Docker Hub.

Команда подтягивания докера для MONGO

Шаг 3 – На Docker Host используйте команду Docker pull, как показано выше, чтобы загрузить последний образ Mongo из Docker Hub.

последнее изображение Монго

Команда Pull MongoDB

Шаг 4. Теперь, когда у нас есть образ для Mongo, давайте сначала запустим контейнер MongoDB, который будет нашим экземпляром для MongoDB. Для этого мы выдадим следующую команду –

sudo docker run -it -d mongo

О вышеупомянутой команде можно отметить следующие моменты:

  • Опция –it используется для запуска контейнера в интерактивном режиме.

  • Опция –d используется для запуска контейнера как процесса демона.

  • И, наконец, мы создаем контейнер из образа Монго.

Опция –it используется для запуска контейнера в интерактивном режиме.

Опция –d используется для запуска контейнера как процесса демона.

И, наконец, мы создаем контейнер из образа Монго.

Затем вы можете выполнить команду docker ps, чтобы увидеть запущенные контейнеры –

MongoDB Контейнер

Обратите внимание на следующие моменты –

  • Название контейнера: tender_poitras . Это имя будет другим, так как имя контейнеров будет меняться, когда вы раскручиваете контейнер. Но просто запишите контейнер, который вы запустили.

  • Затем также обратите внимание на номер порта, на котором он работает. Он прослушивает порт TCP 27017.

Название контейнера: tender_poitras . Это имя будет другим, так как имя контейнеров будет меняться, когда вы раскручиваете контейнер. Но просто запишите контейнер, который вы запустили.

Затем также обратите внимание на номер порта, на котором он работает. Он прослушивает порт TCP 27017.

Шаг 5 – Теперь давайте раскрутим еще один контейнер, который будет действовать как наш клиент, который будет использоваться для подключения к базе данных MongoDB. Давайте выполним следующую команду для этого –

sudo docker run –it –link=tender_poitras:mongo mongo /bin/bash 

О вышеупомянутой команде можно отметить следующие моменты:

  • Опция –it используется для запуска контейнера в интерактивном режиме.

  • Теперь мы связываем наш новый контейнер с уже запущенным контейнером сервера MongoDB. Здесь нужно указать имя уже запущенного контейнера.

  • Затем мы указываем, что хотим запустить контейнер Mongo в качестве нашего клиента, а затем запустить оболочку bin / bash в нашем новом контейнере.

Опция –it используется для запуска контейнера в интерактивном режиме.

Теперь мы связываем наш новый контейнер с уже запущенным контейнером сервера MongoDB. Здесь нужно указать имя уже запущенного контейнера.

Затем мы указываем, что хотим запустить контейнер Mongo в качестве нашего клиента, а затем запустить оболочку bin / bash в нашем новом контейнере.

Бин Баш

Теперь вы будете в новом контейнере.

Шаг 6 – Запустите команду env в новом контейнере, чтобы увидеть подробную информацию о том, как подключиться к контейнеру сервера MongoDB.

ENV Контейнер Новая Команда

Шаг 6 – Теперь пришло время подключиться к серверу MongoDB из клиентского контейнера. Мы можем сделать это с помощью следующей команды –

mongo 172.17.0.2:27017 

Следующие пункты должны быть отмечены о вышеупомянутой команде

  • Команда mongo – это команда client mongo, которая используется для подключения к базе данных MongoDB.

  • IP и номер порта – это то, что вы получаете, когда используете команду env .

Команда mongo – это команда client mongo, которая используется для подключения к базе данных MongoDB.

IP и номер порта – это то, что вы получаете, когда используете команду env .

После запуска команды вы будете подключены к базе данных MongoDB.

База данных MongoDB

Затем вы можете запустить любую команду MongoDB в командной строке. В нашем примере мы запускаем следующую команду –

use demo

Эта команда является командой MongoDB, которая используется для переключения на демонстрацию имени базы данных. Если база данных недоступна, она будет создана.

Название базы данных DEMO

Теперь вы успешно создали контейнер MongoDB клиента и сервера.

Докер – Настройка NGINX

NGINX – это популярное облегченное веб-приложение, которое используется для разработки серверных приложений. Это веб-сервер с открытым исходным кодом, разработанный для работы в различных операционных системах. Поскольку nginx является популярным веб-сервером для разработки, Docker обеспечил поддержку nginx .

Теперь мы увидим различные шаги по запуску контейнера Docker для nginx .

Шаг 1 – Первый шаг – извлечь изображение из Docker Hub. Когда вы войдете в Docker Hub, вы сможете искать и видеть изображение для nginx, как показано ниже. Просто введите nginx в поле поиска и нажмите на ссылку nginx (официальную), которая появляется в результатах поиска.

Официальная ссылка NGINX

Шаг 2 – Вы увидите, что команда Docker pull для nginx в деталях хранилища в Docker Hub.

Команда Docker Pull для NGINX

Шаг 3 – На Docker Host используйте команду Docker pull, как показано выше, чтобы загрузить последний образ nginx из Docker Hub.

NGINX Image

Шаг 4 – Теперь давайте запустим контейнер nginx с помощью следующей команды.

sudo docker run –p 8080:80 –d nginx

Мы выставляем порт на сервере nginx, который является портом 80, на порт 8080 на Docker Host.

NGINX Server

После запуска команды вы получите следующий вывод, если перейдете по URL-адресу http: // dockerhost: 8080 . Это показывает, что контейнер nginx запущен и работает.

NGINX Контейнер

Шаг 5 – Давайте посмотрим на другой пример, где мы можем разместить простую веб-страницу в нашем контейнере ngnix . В нашем примере мы создадим простой файл HelloWorld.html и разместим его в нашем контейнере nginx .

Давайте сначала создадим HTML-файл с именем HelloWorld.html.

HTML-файл

Давайте добавим простую строку Hello World в HTML-файл.

Простая линия Hello World

Затем запустим следующую команду Docker.

sudo docker run –p 8080:80 –v 
   “$PWD”:/usr/share/nginx/html:ro –d nginx 

Следующие пункты должны быть отмечены о вышеупомянутой команде –

  • Мы выставляем порт на сервере nginx, который является портом 80, на порт 8080 на Docker Host.

  • Затем мы присоединяем том к контейнеру, который является / usr / share / nginx / html, к нашему текущему рабочему каталогу. Здесь хранится наш файл HelloWorld.html.

Мы выставляем порт на сервере nginx, который является портом 80, на порт 8080 на Docker Host.

Затем мы присоединяем том к контейнеру, который является / usr / share / nginx / html, к нашему текущему рабочему каталогу. Здесь хранится наш файл HelloWorld.html.

Рабочий каталог

Теперь, если мы перейдем по URL-адресу http: // dockerhost: 8080 / HelloWorld.html, мы получим следующий результат, как и ожидалось:

Ожидаемый выход

Докер – Панель инструментов

Во вводных главах мы увидели установку панели инструментов Docker в Windows. Панель инструментов Docker разработана таким образом, чтобы контейнеры Docker можно было запускать в Windows и MacOS. Сайт для панели инструментов в Windows – https://docs.docker.com/docker-for-windows/

Панель инструментов в Windows

Для Windows вам нужно иметь Windows 10 или Windows Server 2016 с включенным Hyper-V.

Панель инструментов состоит из следующих компонентов –

  • Docker Engine – используется как базовый механизм или демон Docker, используемый для запуска контейнеров Docker.

  • Docker Machine – для запуска команд Docker.

  • Docker Compose для запуска команд Docker compose.

  • Kinematic – это графический интерфейс Docker, созданный для Windows и Mac OS.

  • Oracle virtualbox

Docker Engine – используется как базовый механизм или демон Docker, используемый для запуска контейнеров Docker.

Docker Machine – для запуска команд Docker.

Docker Compose для запуска команд Docker compose.

Kinematic – это графический интерфейс Docker, созданный для Windows и Mac OS.

Oracle virtualbox

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

Работает в Powershell

С помощью панели инструментов Docker в Windows 10 теперь вы можете запускать команды Docker с помощью powershell . Если вы откроете powershell в Windows и введете команду версии Docker, вы получите все необходимые сведения об установленной версии Docker.

Windows Powershell

Вытягивание изображений и запуск контейнеров

Теперь вы также можете извлекать образы из Docker Hub и запускать контейнеры в powershell, как в Linux. Следующий пример вкратце покажет загрузку образа Ubuntu и запуск контейнера из образа.

Первым шагом является использование команды Docker pull для извлечения образа Ubuntu из Docker Hub.

Потянув изображения

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

docker run –it ubuntu /bin/bash 

Вы заметите, что команда такая же, как и в Linux.

Та же команда

Kitematic

Это GUI-эквивалент Docker в Windows. Чтобы открыть этот графический интерфейс, перейдите на панель задач и на значке Docker щелкните правой кнопкой мыши и выберите, чтобы открыть Kitematic.

Kitematic

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

Затем вам будет предложено войти в Docker Hub, войти через GUI. Просто введите имя пользователя и пароль, а затем нажмите кнопку «Вход».

Подключение к Docker Hub

После входа в систему вы сможете увидеть все изображения, загруженные в систему, в левой части интерфейса.

Загруженные изображения

Справа вы найдете все изображения, доступные на Docker Hub.

Давайте рассмотрим пример, чтобы понять, как загрузить образ Node из Docker Hub с помощью Kitematic.

Шаг 1 – Введите ключевое слово узла в критериях поиска.

ключевое слово узла

Шаг 2 – Нажмите кнопку « Создать» на официальном изображении узла. Затем вы увидите загружаемое изображение.

Кнопка Создать

Как только изображение будет загружено, оно начнет запускать контейнер Node.

Узел Контейнер

Шаг 3 – Если вы перейдете на вкладку настроек , вы можете перейти к дополнительным параметрам настроек, как показано ниже.

  • Общие настройки – на этой вкладке вы можете указать имя контейнера, изменить параметры пути и удалить контейнер.

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

Общие настройки

  • Порты – Здесь вы можете увидеть различные сопоставления портов. Если вы хотите, вы можете создать свои собственные сопоставления портов.

Порты – Здесь вы можете увидеть различные сопоставления портов. Если вы хотите, вы можете создать свои собственные сопоставления портов.

Порты

  • Объемы – Здесь вы можете увидеть различные отображения объема.

Объемы – Здесь вы можете увидеть различные отображения объема.

тома

  • Дополнительно – содержит расширенные настройки для контейнера.

Дополнительно – содержит расширенные настройки для контейнера.

продвинутый

Докер – Настройка ASP.Net

ASP.Net – это стандартная среда веб-разработки, предоставляемая Microsoft для разработки серверных приложений. Поскольку ASP.Net находился в разработке достаточно давно, Docker обеспечил поддержку ASP.Net.

В этой главе мы рассмотрим различные этапы настройки и запуска контейнера Docker для ASP.Net.

Предпосылки

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

Шаг 1. Поскольку это может выполняться только в системах Windows, сначала необходимо убедиться, что у вас установлена ​​Windows 10 или Window Server 2016.

Шаг 2 – Затем убедитесь, что Hyper-V установлен и контейнеры установлены в системе Windows. Чтобы установить Hyper-V и контейнеры, вы можете включить или отключить функции Windows. Затем убедитесь, что опция Hyper-V и контейнеры отмечены, и нажмите кнопку OK.

Возможности системы Windows

Система может потребовать перезагрузки после этой операции.

Шаг 3 – Далее вам нужно использовать следующую команду Powershell для установки версии Docker 1.13.0rc4 . Следующая команда загрузит это и сохранит это во временном местоположении.

Invoke-WebRequest "https://test.docker.com/builds/Windows/x86_64/docker-1.13.0-
   rc4.zip" -OutFile "$env:TEMPdocker-1.13.0-rc4.zip" –UseBasicParsing 

Путь назначения

Шаг 4 – Затем вам нужно развернуть архив с помощью следующей команды powershell .

Expand-Archive -Path "$env:TEMPdocker-1.13.0-rc4.zip" -DestinationPath $env:ProgramFiles

Расширить архив

Шаг 5. Затем необходимо добавить файлы Docker в переменную среды с помощью следующей команды powershell .

$env:path += ";$env:ProgramFilesDocker" 

Шаг 6 – Затем вам нужно зарегистрировать Docker Daemon Service, используя следующую команду powershell .

dockerd --register-service 

Шаг 7 – Наконец, вы можете запустить демон docker, используя следующую команду.

Start-Service Docker

Используйте команду docker version в powershell, чтобы убедиться, что демон docker работает

Версия Docker

Установка контейнера ASP.Net

Давайте посмотрим, как установить контейнер ASP.Net.

Шаг 1 – Первый шаг – извлечь изображение из Docker Hub. Когда вы войдете в Docker Hub, вы сможете выполнить поиск и увидеть образ Microsoft / aspnet, как показано ниже. Просто введите asp в поле поиска и нажмите на ссылку Microsoft / aspnet, которая появляется в результатах поиска.

Microsoft / ASPNET

Шаг 2 – Вы увидите, что Docker вытягивает команду для ASP.Net в деталях хранилища в Docker Hub.

Команда извлечения Docker для ASPNET

Шаг 3 – Перейдите в Docker Host и выполните команду Docker pull для образа microsoft / aspnet. Обратите внимание, что изображение довольно большое, где-то близко к 4,2 ГБ.

Microsoft / Aspnet Image

Шаг 4 – Теперь перейдите по следующему адресу https://github.com/Microsoft/aspnet-docker и загрузите весь репозиторий Git.

Шаг 5 – Создайте папку с именем App на вашем диске C. Затем скопируйте содержимое из папки 4.6.2 / sample на ваш диск C. Перейдите в Docker File в каталоге с примерами и введите следующую команду:

docker build –t aspnet-site-new –build-arg site_root=/ 

Следующие пункты должны быть отмечены о вышеупомянутой команде –

  • Он создает новый образ под названием aspnet-site-new из файла Docker.
  • Корневой путь установлен к папке localpath.

Папка Localpath

Шаг 6 – Теперь пришло время запустить контейнер. Это можно сделать с помощью следующей команды –

docker run –d –p 8000:80 –name my-running-site-new aspnet-site-new 

Новый сайт ASPNET

Шаг 7. Теперь IIS будет запущен в контейнере Docker. Чтобы найти IP-адрес контейнера Docker, вы можете выполнить команду Docker inspect, как показано ниже.

IIS работает в контейнере Docker

Докер – Облако

Docker Cloud – это сервис, предоставляемый Docker, в котором вы можете выполнять следующие операции:

  • Узлы – вы можете подключить Docker Cloud к вашим существующим облачным провайдерам, таким как Azure и AWS, чтобы ускорить работу контейнеров в этих средах.

  • Облачный репозиторий – предоставляет место, где вы можете хранить свои собственные репозитории.

  • Непрерывная интеграция – соединитесь с Github и создайте конвейер непрерывной интеграции.

  • Развертывание приложений – развертывание и масштабирование инфраструктуры и контейнеров.

  • Непрерывное развертывание – может автоматизировать развертывание.

Узлы – вы можете подключить Docker Cloud к вашим существующим облачным провайдерам, таким как Azure и AWS, чтобы ускорить работу контейнеров в этих средах.

Облачный репозиторий – предоставляет место, где вы можете хранить свои собственные репозитории.

Непрерывная интеграция – соединитесь с Github и создайте конвейер непрерывной интеграции.

Развертывание приложений – развертывание и масштабирование инфраструктуры и контейнеров.

Непрерывное развертывание – может автоматизировать развертывание.

Начиная

Вы можете перейти по следующей ссылке для начала работы с Docker Cloud – https://cloud.docker.com/

Docker Cloud

После входа в систему вам будет предоставлен следующий базовый интерфейс –

Базовый интерфейс

Подключение к облачному провайдеру

Первым шагом является подключение к существующему облачному провайдеру. Следующие шаги покажут вам, как связаться с провайдером Amazon Cloud.

Шаг 1. Первый шаг – убедиться, что у вас есть нужные ключи AWS. Это можно взять с консоли aws . Войдите в свою учетную запись aws, используя следующую ссылку – https://aws.amazon.com/console/

Консоль управления AWS

Шаг 2 – После входа перейдите в раздел «Учетные данные безопасности». Запишите ключи доступа, которые будут использоваться в Docker Hub.

Раздел «Учетные данные безопасности»

Шаг 3 – Затем вам нужно создать политику в aws , которая позволит Docker просматривать экземпляры EC2. Перейти в раздел профилей в AWS . Нажмите кнопку « Создать политику» .

Создать политику

Шаг 4 – Нажмите «Создать собственную политику» и дайте название политики в виде dockercloudpolicy и определение политики, как показано ниже.

{ 
   "Version": "2012-10-17", 
   "Statement": [ { 
      "Action": [ 
         "ec2:*", 
         "iam:ListInstanceProfiles" 
      ], 
      "Effect": "Allow", 
      "Resource": "*" 
   } ] 
}

Политика обзора

Далее нажмите кнопку « Создать политику»

Шаг 5. Далее необходимо создать роль, которая будет использоваться Docker для раскрутки узлов в AWS. Для этого перейдите в раздел « Роли » в AWS и выберите параметр « Создать новую роль» .

Создать новую роль

Шаг 6 – Дайте название роли как dockercloud-role .

Следующий шаг

Шаг 7. На следующем экране перейдите к разделу «Роль для перекрестного доступа к учетной записи» и выберите «Предоставить доступ между своей учетной записью и учетной записью AWS третьей стороны».

Выберите тип роли

Шаг 8 – На следующем экране введите следующие данные –

  • В поле Идентификатор учетной записи введите идентификатор для службы Docker Cloud: 689684103426.
  • В поле Внешний идентификатор введите свое имя пользователя в Docker Cloud.

Внешний идентификатор аккаунта

Шаг 9 – Затем нажмите кнопку « Следующий шаг» и на следующем экране присоедините политику, созданную на предыдущем шаге.

Присоединить Политику

Шаг 10 – Наконец, на последнем экране, когда создается роль, обязательно скопируйте созданную роль arn .

arn:aws:iam::085363624145:role/dockercloud-role

Создать имя роли ARN

Шаг 11. Вернитесь в Docker Cloud , выберите « Поставщики облаков» и щелкните значок подключаемого модуля рядом с Amazon Web Services.

Облачные провайдеры

Введите роль Арн и нажмите кнопку Сохранить .

Учетные данные AWS

После сохранения интеграция с AWS будет завершена.

Интеграция с AWS

Настройка узлов

Как только интеграция с AWS будет завершена, следующим шагом будет настройка узла. Перейдите в раздел «Узлы» в Docker Cloud. Обратите внимание, что при настройке узлов сначала будет автоматически настроен кластер узлов.

Шаг 1 – Перейдите в раздел «Узлы» в Docker Cloud.

Раздел узлов

Шаг 2. Далее вы можете указать подробности узлов, которые будут настроены в AWS.

Мастер кластеров узлов

Затем вы можете щелкнуть кластер Launch Node, который будет отображаться в нижней части экрана. Как только узел развернут, вы получите уведомление на экране Node Cluster.

действия

Развертывание Сервиса

Следующим шагом после развертывания узла является развертывание службы. Для этого нам необходимо выполнить следующие шаги.

Шаг 1. Перейдите в раздел «Услуги» в Docker Cloud. Нажмите кнопку Создать

Секция услуг

Шаг 2 – Выберите услугу, которая требуется. В нашем случае давайте выберем монго .

Монго

Шаг 3 – На следующем экране выберите опцию Create & Deploy . Это начнет развертывание контейнера Mongo на вашем кластере узлов.

Создать Deploy

После развертывания вы сможете увидеть контейнер в рабочем состоянии.

Контейнер в рабочем состоянии

Докер – логирование

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

Loging Daemon

На уровне ведения журнала демона доступно четыре уровня ведения журнала.

  • Debug – детализирует всю возможную информацию, обрабатываемую процессом демона.

  • Информация – в ней подробно описываются все ошибки + информация, обрабатываемая процессом демона.

  • Ошибки – в нем подробно описываются все ошибки, обработанные процессом демона.

  • Неустранимый – он только детализирует все неустранимые ошибки, обработанные процессом демона.

Debug – детализирует всю возможную информацию, обрабатываемую процессом демона.

Информация – в ней подробно описываются все ошибки + информация, обрабатываемая процессом демона.

Ошибки – в нем подробно описываются все ошибки, обработанные процессом демона.

Неустранимый – он только детализирует все неустранимые ошибки, обработанные процессом демона.

Выполните следующие шаги, чтобы узнать, как включить ведение журнала.

Шаг 1 – Во-первых, нам нужно остановить процесс демона docker , если он уже запущен. Это можно сделать с помощью следующей команды –

sudo service docker stop 

Docker Daemon Process

Шаг 2 – Теперь нам нужно запустить процесс демона docker . Но на этот раз нам нужно добавить параметр –l, чтобы указать опцию регистрации. Итак, давайте запустим следующую команду при запуске процесса демона docker .

sudo dockerd –l debug &

Следующие пункты должны быть отмечены о вышеупомянутой команде –

  • dockerd – это исполняемый файл для процесса демона docker .

  • Параметр –l используется для указания уровня ведения журнала. В нашем случае мы ставим это как отладочную

  • & используется для возврата в командную строку после включения ведения журнала.

dockerd – это исполняемый файл для процесса демона docker .

Параметр –l используется для указания уровня ведения журнала. В нашем случае мы ставим это как отладочную

& используется для возврата в командную строку после включения ведения журнала.

Точки

После запуска процесса Docker с ведением журналов вы также увидите журналы отладки , отправленные на консоль.

Отчет об ошибках

Теперь, если вы выполните какую-либо команду Docker, такую ​​как образы Docker, информация об отладке также будет отправлена ​​на консоль.

Регистрация изображений Docker

Регистрация контейнеров

Ведение журнала также доступно на уровне контейнера. Итак, в нашем примере давайте сначала раскрутим контейнер Ubuntu. Мы можем сделать это с помощью следующей команды.

sudo docker run –it ubuntu /bin/bash 

Регистрация контейнеров

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

Синтаксис

Docker logs containerID 

параметры

  • containerID – это идентификатор контейнера, для которого вам нужно просмотреть журналы.

containerID – это идентификатор контейнера, для которого вам нужно просмотреть журналы.

пример

На нашем хосте Docker давайте выполним следующую команду. Перед этим вы можете выполнить некоторые команды, находясь в контейнере.

sudo docker logs 6bfb1271fcdd 

Выход

Выход из контейнера

Из результатов видно, что команды, выполняемые в контейнере, отображаются в журналах.

Докер – составь

Docker Compose используется для запуска нескольких контейнеров как одного сервиса. Например, предположим, что у вас есть приложение, которое требует NGNIX и MySQL, вы можете создать один файл, который будет запускать оба контейнера как службу без необходимости запускать каждый из них по отдельности.

В этой главе мы увидим, как начать работу с Docker Compose. Затем мы рассмотрим, как получить простой сервис с MySQL и NGNIX и запустить его с помощью Docker Compose.

Docker Compose ─ Установка

Чтобы запустить Docker Compose, необходимо выполнить следующие шаги.

Шаг 1 – Загрузите необходимые файлы с github, используя следующую команду –

curl -L "https://github.com/docker/compose/releases/download/1.10.0-rc2/dockercompose
   -$(uname -s) -$(uname -m)" -o /home/demo/docker-compose

Приведенная выше команда загрузит последнюю версию Docker Compose, которая на момент написания этой статьи была 1.10.0-rc2 . Затем он будет хранить его в каталоге / home / demo / .

Docker Compose

Шаг 2 – Далее нам нужно предоставить права на выполнение загруженному файлу Docker Compose, используя следующую команду –

chmod +x /home/demo/docker-compose

Выполнить привилегии

Затем мы можем использовать следующую команду, чтобы увидеть составную версию.

Синтаксис

docker-compose version 

параметры

  • версия – это используется, чтобы указать, что мы хотим узнать подробности о версии Docker Compose .

версия – это используется, чтобы указать, что мы хотим узнать подробности о версии Docker Compose .

Выход

Будет отображена информация о версии Docker Compose.

пример

В следующем примере показано, как получить версию docker-compose .

sudo ./docker-compose -version 

Выход

Затем вы получите следующий вывод –

Docker Compose Установка

Создание вашего первого Docker-Compose File

Теперь давайте продолжим и создадим наш первый файл Docker Compose. Все файлы Docker Compose являются файлами YAML. Вы можете создать его с помощью редактора vim. Поэтому выполните следующую команду, чтобы создать файл compose

sudo vim docker-compose.yml 

Создать файл

Давайте внимательно рассмотрим различные детали этого файла –

  • База данных и веб- ключевое слово используются для определения двух отдельных сервисов. Один будет работать с нашей базой данных mysql, а другой будет нашим веб-сервером nginx .

  • Ключевое слово image используется для указания изображения из dockerhub для наших контейнеров mysql и nginx

  • Для базы данных мы используем ключевое слово ports, чтобы указать порты, которые должны быть выставлены для mysql .

  • И затем, мы также указываем переменные окружения для mysql, которые необходимы для запуска mysql .

База данных и веб- ключевое слово используются для определения двух отдельных сервисов. Один будет работать с нашей базой данных mysql, а другой будет нашим веб-сервером nginx .

Ключевое слово image используется для указания изображения из dockerhub для наших контейнеров mysql и nginx

Для базы данных мы используем ключевое слово ports, чтобы указать порты, которые должны быть выставлены для mysql .

И затем, мы также указываем переменные окружения для mysql, которые необходимы для запуска mysql .

Теперь давайте запустим наш файл Docker Compose, используя следующую команду –

sudo ./docker-compose up 

Эта команда возьмет файл docker-compose.yml в ваш локальный каталог и начнет сборку контейнеров.

Докер Compose YML

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

Начать загрузку

И когда вы делаете docker ps , вы можете видеть, что контейнеры действительно работают.

Докер составить контейнер

Докер – Непрерывная интеграция

В Docker интегрированы многие инструменты Continuous Integrations, в которые также входит популярный инструмент CI, известный как Jenkins . В Jenkins у вас есть плагины, которые можно использовать для работы с контейнерами. Итак, давайте быстро рассмотрим плагин Docker, доступный для инструмента Jenkins.

Давайте пойдем шаг за шагом и посмотрим, что доступно в Jenkins для контейнеров Docker.

Шаг 1 – Перейдите на панель инструментов Jenkins и нажмите Manage Jenkins .

Управление Дженкинс

Шаг 2 – Перейти к управлению плагинами .

Управление плагинами

Шаг 3 – Поиск плагинов Docker. Выберите плагин Docker и нажмите кнопку « Установить без перезагрузки» .

Кнопка «Установить без перезагрузки»

Шаг 4 – После завершения установки перейдите к своей работе на панели управления Jenkins. В нашем примере у нас есть работа под названием Demo .

демонстрация

Шаг 5 – В задании, когда вы переходите к шагу сборки, теперь вы можете видеть опцию запуска и остановки контейнеров.

Добавить шаг сборки

Шаг 6 – В качестве простого примера вы можете выбрать дополнительную опцию, чтобы остановить контейнеры, когда сборка будет завершена. Затем нажмите кнопку Сохранить .

Остановить все контейнеры

Теперь просто работай в Дженкинс. В выходных данных консоли вы сможете увидеть, что команда Stop All Containers выполнена.

Консольный выход

Докер – Архитектура Кубернетес

Kubernetes – это структура оркестровки для контейнеров Docker, которая помогает представить контейнеры как сервисы для внешнего мира. Например, у вас может быть две службы: одна будет содержать nginx и mongoDB , а другая – nginx и redis . Каждая служба может иметь IP-адрес или точку обслуживания, к которой могут подключаться другие приложения. Kubernetes затем используется для управления этими услугами.

На следующей диаграмме в упрощенном формате показано, как Kubernetes работает с точки зрения архитектуры.

Kubernetes Architecture

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

Kubernetes имеет несколько компонентов в своей архитектуре. Роль каждого компонента объясняется ниже & mius;

  • etcd – этот компонент является хранилищем значений ключа высокой доступности, которое используется для хранения общей конфигурации и обнаружения служб . Здесь различные приложения смогут подключаться к сервисам через сервис обнаружения .

  • Фланель – это внутренняя сеть, которая требуется для контейнеров.

  • kube-apiserver – это API, который можно использовать для организации контейнеров Docker.

  • kube-controller-manager – используется для управления сервисами Kubernetes .

  • kube-scheduler – используется для планирования контейнеров на хостах.

  • Kubelet – используется для управления запуском контейнеров через файлы манифеста .

  • kube-proxy – используется для предоставления сетевых прокси-сервисов внешнему миру.

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

Фланель – это внутренняя сеть, которая требуется для контейнеров.

kube-apiserver – это API, который можно использовать для организации контейнеров Docker.

kube-controller-manager – используется для управления сервисами Kubernetes .

kube-scheduler – используется для планирования контейнеров на хостах.

Kubelet – используется для управления запуском контейнеров через файлы манифеста .

kube-proxy – используется для предоставления сетевых прокси-сервисов внешнему миру.

Докер – Рабочая Кубернетес

В этой главе мы увидим, как установить Kubenetes через kubeadm . Это инструмент, который помогает в установке Kubernetes. Давайте пойдем шаг за шагом и узнаем, как установить Kubernetes.

Шаг 1 – Убедитесь, что версия сервера Ubuntu, с которой вы работаете, – 16.04 .

Шаг 2 – Убедитесь, что вы сгенерировали ключ ssh, который можно использовать для входа по ssh . Вы можете сделать это с помощью следующей команды.

ssh-keygen 

Это сгенерирует ключ в вашей домашней папке, как показано ниже.

Домашняя папка

Шаг 3 – Далее, в зависимости от версии Ubuntu, вам нужно будет добавить соответствующий сайт в список docker.list для менеджера пакетов apt , чтобы он мог обнаружить пакеты Kubernetes с сайта kubernetes и загрузить их соответственно.

Мы можем сделать это с помощью следующих команд.

curl -s https://packages.cloud.google.com/apt/doc/apt-key.gpg | apt-key add -  
echo "deb http://apt.kubernetes.io/ kubernetes-xenial main” | sudo tee /etc/apt/sources.list.d/docker.list

Шаг 4 – Затем мы выпускаем обновление apt-get, чтобы убедиться, что все пакеты загружены на сервер Ubuntu.

Проблема APT Получить обновление

Шаг 5 – Установите пакет Docker, как описано в предыдущих главах.

Шаг 6 – Теперь пришло время установить kubernetes , установив следующие пакеты:

apt-get install –y kubelet kubeadm kubectl kubernetes-cni

Установить Кубенетес

Пакет Docker

Шаг 7 – Как только все пакеты kubernetes загружены, пришло время запустить контроллер kubernetes, используя следующую команду –

kubeadm init 

Кубернетес Пакеты

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

В этом гайде разбираемся, для чего нужен Docker и Docker Compose, что такое контейнеризация и Docker-образы, а также как развернуть простое веб-приложение с использованием PHP-FPM, Nginx и Postgres.

  • Что такое Docker
  • Как работает Docker
  • Как создать свой Docker-образ
  • Что такое Docker Compose и как он работает
  • Как создать простое веб-приложение с помощью Docker
  • Итог

Давайте представим себе разработчика, который приходит на работу в новую компанию. На онбординге тимлид дает ему первое шуточное задание: изучить сайт организации и найти на нем страницу с фотографиями котиков.

Разработчик узнаёт, что сайт компании работает с помощью веб-сервера Nginx, менеджера процессов PHP-FPM и системы управления базами данных Postgres. Теперь программист ищет нужную страницу. Поиск выглядит так:

  1. Разработчик вводит в браузере адрес сайта
  2. Браузер запрашивает HTML-страницу с котиками по указанному адресу
  3. HTTP-сервер Nginx принимает запрос и делегирует создание страницы PHP-FPM
  4. PHP-FPM запрашивает данные о котиках из базы Postgres, строит HTML-страницу и отдает обратно его серверу Nginx, а тот — клиенту-браузеру
  5. Разработчик видит страницу с котиками.

Свое первое задание разработчик выполняет на компьютере тимлида, где уже установлен Nginx, PHP-FPM и Postgres. На следующий день ему выдают новый компьютер, на котором этих программ нет.

Чтобы начать работать над сайтом вместе с коллегами, разработчик разворачивает проект, то есть устанавливает и настраивает все необходимое для работы. Он делает это последовательно:

  • Устанавливает Nginx
  • Устанавливает PHP-FPM и все нужные расширения
  • Настраивает совместную работу Nginx и PHP-FPM
  • Устанавливает Postgres, создает пользователей, нужные базы и схемы.

Установка идет долго: приходится ждать, пока сначала установится одна программа, потом другая. Сложности добавляет и то, что вся его команда работает над проектом на разных операционных системах: одни на macOS, а другие на Ubuntu или Windows.

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

Что такое Docker

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

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

Простыми словами контейнер — это некая изолированная песочница для запуска ваших приложений.

На картинке видно, что приложение 1 и приложение 2 изолированы как друг от друга, так и от операционной системы.

Что еще может делать Docker:

  • Управлять изолированными приложениями
  • Ускорять и автоматизировать развертывание приложений
  • Доставлять приложения до серверов
  • Масштабировать приложения
  • Запускать на одном компьютере разные версии одной программы.

Читайте также:
Как читать чужой код: 6 правил, которые стоит помнить разработчику

Как работает Docker

Концепцию программы легче понять на практике. Сначала установим на компьютер Docker и запустим HTTP-сервер Nginx. Для этого введем следующую команду:

docker run -p 8080:80 nginx:latest

Далее откроем браузер и забьем в адресную строку: 127.0.0.1:8080. Откроется страница приветствия Nginx.

Теперь разберемся подробнее, что происходит, когда мы вводим команду docker run -p 8080:80 nginx:latest. Она выполняет следующее:

  1. Скачивает docker-образ — шаблон для создания Docker-контейнера — nginx:latest из публичного репозитория Docker Hub (если его не скачивали ранее). Docker-образ содержит все необходимое для запуска приложения: код, среду выполнения, библиотеки, переменные окружения и файлы конфигурации. На странице Nginx в Docker Hub можно найти Docker-образ nginx:latest, где latest — это тег (метка, снимок), который ссылается на самый свежий docker-образ и описывает его.
  2. Запускает Docker-контейнер с помощью Docker-образа
  3. Пробрасывает порт. Ранее мы объясняли, что процессы в Docker-контейнерах запускаются в изоляции от ОС, то есть все порты между ОС и Docker-контейнером закрыты. Для того, чтобы мы смогли обратиться к Nginx, нужно пробросить порт, что и делает опция -p 8080:80, где 80 — это порт Nginx внутри контейнера, а 8080 — порт в локальной сети ОС.

Как создать свой Docker-образ

Теперь попробуем создать свой Docker-образ, взяв за основу nginx:latest. Docker умеет создавать Docker-образ, читая текстовые команды, которые записаны в файл Dockerfile.

Вот пример простейшего Dockerfile:

FROM nginx:latest

RUN echo 'Hi, we are building a custom docker image from nginx:latest!'

COPY nginx-custom-welcome-page.html /usr/share/nginx/html/index.html

Команда FROM задает базовый (родительский) Docker-образ и всегда вызывается в первую очередь. Команда COPY копирует файлы в Docker-контейнер.

С помощью COPY можно заменить стандартную велком-страницу Nginx на такую страницу:

<!DOCTYPE html>
<html>
<body>
<h1>Welcome to custom Nginx page!</h1>
</body>
</html>

Узнать подробнее об этих и других командах Docker можно в официальной документации.

Теперь, когда мы разобрались, за что отвечают команды, создадим Docker-образ из Dockerfile:

$ docker build -t nginx_custom:latest -f  /opt/src/docker-for-kids/dockerFiles/Nginx-custom/Dockerfile /opt/src/docker-for-kids
Sending build context to Docker daemon  139.3kB
Step 1/3 : FROM nginx:latest
latest: Pulling from library/nginx
31b3f1ad4ce1: Pull complete
fd42b079d0f8: Pull complete
30585fbbebc6: Pull complete
18f4ffdd25f4: Pull complete
9dc932c8fba2: Pull complete
600c24b8ba39: Pull complete
Digest: sha256:0b970013351304af46f322da1263516b188318682b2ab1091862497591189ff1
Status: Downloaded newer image **for** nginx:latest
---**>** 2d389e545974
Step 2/3 : RUN echo 'Hi, we are building a custom docker image from nginx:latest!'
---**>** Running **in** 05ffd060061f
Hi, we are building a custom docker image from nginx:latest!
Removing intermediate container 05ffd060061f
---**>** 9ac62be4252a
Step 3/3 : COPY nginx-custom-welcome-page.html /usr/share/nginx/html/index.html
---**>** 704121601a45
Successfully built 704121601a45
Successfully tagged nginx_custom:latest

Поясним, какие команды мы использовали в этом коде:

  • -t nginx_custom:latest — это имя будущего Docker-образа, latest — это тег
  • -f /opt/src/docker-for-kids/dockerFiles/Nginx-custom/Dockerfile — путь до Dockerfile
  • /opt/src/docker-for-kids — директория, в контексте которой будет создан Docker-образ. Контекст — это все то, что доступно для команд из Dockerfile при сборке (билде) образа. Процесс создания Docker-образа может ссылаться на любой из файлов в контексте.

Теперь запускаем команду:

$ docker run -p 8080:80 Nginx_custom:latest

Docker-образ готов.

Читайте также:
Как настроить VS Code для разработки на PHP и JavaScript

Что такое Docker Compose и как он работает

С ростом количества Docker-контейнеров их становится труднее поддерживать. Конфигурация каждого контейнера описывается в своем Dockerfile, и их нужно запускать отдельной командой. Это же касается сборки или пересборки контейнеров.

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

Для описания приложений используется YAML-файл.

version: '3'

services:
  nginx:
    container_name: nginx-test # имя Docker-контейнера
    build: # создать Docker-образ из DockerFile
      context: . # путь, в контексте которого будет создан Docker-образ
      dockerfile: ./dockerFiles/nginx/Dockerfile # путь до Dockerfile, из которого будет собран Docker-образ
    ports: # проброс портов
      - "80:80"
    networks: # имя сети, к которой будет подключен Docker-контейнер
      - test-network
    depends_on: # эта программа будет запущена только после того, как запустится сервис под именем php-fpm 
      - php-fpm
    volumes: #  монтирование директорий, директория-на-хост-машине: директория-в-докере
      - ./:/var/www/hello.dev/
  php-fpm:
    container_name: php-fpm-test
    build:
      context: .
      dockerfile: ./dockerFiles/php-fpm/Dockerfile
    networks:
      - test-network
    volumes:
      - ./:/var/www/hello.dev/
  postgres:
    container_name: postgres-test
    image: postgres:14.1-alpine # тег Docker-образа из https://hub.docker.com/
    environment:
      postgres_PASSWORD: mysecretpass # переменные окружения, которые использует Docker-контейнер
    networks:
      - test-network
networks: # явно объявленные сети
  test-network:
    driver: bridge

Если изображать этот код схематично, то описание приложения выглядит так:

Каждый сервис находится внутри Docker-контейнера. Точкой входа в приложение, как и в случае с тем разработчиком и веб-сайтом компании, является Nginx. Пользователи веб-сайта делают запросы к Nginx, у которого проброшен порт 80.

Разберем еще несколько команд, которые реализует Docker:

  1. network. Как мы объяснили ранее, каждое приложение в Docker-контейнере находится в изоляции. networks объединяет все Docker-контейнеры в одну сеть с именем test-network, и это позволяет обращаться к нужному контейнеру по его имени.
  2. volumes — это механизм для хранения данных вне Docker-контейнера, то есть в файловой системе нашей ОС. volumes решает проблему совместного использования файлов.

Все примеры, а также исходники Dockerfile можно взять из репозитория на GitHub.

Как создать простое веб-приложение с помощью Docker

Создадим простое веб-приложение, которое покажет нам сообщение об успешном подключении к базе данных. Вместо адреса базы данных используем host=postgres, такое же имя cервиса, как и в YAML-файле. Напомню, что эта возможность появилась благодаря общей сети test-network.

index.php
<?php

try {
    $pdo = new PDO("pgsql:host=postgres;dbname=postgres", 'postgres', 'mysecretpass');
    echo "Подключение к базе данных установлено! <br>";

    return;
} catch (PDOException $exception) {
    echo "Ошибка при подключении к базе данных<br><b>{$exception->getMessage()}</b><br>";
}

PDO — это интерфейс для доступа к базам данных в PHP. Подробнее об этом можно узнать в официальной документации.

Теперь, чтобы создать все Docker-образы и запустить Docker-контейнеры нужно выполнить:

docker-compose up --build

Выполняем index.php и видим успешное соединение с базой данных.

Веб-приложение для самостоятельного запуска можно найти в репозитории на GitHub.

Итог

Освоив Docker, разработчики могут разворачивать все необходимые им сервисы на каком угодно компьютере. Также эта программа — отличный инструмент для быстрой доставки до серверов, тестирования. Изучить Docker не так тяжело, как может показаться новичкам, но зато это умение значительно сэкономит их время на ручной установке софта. Почитать про Docker подробнее можно на официальном сайте.

Изучите основы Docker:
На Хекслете есть курс по основам Docker. Пройдите его, чтобы подробнее узнать об этой программе, научиться работать с образами, управлять контейнерами и получить поддержку от менторов и единомышленников.

Изучить Docker

Понравилась статья? Поделить с друзьями:
  • Беталок зок 25 инструкция по применению при каком давлении принимать
  • Пошаговая инструкция плетения из бисера браслеты
  • Расходомер гиперфлоу 3пм руководство по эксплуатации
  • Мануал для ремонта бмв
  • Оршанский отдел департамента охраны мвд руководство