Стандартный способ распространения образов Docker — использование репозиториев Docker, которые позволяют как опубликовать вновь созданные образы, так и скачать их для локального использования. Развернуть локальный реестр Docker можно за 1 минуту, однако, для полноценного использования требуется больше действий, например, установка SSL-сертификата и поддержка авторизации.
Бывают случаи, когда серверы, на которых планируется выполнять контейнеры, созданные из образов, полностью изолированы от сегмента сети и не могут скачать себе образ из реестра. В этом случае у разработчиков возникает необходимость каким-то образом сформировать образ контейнера на сервере. Команда docker build тоже часто не подходит, поскольку большинство образов при сборке скачивает зависимости и необходимые слои из сети. Если хост не имеет подключения к сети, то и скачать ничего не сможет.
К счастью, Docker предоставляет стандартный механизм для распространения образов без использования реестров с помощью импорта и экспорта. Далее в статье мы рассмотрим как воспользоваться этими возможностями для того, чтобы эффективно распространять образы на серверы, где подключение к интернет невозможно.
Вообще, данный подход можно применять и в ряде других случаев, часть из которых мы перечислим ниже:
- обеспечение развертывания без сети;
- гарантированное развертывание с твердого носителя (USB, DVD);
- поставка в форме готового к использовании дистрибутива;
- минимизация инфраструктуры за счет исключения лишних элементов (registry).
Сохранение образа в архив
Для начала рассмотрим как можно выполнить сохранение образа контейнера из среды. Для выполнения данной операции используется команда docker save (man docker-save):
docker pull ubuntu:18.04 docker save -o ubuntu-1804.tar ubuntu:18.04
После выполнения данной команды образ со всеми слоями будет выгружен из пространства образов демона Docker в файловую систему в виде архива tar.
Интересно, что таким образом можно выгрузить более одного образа:
docker pull ubuntu:16.04 docker save -o ubuntu-16+18.tar ubuntu:18.04 ubuntu:16.04
Таким образом, вы можете за одну команду выгрузить все необходимые для распространения контейнеры в один tar-архив.
Загрузка образа в среду Docker
Для выполнения загрузки ипользуется обратная операция docker load:
# удалим образы docker rmi ubuntu:18.04 ubuntu:16.04 # убедимся, что нет доступных образов docker images | grep ubuntu | wc -l # загрузим образы из архива в среду Docker docker load -i ubuntu-16+18.tar aa54c2bc1229: Loading layer [==================================================>] 121.6MB/121.6MB 7dd604ffa87f: Loading layer [==================================================>] 15.87kB/15.87kB 2f0d1e8214b2: Loading layer [==================================================>] 11.78kB/11.78kB 297fd071ca2f: Loading layer [==================================================>] 3.072kB/3.072kB Loaded image: ubuntu:16.04 Loaded image: ubuntu:18.04 # проверим доступное количество образов docker images | grep ubuntu | wc -l 2
Таким образом вы можете распространять образы контейнеров Docker между узлами без использования реестра и даже сети, например, на DVD или накопителе USB.
Отличия Save, Load от Export, Import
Docker поддерживает команды export и import, которые часто могут быть перепутаны с save, load. Ключевое отличие данных команд в том, для чего они предназначены:
- save/load выгружают и загружают образы контейнеров, которые будут использоваться для создания контейнеров;
- export выгружает файловую систему созданного контейнера (не образ контейнера, а изменения, которые внес контейнер в образ);
- import позволяет создать образ тома файловой системы из архива, созданного с помощью export, который может использоваться, например, при запуске контейнера с помощью —volumes-from.
В целом, разница заключается, что save/load относятся к данным образов, а export/import к данным контейнеров.