Продакшен и Деплой
Теория: Деплой
Теперь, когда у нас есть готовый образ приложения, выполним его деплой. Деплой через Docker содержит такие шаги:
- Скачивание нужного образа на сервера
- Остановка старого контейнера
- Запуск нового контейнера из скаченного образа
В продвинутых сценариях деплой образов выполняется с помощью Kubernetes. А здесь мы выполняем деплой напрямую, с помощью Ansible. Почему именно он? Ansible наиболее простой и удобный инструмент, из существующих, который позволяет буквально небольшим yaml файлом описать процесс деплоя и использовать его для любого количества серверов. Ansible берет на себя обработку ошибок, параллельное выполнение и многое другое.
Подготовка сервера
Подготовка сервера для деплоя Docker приложения, очень простая задача. В таком случае, вся настройка сведется добавлению ssh-ключей для доступа без пароля и установке Docker.
Создайте самый дешевый сервер (Droplet в терминах DigitalOcean, Compute Cloud у Yandex Cloud) для деплоя. Его стоимость 5$ в месяц. Здесь есть хитрость, по умолчанию DO предлагает сервера с чистыми операционными системами, но если переключиться на вкладку Markeplace, то там есть Ubuntu с предустановленным Docker. То что нам нужно.
Во время создания, вам предложат выбор как подключаться к серверу: по паролю или через ssh-ключ. Выберите ssh-ключ и добавьте его. Если у вас нет ssh-ключа, то создайте его по этой инструкции.
Когда сервер будет готов, DO покажет вам его ip-адрес. Возьмите этот адрес и попробуйте подключиться к серверу по ssh. Если у вас получилось, то можно готовиться к деплою.
Подготовка к деплою
Для деплоя нам понадобится настроенный Ansible. Установите его локально на свой компьютер. Все файлы Ansible мы будем хранить в директории ansible.
Создадим плейбук, который выполняет всю работу по деплою приложения. Первым делом нам нужно установить python-пакет docker, который используется Ansible для управления Docker. В свою очередь python-пакеты устанавливаются через pip3, который тоже нужно установить. В ручную мы бы сделали это так:
Теперь тоже самое, но через Ansible:
Осталось добавить старт приложения и можно пробовать запускать. Для работы с Docker у Ansible есть специальный модуль community.docker.docker_container. У него много настроек, но нам сейчас нужны лишь некоторые:
Процесс деплоя состоит буквально из одной задачи, которая скачивает новый образ и перезапускает приложение.
Осталось создать inventory-файл. Здесь все просто. Добавляем группу webservers с одним сервером web1:
По необходимости сюда легко добавляются новые сервера. Схема с деплоем на множество серверов рассматривается в одном из следующих уроков.
Деплой
Когда все готово, остается запустить одну команду, которая выполнит деплой:
Во время деплоя передается версия, которую мы хотим выкатить. В нашем случае она совпадает с именем тега у Docker-образа и git-репозитория.
У такого способа деплоя, когда рестартует контейнер, есть одна особенность о которой нужно знать. Остановка старого контейнера и запуск нового — не моментальная операция. Какое-то время не будет запущен ни один контейнер, а значит пользователь увидит ошибку. Чтобы избежать этого, нужно перед приложением добавить реверспрокси (Nginx, Caddy, ...), в котором будет настроена обработка подобных ошибок и возврат красивой страницы с объяснением того, что происходит. Об этом в следующем уроке.
Откат
Во время деплоя могут возникнуть проблемы и тогда потребуется откат. Как его выполнять? Секрет в том, что откатов не существует. Мы всегда движемся вперед, даже если переключаемся на старую версию кода. Все что нужно — выполнить плейбук с нужной версией кода:
Ситуация чуть сложнее когда у нас есть база данных, но об этом дальше по курсу.
Разделение плейбуков
Плейбук, который мы создали выше, состоит из двух независимых частей — настройки сервера и самого деплоя. В простейшем случае мы можем оставить все как есть, но настройка может усложниться и замедлить скорость деплоя. Поэтому, лучше, вынести настройку в отдельный плейбук и запускать ее независимо. Такая схема безопаснее, если вы захотите обновить сервер, то случайно не перезапустите приложение и наоборот, если захотите деплоить, то случайно не обновите сервер.









