CI設定のパフォーマンス
中断可能なパイプライン
デフォルトでは、すべてのジョブは割り込み可能です。ただし、dont-interrupt-me ジョブはmainで自動的に実行され、それ以外はmanual となります。
マージリクエストに新しいコミットをプッシュしても実行中のパイプラインを終了させたい場合は、プッシュする前に必ずdont-interrupt-me ジョブを開始してください。
Git フェッチキャッシュ
GitLab.comはpack-objectsキャッシュを使用しているため、同じパイプラインの同時GitフェッチはGitalyサーバー上で(常に)重複排除され、(利用可能な場合は)キャッシュから提供されます。
これは以下の理由でうまく機能します:
- pack-objectsキャッシュはGitLab.comのすべてのGitalyサーバーで有効になっています。
- 
gitlab-org/gitlabの CI/CDGit 戦略設定は Git cloneで、すべてのジョブが同じデータを取得するようにし、キャッシュのヒット率を最大にしています。
- ジョブごとに Git の全履歴をダウンロードするのを避けるために、shallow cloneを使っています。
キャッシュ戦略
- デフォルトでは、すべてのジョブはキャッシュをプルするだけです。
- すべてのジョブは空のキャッシュでパスできなければなりません。言い換えれば、キャッシュはジョブを高速化するためだけに存在します。
- 現在、.gitlab/ci/global.gitlab-ci.ymlで、固定キーで定義されたいくつかの異なるキャッシュ定義があります:- .setup-test-env-cache
- .ruby-cache
- .static-analysis-cache
- .rubocop-cache
- .ruby-gems-coverage-cache
- .ruby-node-cache
- .qa-cache
- .yarn-cache
- 
.assets-compile-cache(キーは${NODE_ENV}を含むので、実際には2つの異なるキャッシュです)。
 
- これらのキャッシュ定義は複数のアトミック・キャッシュで Composer されています。
- 2時間ごとにmaintenanceスケジュールされたパイプラインで実行される以下のジョブのみがキャッシュにプッシュ(つまり更新)されます:- 
update-setup-test-env-cache.gitlab/ci/rails.gitlab-ci.ymlで定義されています。
- 
update-gitaly-binaries-cache.gitlab/ci/rails.gitlab-ci.ymlで定義されています。
- 
update-rubocop-cache.gitlab/ci/rails.gitlab-ci.ymlで定義されています。
- 
update-qa-cache.gitlab/ci/qa.gitlab-ci.ymlで定義されています。
- 
update-assets-compile-production-cache.gitlab/ci/frontend.gitlab-ci.ymlで定義されています。
- 
update-assets-compile-test-cache.gitlab/ci/frontend.gitlab-ci.ymlで定義されています。
- 
update-storybook-yarn-cache.gitlab/ci/frontend.gitlab-ci.ymlで定義されています。
 
- 
- これらのジョブは、pipeline:update-cacheラベルを持つマージリクエストで実行させることもできます (これはキャッシュキーを更新する MR でキャッシュをウォームアップするのに便利です)。
アーティファクト戦略
アップロード/ダウンロードの時間とコストを削減し、アーティファクトのストレージを削減するために、ジョブによって保存および取得されるアーティファクトを最小限に制限します。
コンポーネントのキャッシュ
GitLabのいくつかの外部コンポーネント(GitLab Workhorseやフロントエンドのアセット)は、テストを実行するための前段階としてソースからビルドする必要があります。
cache-workhorse
今回のMR、そして今回のMRでは、cache-workhorse という新しいジョブを紹介しました:
- すべての GitLab.comgitlab-org/gitlabスケジュールパイプラインに対して自動的に実行されます。
- 
workhorse/フォルダに触れたmasterのコミットに対して自動的に実行されます。
- は、GitLab.com のgitlab-orgのキャッシング関連ファイルに触れる MR に対して手動で実行されます。
このジョブは、GitLab テストスイート(tmp/tests/gitlab-workhorse 以下)で必要な GitLab Workhorse バイナリを含む汎用パッケージをダウンロードしようとします。
- パッケージの URL が 404 を返した場合
- 
scripts/setup-test-envを実行し、GitLab Workhorse のバイナリがビルドされます。
- その後、バイナリを含むアーカイブを作成し、汎用パッケージとしてアップロードします。
 
