懵了,構建一個 Docker 映象花 60 分鐘?如何提高效率?

作者 | Andy

來源 | 進擊雲原生

最近,有一個需求:向映象構建管道添加一個參數,以允許使用者在構建時配置超時時間。

我們計劃在構建時配置 10 分鐘的默認超時,並且允許使用者覆蓋此配置,因為他們的某些映象構建需要長達 60 分鐘才能完成。而且每天都在進行多次構建。

為了便於閱讀,我刪除了一些內容,Dockerfile 看起來像這樣:

FROM ubuntu:focal-20210119
RUN apt-get -y update && \
apt-get -y upgrade && \
apt-get install -y --no-install-recommends \
dos2unix \
jq \
libpython3.10 \
python3-pip \
software-properties-common \
tar \
unzip \
wget \
zip && \
echo"Cleaning up" && \
rm -rf /var/lib/apt/lists/* && \
apt-get clean
RUN pip3 install boto3 flask

RUNecho"Installing AWS CLIv2" && \
TMPDIR=$(mktemp -d) && \
wget -P $TMPDIR --no-check-certificate "https://awscli.amazonaws.com/awscli-exe-linux-x86_64.zip" && \
unzip $TMPDIR/awscli-exe-linux-x86_64.zip -d $TMPDIR && \
$TMPDIR/aws/install && \
rm -rf /usr/local/aws-cli/v2/dist/awscli/examples/ && \
rm -rf $TMPDIR
RUNecho"Installing kubectl" && \
wget -P /usr/bin/ --no-check-certificate https://storage.googleapis.com/kubernetes-release/release/$(wget --no-check-certificate -O - https://storage.googleapis.com/kubernetes-release/release/stable.txt)/bin/linux/amd64/kubectl && \
chmod +x /usr/bin/kubectl
# Install the app
COPY dummyapp.py /app/

rebuild 的重點是應用程序更改,而不是對底層依賴項的更改。

由於 Dockerfile 已被精簡,現在大約 5 分鐘內構建完成。但講真,這時間仍然很長,因為通常可能只要幾秒鐘。

這是我構建的部分輸出:

# time docker build --no-cache --progress=plain -t test:test .
Sending build context to Docker daemon 3.072kB
Step 1/5 : FROM ubuntu:focal-20210119
---> f63181f19b2f
Step 2/5 : RUN apt-get -y update && apt-get -y upgrade && apt-get install -y --no-install-recommends dos2unix jq libpython3.10 python3-pip software-properties-common tar unzip wget zip && echo"Cleaning up" && rm -rf /var/lib/apt/lists/* && apt-get clean
---> Running in 37bff266446e
Get:1 http://security.ubuntu.com/ubuntu focal-security InRelease [114 kB]
Get:2 http://security.ubuntu.com/ubuntu focal-security/main amd64 Packages [1470 kB]

45400K .......... .......... .......... .......... .......... 99% 2.31M 0s
45450K .......... .......... .......... .......... ...... 100% 8.05M=18s
2022-01-2819:37:06 (2.40 MB/s) - '/usr/bin/kubectl' saved [46587904/46587904]
Removing intermediate container 86223b438cef
---> b8f9a2cc1d9a
Step 6/6 : COPY dummyapp.py /app/
---> b95d22cdca6f
Successfully built b95d22cdca6f
Successfully tagged test:test
real 5m11.679s
user0m1.248s
sys 0m1.961s

怎樣才能讓這個構建更快?

每次構建這個 Dockerfile 時,都會重複很多處理,其結果不太可能經常改變。

  • 更新 ubuntu 軟體包列表

  • 升級 ubuntu 軟體包

  • 安裝一些額外的軟體包

  • 使用 pip3 安裝一些 python 包

  • 安裝 AWS CLI

  • 安裝 kubectl

  • 安裝應用程序

還 FROM 一個相當舊的 Ubuntu 版本,需要升級更多的包,因此升級步驟將花費更長的時間。

此映象的大多數重新 build 的目的是合併應用程序更改(即僅 Dockerfile 中的最後一行)。因此,最明顯的變化是將此 Dockerfile 拆分為 2 個(或更多)Dockerfile,並且將 FROM 語句更改為使用最新的 Ubuntu 基礎映象。

第一個 Dockerfile 看起來像這樣:

FROM ubuntu:latest
RUN apt-get -y update && \
apt-get -y upgrade && \
apt-get install -y --no-install-recommends \
dos2unix \
jq \
libpython3.10 \
python3-pip \
software-properties-common \
tar \
unzip \
wget \
zip && \
echo"Cleaning up" && \
rm -rf /var/lib/apt/lists/* && \
apt-get clean
RUN pip3 install boto3 flask

RUNecho"Installing AWS CLIv2" && \
TMPDIR=$(mktemp -d) && \
wget -P $TMPDIR --no-check-certificate "https://awscli.amazonaws.com/awscli-exe-linux-x86_64.zip" && \
unzip $TMPDIR/awscli-exe-linux-x86_64.zip -d $TMPDIR && \
$TMPDIR/aws/install && \
rm -rf /usr/local/aws-cli/v2/dist/awscli/examples/ && \
rm -rf $TMPDIR
RUNecho"Installing kubectl" && \
wget -P /usr/bin/ --no-check-certificate https://storage.googleapis.com/kubernetes-release/release/$(wget --no-check-certificate -O - https://storage.googleapis.com/kubernetes-release/release/stable.txt)/bin/linux/amd64/kubectl && \
chmod +x /usr/bin/kubectl

第二個 Dockerfile 可能看起來像這樣:

FROM dummyapp-dependencies:latest
# Install the app
COPY dummyapp.py /app/

構建第一個 Dockerfile 並沒有為我們節省任何時間,雖然需要大約 5 分鐘,但只需要相對不頻繁地構建第一個 Dockerfile。

然而,構建第二個 Dockerfile 的效果要好得多,只需要大約 2 秒:

# time docker build --no-cache --progress=plain -t tes
t:test -f Dockerfile.app .
Sending build context to Docker daemon 5.12kB
Step 1/2 : FROM dummyapp:1.0.0
pull access denied for dummyapp, repository does not exist or may require 'docker login': denied: requested access to the resource is denied
real 0m2.125s
user0m0.043s
sys 0m0.030s

鑑於應用程序的更改比底層依賴項更頻繁,剛剛節省了大量時間。

相關文章

Docker 映象詳細講解

Docker 映象詳細講解

作者 | 微楓Micromaple 來源 | CSDN部落格 前言 大家好,本文是對 Docker 映象的詳細講解,講解了如何安裝 Dock...

在 MacOS 上運行 Docker 太慢!

在 MacOS 上運行 Docker 太慢!

你是否也覺得,MacOS 中的 Docker 非常慢?本文作者想出了解決辦法,不妨來試試看。 原文連結:https://www.paolom...

Docker 如何安全地進入到容器內部

Docker 如何安全地進入到容器內部

作者 | 飛向星的客機 來源 | CSDN部落格 🌟 前言 映象是構建容器的藍圖,Docker 以映象為模板,構建出容器。 容器在映象的基礎...

40 張圖 詳解 Docker 容器監控

40 張圖 詳解 Docker 容器監控

作者 | 飛向星的客機 來源 | CSDN部落格 前言 在企業中,通常業務是不允許隨意停止的,否則將給企業帶來巨大的經濟損失。 運維工程師要...