Peter Grainger의 답변을 확장 하여 Docker 17.05부터 다단계 빌드 를 사용할 수있었습니다 . 공식 페이지 상태 :
다단계 빌드에서는 FROM
Dockerfile에서 여러 명령문 을 사용 합니다. 각 FROM
명령어는 다른베이스를 사용할 수 있으며 각 명령어는 새로운 빌드 단계를 시작합니다. 최종 이미지에서 원하지 않는 모든 것을 남겨두고 한 단계에서 다른 단계로 아티팩트를 선택적으로 복사 할 수 있습니다.
이 점을 염두에 두는 것은 Dockerfile
세 가지 빌드 단계 를 포함하는 나의 예입니다 . 클라이언트 웹 애플리케이션의 프로덕션 이미지를 작성하기위한 것입니다.
# Stage 1: get sources from npm and git over ssh
FROM node:carbon AS sources
ARG SSH_KEY
ARG SSH_KEY_PASSPHRASE
RUN mkdir -p /root/.ssh && \
chmod 0700 /root/.ssh && \
ssh-keyscan bitbucket.org > /root/.ssh/known_hosts && \
echo "${SSH_KEY}" > /root/.ssh/id_rsa && \
chmod 600 /root/.ssh/id_rsa
WORKDIR /app/
COPY package*.json yarn.lock /app/
RUN eval `ssh-agent -s` && \
printf "${SSH_KEY_PASSPHRASE}\n" | ssh-add $HOME/.ssh/id_rsa && \
yarn --pure-lockfile --mutex file --network-concurrency 1 && \
rm -rf /root/.ssh/
# Stage 2: build minified production code
FROM node:carbon AS production
WORKDIR /app/
COPY --from=sources /app/ /app/
COPY . /app/
RUN yarn build:prod
# Stage 3: include only built production files and host them with Node Express server
FROM node:carbon
WORKDIR /app/
RUN yarn add express
COPY --from=production /app/dist/ /app/dist/
COPY server.js /app/
EXPOSE 33330
CMD ["node", "server.js"]
.dockerignore
의 내용을 반복 .gitignore
(그것을 방지 파일 node_modules
및 결과 dist
복사되는 프로젝트의 디렉토리) :
.idea
dist
node_modules
*.log
이미지를 빌드하는 명령 예 :
$ docker build -t ezze/geoport:0.6.0 \
--build-arg SSH_KEY="$(cat ~/.ssh/id_rsa)" \
--build-arg SSH_KEY_PASSPHRASE="my_super_secret" \
./
개인 SSH 키에 암호가 없으면 빈 SSH_KEY_PASSPHRASE
인수를 지정하십시오 .
이것이 작동하는 방식입니다.
1). 첫 번째 단계에서 package.json
, yarn.lock
파일과 개인 SSH 키라는 이름의 첫 번째 중간 이미지로 복사됩니다 sources
. 더 이상의 SSH 키 암호 문구 프롬프트를 피하기 위해 자동으로 추가됩니다 ssh-agent
. 드디어yarn
명령은 NPM에서 필요한 모든 종속성을 설치하고 SSH를 통해 Bitbucket에서 개인 git 리포지토리를 복제합니다.
2). 두 번째 단계는 웹 애플리케이션의 소스 코드를 빌드 및 축소 dist
하여 다음 중간 이미지의 디렉토리에 배치합니다 production
. 설치된 소스 코드 는 첫 번째 단계에서 생성 된 node_modules
이미지에서 sources
다음 줄로 복사됩니다 .
COPY --from=sources /app/ /app/
아마도 다음 줄이 될 수도 있습니다.
COPY --from=sources /app/node_modules/ /app/node_modules/
node_modules
여기 첫 번째 중간 이미지의 디렉토리 만 SSH_KEY
있으며 SSH_KEY_PASSPHRASE
더 이상 인수가 없습니다. 빌드에 필요한 나머지는 모두 프로젝트 디렉토리에서 복사됩니다.
삼). 세 번째 단계 에서는 이름이 지정된 두 번째 중간 이미지의 디렉토리 ezze/geoport:0.6.0
만 포함 하고 웹 서버를 시작하기 위해 Node Express를 설치 하여 태그 될 최종 이미지의 크기를 줄 입니다.dist
production
이미지 나열은 다음과 같은 출력을 제공합니다.
REPOSITORY TAG IMAGE ID CREATED SIZE
ezze/geoport 0.6.0 8e8809c4e996 3 hours ago 717MB
<none> <none> 1f6518644324 3 hours ago 1.1GB
<none> <none> fa00f1182917 4 hours ago 1.63GB
node carbon b87c2ad8344d 4 weeks ago 676MB
태그가 지정되지 않은 이미지는 첫 번째 및 두 번째 중간 빌드 단계에 해당합니다.
당신이 실행하는 경우
$ docker history ezze/geoport:0.6.0 --no-trunc
당신은 어떤이의 언급이 표시되지 않습니다 SSH_KEY
및 SSH_KEY_PASSPHRASE
최종 이미지에서.