Как создать большой образ докера с относительно небольшим использованием дискового пространства?

Фон

Я пытаюсь создать образ Docker из Dockerfile на виртуальной машине. Виртуальная машина работает с Redhat 7.1 (ядро 3.10), а Docker - с 1.10.2.

Dockerfile имеет следующий контент

FROM rhel
MAINTAINER MyName<me@email.com>
RUN #yum install wget and other tools (less than 500 MB)
COPY entitlementfile /opt/entitlementfile
RUN  wget -O /opt/installer.bin https://installer.com/installer.bin \ 
    && chmod +x /opt/* \
    && /opt/installer.bin --quiet \
    && rm -f /opt/*.bin
USER admin

Моя сборка VM имеет около 16G свободного места

[root@xrh701 DockerImage]# df -h
Filesystem                                        Size  Used Avail Use% Mounted on
/dev/mapper/rhel-root                              18G  2.1G   16G  12% /
...

Установщик около 3G, а установленный пакет около 8G. Это составляет максимум до 11G, немного превышает значения по умолчанию для базового устройства докера, которые составляют 10G.

Поэтому я вручную запускаю демон docker с большим dm.size (15G), чтобы обойти эту проблему.

docker daemon --storage-opt dm.basesize=15G

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

(1) максимальный размер, который может получить мое изображение, составляет 11G (установщик в одном слое 3G, а слой пакета добавлен поверх 8G)

(2) и если я запустил установщик, запустите его, а затем удалите установщик в той же команде RUN, образ должен быть только 8G (так как установщик 3G удален)

В любом случае, суть в том, что 16G места должно быть более чем достаточно.

проблема

Но мое текущее наблюдение заключается в том, что во время процесса сборки докера он всегда зависал, так как занимал все доступное пространство

[root@xrh701 DockerImage]# df -h
Filesystem                                        Size  Used Avail Use% Mounted on
/dev/mapper/rhel-root                              18G   18G   20K 100% /
...

Я вижу два изображения

$ docker images
REPOSITORY          TAG                 IMAGE ID            CREATED             SIZE
<none>              <none>              fa09e98656ba        About an hour ago   258.1 MB
rhel                latest              32f8a1d5f019        9 days ago          203.2 MB

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

docker ps -a
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS                         PORTS               NAMES
232245023f90        fa09e98656ba        "/bin/sh -c 'wget -O "   About an hour ago   Exited (0) About an hour ago                       lonely_curie

Этот промежуточный контейнер завершил выполнение строки wget RUN, успешно завершился, но не зафиксировал образ докера из-за недостатка места

Что еще хуже, я не могу ни удалить контейнер, ни удалить /var/lib/docker, чтобы восстановить пространство назад

# docker rm -f lonely_curie
Failed to remove container (lonely_curie): Error response from daemon: Driver devicemapper failed to remove root filesystem 232245023f90b42a4dbd19a78bf32836f9f8618d7dbcba54159c3df029b5b114: mount still active

Вопрос

  1. Почему докер израсходовал все пространство? Согласно расчету, дискового пространства (16G) должно быть более чем достаточно для целевого изображения (8G). [У меня есть эта виртуальная машина, поэтому я могу гарантировать, что никто другой или какой-либо другой процесс не будет занимать место на жестком диске]

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

  3. Как мне создать этот образ 8G (или образ 11G, если вы считаете установщик) на виртуальной машине 16G? Если это невозможно, каково минимальное пространство для его успешной сборки? В настоящее время я подаю заявку на 32G VM из лаборатории.

1 ответ

Решение

TL;DR

Предположим, что установщик 3G и установленный пакет 8G.

Если я выпущу Dokcerfile, то для создания этого образа потребуется минимум 22 G [ (3+8)*2 = 22 ].

Если я освобождаю изображение и отправляю его в Dockerhub, то пользователю нужно только 11 G, чтобы вытащить изображение и запустить контейнер на его основе.

================================================== ================

строить

У меня была машина размером около 50G, чтобы перезапустить сборку и контролировать потребление диска.

Перед началом сборки

# df -h
Filesystem                 Size  Used Avail Use% Mounted on
/dev/mapper/vg_01-lv_root   59G   6G   53G  9% /
...

После завершения установки

# df -h
Filesystem                 Size  Used Avail Use% Mounted on
/dev/mapper/vg_01-lv_root   59G   19G   38G  34% /
...

После того, как изображение передано

# df -h
Filesystem                 Size  Used Avail Use% Mounted on
/dev/mapper/vg_01-lv_root   59G   27G   30G  48% /
...

Итак, чтобы ответить на мой собственный вопрос: (1) Он израсходовал весь диск, потому что он требует, по крайней мере, столько места на диске. Предыдущий расчет предполагал, что построенный контейнер и изображение будут иметь один и тот же слой.

(2) Еще не разобрался в этой части. Прямо сейчас я просто выбрасываю ВМ и позволяю вернуть его.

(3) Минимальный требуемый диск будет (3G + 8G) * 2 = 22 ГБ. Поэтому я думаю, что для дальнейшего использования я должен зарезервировать вдвое больше теоретически рассчитанного размера изображения, так как слой представляется скопированным, а не общим при передаче работающего контейнера на изображение. [Создание Dockerfile по сути аналогично ручному запуску контейнера и фиксации изображения.]

================================================== ===============

Бежать

И для продолжения, после того, как я фиксирую образ и удаляю контейнер, диск можно восстановить

# df -h
Filesystem                 Size  Used Avail Use% Mounted on
/dev/mapper/vg_01-lv_root   59G   15G   42G  26% /
....

И с этого момента запуск работающего контейнера не увеличит потребление диска (значительно).

# df -h
Filesystem                 Size  Used Avail Use% Mounted on
/dev/mapper/vg_01-lv_root   59G   15G   42G  26% /
...
Другие вопросы по тегам