- 
- そうでなければ、パッケージがすでに存在する場合、ジョブを正常に終了します。
また、setup-test-env のジョブを変更しました:
- 最初にGitLab Workhorse汎用パッケージをダウンロードし、cache-workhorse。
- パッケージの取得に成功すると、その内容が適切なフォルダ(例えば、tmp/tests/gitlab-workhorse)に配置され、scripts/setup-test-envを後で実行したときにバイナリがビルドされるのを防ぎます。
- パッケージの URL が 404 を返した場合、動作は現在のものと変わりません: GitLab Workhorse のバイナリはscripts/setup-test-envの一部としてビルドされます。
git rev-parse HEAD:workhorse )。
cache-assets
このMRでは、cache-assets:test 、cache-assets:test as-if-foss、cache-assets:production の3つの新しいジョブを紹介しました:
- 以下のジョブを導入しました。$CACHE_ASSETS_AS_PACKAGE == "true"
- すべての GitLab.comgitlab-org/gitlabスケジュールパイプラインに対して自動的に実行されます。
- アセット関連フォルダに触れたmasterのコミットに対して自動的に実行されます。
- は、GitLab.com のgitlab-orgのキャッシング関連ファイルに触れる MR に対して手動で実行されます。
このジョブは、GitLab テストスイートで必要となる GitLab コンパイル済みアセットを含む汎用パッケージをダウンロードしようとします (app/assets/javascripts/locale/**/app.js とpublic/assets のもとで)。
- パッケージの URL が 404 を返した場合
- 
bin/rake gitlab:assets:compileを実行し、GitLabアセットがコンパイルされるようにします。
- その後、アセットを含むアーカイブを作成し、汎用パッケージとしてアップロードします。パッケージのバージョンはassetsフォルダのハッシュ合計に設定されます。
 
- 
- そうでなければ、パッケージがすでに存在する場合、ジョブを正常に終了します。
compile-*-assets
また、compile-test-assets、compile-test-assets as-if-foss 、compile-production-assets のジョブを変更しました:
- まず “ネイティブ “キャッシュアセットをダウンロードします:
- コンパイルされたアセット。
- 
cached-assets-hash.txtファイル アセットが依存するすべてのソースファイルのSHA25616進ダイジェストを含みます。このファイルのリストは悲観的なリストで、アセットはこれらのファイルのいくつかに依存しないかもしれません。最悪の場合、アセットをより頻繁にコンパイルすることになります。このファイルはアセットがコンパイルされた後に作成されます。 
 
- 次に、アセットが依存するすべてのソースファイルのSHA25616進ダイジェストを、現在のチェックアウトされたブランチについて計算します。このヘックスダイジェストをGITLAB_ASSETS_HASH変数に格納します。
- 
$CACHE_ASSETS_AS_PACKAGE == "true"の場合、cache-assets:*によってビルドされアップロードされた汎用パッケージをダウンロードします。- チェックアウトしたブランチのキャッシュが最新であれば、ネイティブキャッシュとキャッシュパッケージをダウンロードします。遺伝的パッケージをダウンロードしないことで最適化することもできますが、ネイティブキャッシュは2時間ごとにしか再構築されないため、実際には非常に頻繁に古くなります。
 
- 
私たちは assets_compile_script関数を実行します。この関数は内部でassets:compileRake タスク を実行します。このタスクは、アセットをコンパイルする必要があるかどうかを決定します。 $GITLAB_ASSETS_HASHからのHEADSHA256hexdigest とcached-assets-hash.txtからのmasterhexdigest を比較します。
- ハッシュが同じなら、何もコンパイルしません。異なる場合は、アセットをコンパイルします。
