Docker 0.1: смотрим, щупаем, откладываем в сторону
Docker публично анонсирован на PyCon 2013. Изучаем 0.1, восхищаемся идеей контейнеров - и возвращаемся к LXC: для production инструмент пока сырой.
Docker публично анонсирован на PyCon в марте 2013; идея контейнерной изоляции начинает привлекать внимание ops-сообщества
На прошлой неделе в Twitter и HackerNews прокатилась волна постов про Docker - проект dotCloud, который Solomon Hykes показал на PyCon US 2013. Идея: взять Linux-контейнеры (LXC), добавить поверх удобный слой управления образами и получить что-то вроде «git для файловых систем контейнеров». Мы посмотрели. Поставили на стенд. Поигрались пару дней. И вот что думаем.
Что это вообще такое
Docker - это не виртуализация в привычном смысле. Нет гипервизора, нет отдельного ядра внутри контейнера. Контейнер делит ядро с хостом, но изолирован через cgroups и namespaces. Процессы внутри видят свою файловую систему, своё дерево процессов, свои сетевые интерфейсы - и не видят остального.
LXC мы используем уже какое-то время для изоляции сервисов у нескольких клиентов: отдельный контейнер под веб-приложение, отдельный под базу. Работает, стабильно, но управление образами - больная тема. Создать новый контейнер из шаблона, синхронизировать конфигурацию между экземплярами, откатить на предыдущее состояние - всё это делается скриптами и руками, единого подхода нет.
Docker предлагает ответ на этот вопрос: Union FS поверх слоёв образов, docker commit, docker push/pull. Запустил контейнер, внёс изменения, зафиксировал новый слой - и этот слой можно распространять. Выглядит красиво на демо.
Что потрогали на стенде
Установка на Ubuntu 12.10 прошла без сюрпризов. docker pull ubuntu, docker run -i -t ubuntu /bin/bash - и ты внутри контейнера. Первые десять минут ощущение «вот это да» не отпускает.
Попробовали несколько сценариев:
- Запуск nginx в контейнере. Поднялся, порт пробросили через
-p. Работает. Но конфигурация внутри образа - значит каждое изменение это новыйdocker commit. Привыкнуть можно, но непривычно. - Монтирование данных.
-v /host/path:/container/pathработает, но документация по этому вопросу скудная, и поведение в ряде случаев неочевидное. Данные в самом контейнере - эфемерны: удалил контейнер, данные пропали. Это принципиальный момент для любой базы данных или чего-то stateful. - Несколько контейнеров, взаимодействие между собой. Вот здесь начинается интересное - в смысле «интересно как это вообще делать». Механизма координации несколько контейнеров нет. IP-адреса динамические, discovery нет, никакого service mesh нет. Руками прописывать адреса - так себе архитектура.
Почему не production
Причин несколько, и они накапливаются.
Версия 0.1 - это буквально 0.1. Выпущена три недели назад. Проект не дозрел до стабильного API. Запускать на этом что-то у клиентов и потом поддерживать - серьёзная авантюра. Нет нормальной документации, нет community вокруг операционных вопросов, нет понятного пути обновления.
Хранилище эфемерно по замыслу. Для stateless-приложений это нормально. Для всего остального нужны внешние решения, которых в экосистеме Docker нет. Volumes через bind mount работают, но это не production-решение для данных с гарантиями.
Оркестрации нет вообще. Запустить один контейнер вручную - просто. Запустить десять контейнеров, убедиться что они нашли друг друга, обеспечить рестарт при падении, балансировать трафик - это вопросы без ответа в текущем инструменте. Скрипты руками? Можно. Но тогда зачем Docker, а не просто LXC с теми же скриптами, которые у нас уже есть.
LXC сам по себе работает. У нас несколько production-инсталляций с LXC-изоляцией. Стабильно, предсказуемо, понятно что делать при проблемах. Puppet управляет конфигурацией внутри контейнеров так же, как на железе - декларативно, идемпотентно. Это работающая связка, отлаженная, без экспериментальных зависимостей.
Что реально нравится в идее
Слоистые образы - это умно. Базовый слой с Ubuntu, поверх слой с зависимостями приложения, поверх слой с самим приложением. Rebuild только изменённых слоёв. Распространение через registry. Если всё это дозреет до стабильного состояния - способ упаковывать и доставлять окружения станет заметно удобнее.
Dockerfile как декларативное описание сборки образа - тоже интересная идея. Не скрипт, а рецепт: FROM, RUN, ADD, EXPOSE. Читается и версионируется нормально.
Но между «интересная идея» и «можно ставить клиентам» - пропасть.
Что делаем
Кладём в папку «наблюдаем». Один человек в команде подписался на рассылку проекта и будет следить за релизами. На production продолжаем LXC с Puppet - эта связка нас устраивает, и нет причин её ломать ради инструмента версии 0.1.
Если Docker выйдет в какую-то стабильную версию с нормальным управлением состоянием и хотя бы минимальной оркестрацией - вернёмся и посмотрим серьёзнее. А пока - хорошее демо на конференции, не более.