Вот три предложения. Важной частью здесь является то, что вам не нужно доводить его до совершенства с первого раза;поэтому разбейте проблему на более мелкие части и поэкспериментируйте.
Первое общее полезное предложение - разбить ваши RUN
утверждения во время разработки. Типичный стиль Docker состоит в том, чтобы иметь небольшое количество больших RUN
утверждений
RUN apk add ... \
&& pip3 install -r requirements.txt \
&& ... \
&& apk del ...
Но пока вы разрабатываете это и пытаетесь решить проблемы, может быть полезно разбить это на более мелкие утверждения
RUN apk add ...
# If the next line breaks, you'll get caching on the previous line
RUN pip3 install -r requirements.txt
Отладьте это и объедините их позже.
Во время выполнения docker build
после каждого шага будут выводиться строки, подобные
---> e38ccc1e7f56
Каждая из этих строкявляется действительным идентификатором образа Docker, и вы можете запустить
docker run --rm -it e38ccc1e7f56 sh
, чтобы получить отладочную оболочку на выходе этого шага. Для второго трюка вы можете заставить команду RUN
выполнить
RUN pip3 install -r requirements.txt || true
Это всегда будет «успешным», так что вы получите действительный образ Docker. Это будет в том состоянии, в котором вы пытаетесь отлаживать: установка пакета завершилась неудачно, но все до этого в Dockerfile запустилось, и pip уже загрузил пакеты.
Теперь у вас есть интерактивная оболочкав одноразовом контейнере в результате сломанной сборки. Вы можете довольно свободно экспериментировать здесь. Попробуйте запустить pip3 install
еще раз;это лучше? apk add
помогает какой-то конкретный пакет разработки или компилятор? Важным третьим трюком здесь является проведение этого эксперимента, когда ваш Dockerfile открыт в текстовом редакторе: у вас, вероятно, уже есть рабочая строка apk add
, в которую вы можете легко добавить больше пакетов, поэтому каждый раз, когда вам нужен другой пакет, чтобыpip3 install
На шаг впереди, просто добавьте его в свой Dockerfile.
Ваша мысль о pip3 install
упаковках по одному также находится в этом ключе. Это оптимальное производство Dockerfile
? Нет, но вам будет намного легче отлаживать, почему не устанавливается отдельный пакет.
Как только у вас все заработает, вы должны удалить лишние || true
биты, объединить ваши строки RUN
вместе, и так далее. Думайте об этом как об окончательном этапе очистки перед тем, как вы будете готовы к отправке.
Более новый Docker имеет механизм альтернативной сборки не по умолчанию , который поддерживает некоторый экспериментальный синтаксис сборки. У него есть определенный вариант RUN, явно поддерживающий каталоги кеша , и вы можете использовать его для кэширования каталога .pip
. Я не видел много использования этого, отчасти потому, что он так заметно помечен как «экспериментальный».