【问题标题】:Share Kaniko Cache for Multi Stage Docker Builds with CloudBuild使用 CloudBuild 共享用于多阶段 Docker 构建的 Kaniko 缓存
【发布时间】:2020-02-09 15:35:06
【问题描述】:

我正在编写一个 CloudBuild 脚本,该脚本构建一个用于集成测试的多阶段 Docker 映像。为了优化构建脚本,我选择使用Kaniko。 Dockerfile 和 cloudbuild.yaml 文件的相关部分如下所示。

cloudbuild.yaml

steps:
  # Build BASE image
  - name: gcr.io/kaniko-project/executor:v0.17.1
    id: buildinstaller
    args:
      - --destination=gcr.io/$PROJECT_ID/<MY_REPO>-installer:$BRANCH_NAME
      - --destination=gcr.io/$PROJECT_ID/<MY_REPO>-installer:$SHORT_SHA
      - --cache=true
      - --cache-ttl=24h
      - --cache-repo=gcr.io/$PROJECT_ID/<MY_REPO>/cache
      - --target=installer
  # Build TEST image
  - name: gcr.io/kaniko-project/executor:v0.17.1
    id: buildtest
    args:
      - --destination=gcr.io/$PROJECT_ID/<MY_REPO>-test:$BRANCH_NAME
      - --destination=gcr.io/$PROJECT_ID/<MY_REPO>-test:$SHORT_SHA
      - --cache=true
      - --cache-ttl=24h
      - --cache-repo=gcr.io/$PROJECT_ID/<MY_REPO>/cache
      - --target=test-image
    waitFor:
      - buildinstaller
  # --- REMOVED SOME CODE FOR BREVITY ---
  # Build PRODUCTION image
  - name: gcr.io/kaniko-project/executor:v0.17.1
    id: build
    args:
      - --destination=gcr.io/$PROJECT_ID/<MY_REPO>:$BRANCH_NAME
      - --destination=gcr.io/$PROJECT_ID/<MY_REPO>:$SHORT_SHA
      - --destination=gcr.io/$PROJECT_ID/<MY_REPO>:latest
      - --cache=true
      - --cache-ttl=24h
      - --cache-dir=/cache
      - --target=production-image
    waitFor:
      - test # TODO: This will run after tests which were not included here for brevity
images:
  - gcr.io/$PROJECT_ID/<MY_REPO>

Dockerfile

FROM ruby:2.5-alpine AS installer

# Expose port
EXPOSE 3000

# Set desired port
ENV PORT 3000

# set the app directory var
ENV APP_HOME /app
RUN mkdir -p ${APP_HOME}
WORKDIR ${APP_HOME}

# Install necessary packanges
RUN apk add --update --no-cache \
  build-base curl less libressl-dev zlib-dev git \
  mariadb-dev tzdata imagemagick libxslt-dev \
  bash nodejs

# Copy gemfiles to be able to bundle install
COPY Gemfile* ./

#############################
# STAGE 1.5: Test build #
#############################
FROM installer AS test-image

# Set environment
ENV RAILS_ENV test

# Install gems to /bundle
RUN bundle install --deployment --jobs $(nproc) --without development local_gems 

# Add app files
ADD . .
RUN bundle install --with local_gems

#############################
# STAGE 2: Production build #
#############################
FROM installer AS production-image

# Set environment
ENV RAILS_ENV production

# Install gems to /bundle
RUN bundle install --deployment --jobs $(nproc) --without development test local_gems 

# Add app files
ADD . .
RUN bundle install --with local_gems

# Precompile assets
RUN DB_ADAPTER=nulldb bundle exec rake assets:precompile assets:clean

# Puma start command
CMD ["bundle", "exec", "puma", "-C", "config/puma.rb"]

由于我的 Docker 映像是一个多阶段构建,具有 2 个独立的结束阶段,它们共享一个公共基础构建,我想在公共部分和其他两个之间共享缓存。为此,我将所有构建设置为共享相同的缓存存储库- --cache-repo=gcr.io/$PROJECT_ID/&lt;MY_REPO&gt;/cache。到目前为止,它在我所有的测试中都有效。但是,我无法确定这是否是最佳实践,或者是否会推荐其他缓存基本图像的方式。这是一个可接受的实现吗?

我遇到过Kaniko-warmer,但我无法根据我的情况使用它。

【问题讨论】:

  • 我也在为此苦苦挣扎。我最初将我的目的地设置为不同的图像,并且没有--cache-repo 参数,图像之间就没有缓存层的重用。我更改了步骤以构建同一图像的不同 标签,并且不再需要该参数。然后cache 图像出现在我的仓库中,并且缓存在步骤之间起作用。我也不确定这是否是正确的方法。
  • 我正在尝试一次构建它(我只关心最终图像),我收到一条错误消息:没有为 cmd COPY --from=builder /venv /venv 找到缓存层
  • 除了缓存之外,--skip-unused-stages 也可能使您的构建受益。例如,此标志将确保您的生产版本也不会构建测试映像。

标签: docker continuous-integration google-cloud-build kaniko


【解决方案1】:

在提及有关如何缓存基本映像的任何最佳实践之前,请先了解一些最佳实践,以便optimize the performance of your build。由于您已经使用 Kaniko 并且正在缓存存储库中的图像,我相信您的实现遵循上述最佳实践。

我要提出的唯一建议是使用Google Cloud Storage 来重用您之前构建的结果。如果您的构建需要很长时间并且生成的文件不是很多,并且将它们复制到 Cloud Storage 并不需要很多时间,这将加快您的构建速度。

此外,关于Optimization of your build cache,以下文章中还介绍了一些最佳实践。我认为其中最重要的是:

"将经常更改的构建步骤放在 Dockerfile 的底部。如果将它们放在顶部,Docker 将无法将其构建缓存用于其他不经常更改的构建步骤。因为通常会使用新的 Docker 映像为每个新版本的源代码构建,尽可能晚地将源代码添加到 Dockerfile 中的镜像”。

最后我要考虑的另一件事是the cache expiration time

请记住,它必须进行适当的配置,以免丢失任何依赖项的更新,但不会在没有任何用途的情况下运行构建。

您可能认为有用的更多链接(请记住,这些不是 Google 来源):

Docker documentation about Multi-stage Builds

Using Multi-Stage Builds to Simplify And Standardize Build Processes

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2020-04-16
    • 1970-01-01
    • 2019-03-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-03-09
    相关资源
    最近更新 更多