- 멀티 스테이지 빌드는 최종 결과 이미지를 최적화하기에 유리하다.
예제 17-5 스크립트 가독성과 이미지 최적화를 모두 고려한 멀티 스테이지 Dockerfile 스크립트
FROM diamol/base AS download
ARG DATASET_URL=https://archive.ics.uci.edu/ml/machine-learning-databases/url/url_svmlight.tar.gz
RUN wget -O dataset.tar.gz ${DATASET_URL}
FROM diamol/base AS expand
COPY --from=download dataset.tar.gz .
RUN tar xvzf dataset.tar.gz
FROM diamol/base
WORKDIR /dataset/url_svmlight
COPY --from=expand url_svmlight/Day1.svm .
- 스테이지별로 어떤 단계를 밟는 중인지 이해하기 쉬우면서도 인스트럭션을 줄이느라 복잡하게 명령어를 합칠 필요가 없다.
- 최종적으로 빌드되는 이미지에는 앞선 단계에서 명 시적으로 복사해 온 파일만이 포함되기 때문이다.
실습 인자 target의 값을 지정하면 해당 스테이지에서 멀티 스테이지 빌드를 중단할 수 있다. v3 버전 이미지의 빌드를 각 스테이지에서 중단해 보자.
001) ➜ cd ch17/exercises/ml-dataset
002)
003) ➜ ml-dataset git:(main) docker image build -t diamol/ch17-ml-dataset:v3 -f Dockerfile.v3 .
004) [+] Building 42.3s (11/11) FINISHED
005) => exporting to image 0.0s
006) => => naming to docker.io/diamol/ch17-ml-dataset:v3 0.0s
007)
008) ➜ ml-dataset git:(main) docker image build -t diamol/ch17-ml-dataset:v3-download -f Dockerfile.v3 --target download .
009) [+] Building 1.3s (6/6) FINISHED
010) => exporting to image 0.4s
011) => => naming to docker.io/diamol/ch17-ml-dataset:v3-download 0.0s
012)
013) ➜ ml-dataset git:(main) docker image build -t diamol/ch17-ml-dataset:v3-expand -f Dockerfile.v3 --target expand .
014) [+] Building 4.2s (8/8) FINISHED
015) => exporting to image 3.1s
016) => => naming to docker.io/diamol/ch17-ml-dataset:v3-expand 0.0s
017)
018) ➜ ml-dataset git:(main) docker image ls -f reference=diamol/ch17-ml-dataset
019) REPOSITORY TAG IMAGE ID CREATED SIZE
020) diamol/ch17-ml-dataset v3-download a0a95962f311 2 minutes ago 252MB
021) diamol/ch17-ml-dataset v3-expand 0afb882fce4c About a minute ago 2.46GB
022) diamol/ch17-ml-dataset v3 b8ef7c3aa7aa About a minute ago 25.3MB
- 중단 이미지를 보면 디스크 용량이 어디에 사용됐는지 알 수 있다.
실습 이번 실습에서는 최소한의 요소만 설치된 젠킨스 이미지를 만들어 볼 것이다. 아직 완전한 이미지가 아니므로 지금 만든 이미지는 정상적으로 실행되지 않는다. Doc kerfile 스크립트를 보면, 먼저 젠킨스 자바 배포 파일을 내려받은 다음 최소한의 설정을 적용한다. V2 버전 스크립트는 캐시를 잘 활용하는데, 이미지 내용을 바꿔 보면 이 캐시의 효과를 알 수 있다.
cd ch17/exercises/jenkins
# 일반 이미지 v1과 최적화 이미지 v2를 빌드한다
docker image build -t diamol/ch17-jenkins:v1 .
docker image build -t diamol/ch17-jenkins:v2 -f Dockerfile.v2 .
# 두 빌드에서 모두 사용되는 설정 파일을 수정한다
echo 2.0 > jenkins.install.UpgradeWizard.state
# 두 이미지를 다시 빌드하고 빌드 시간을 확인한다
docker image build -t diamol/ch17-jenkins:v1 .
docker image build -t diamol/ch17-jenkins:v2 -f Dockerfile.v2 .
- 캐시를 잘 활용하면 소스 코드를 수정할 때마다 CI/CD 파이프라인에서 시간을 낭비하지 않고도 이미지를 빌드하고 푸시할 수 있다.
- 하지만 RUN 인스트럭션을 사용해 내려받거나 설치한 다른 소프트웨어처럼 불필요한 요소까지 캐싱하지 않도록 주의해야 한다.
- 이렇게 캐싱된 소프트웨어는 Dockerfile 스크립트에서 해당 인스트럭션을 수정할 때까지 그대로 캐시에 유지된다.
- 그리고 이미지에 패키지를 추가할 때는 정확한 버전을 명시해 실행 또는 업데이트 대상을 명확히 한다.
- 예제 17-3을 보면 apt 명령에서 정확한 버전을 명시했고, 젠킨스 예제에서는 ARG 인스트럭션에서 내려받을 버전을 명시했다.
- 두 가지 방법 모두 버전을 변경하지 않는 한 캐시를 그대로 활용한다.