ジョブの実行方法を制御する
- プラン: Free、Premium、Ultimate
- 提供形態: GitLab.com、GitLab Self-Managed、GitLab Dedicated
新しいパイプラインを開始する前に、GitLabはそのパイプラインの設定をチェックし、そのパイプラインのどのジョブが実行可能かを判断します。rulesを使用すると、変数の値やパイプラインの種類などの条件に応じてジョブを実行するように設定できます。ジョブルールを使用する場合は、重複パイプラインを回避する方法を確認してください。パイプラインの作成を制御するには、workflow:rulesを使用します。
手動の実行が必要なジョブを作成する
ユーザーが開始しない限り、ジョブが実行されないように設定できます。これはmanual job(手動ジョブ)と呼ばれます。本番環境へのデプロイなど、手動ジョブの使用が適切な場合があります。
ジョブを手動ジョブとして指定するには、.gitlab-ci.ymlファイルのジョブにwhen: manualを追加します。
デフォルトでは、手動ジョブはパイプラインの開始時にスキップ済みと表示されます。
保護ブランチを使用して、未許可のユーザーによる実行を防ぎ、より厳密に手動デプロイを保護できます。
アーカイブされた手動ジョブは実行されません。
手動ジョブの種類
手動ジョブには、オプションとブロックの2種類があります。
オプション手動ジョブでは、次のようになります:
allow_failureがtrueになります。これは、rules以外でwhen: manualが定義されたジョブのデフォルト設定です。- このジョブのステータスは、パイプライン全体のステータスに影響を及ぼすことはありません。すべての手動ジョブが失敗しても、パイプラインは正常に完了する可能性があります。
ブロック手動ジョブでは、次のようになります:
allow_failureがfalseになります。これは、rules内でwhen: manualが定義されたジョブのデフォルト設定です。- パイプラインは、ジョブが定義されているステージで停止します。パイプラインの実行を継続するには、手動ジョブを実行します。
- パイプラインが完了しているが有効になっているプロジェクトのマージリクエストは、ブロックされたパイプラインとはマージできません。
- パイプラインのステータスにはblocked(ブロック)と表示されます。
trigger:strategyを使用してトリガーされたパイプラインで手動ジョブを使用する場合、手動ジョブの種類によっては、パイプラインの実行中にトリガージョブのステータスに影響を及ぼす可能性があります。
手動ジョブを実行する
手動ジョブを実行するには、割り当てられたブランチにマージする権限が必要です:
- パイプライン、ジョブ、環境、またはデプロイビューに移動します。
- 手動ジョブの横にある実行( )を選択します。
手動ジョブの実行時に変数を指定する
手動ジョブの実行時に、ジョブ固有のCI/CD変数を追加で指定できます。CI/CD変数を使用するジョブの実行を変更する場合は、ここで変数を指定します。
手動ジョブを実行して追加の変数を指定するには、次のようにします:
- パイプラインビューで、手動ジョブの名前を選択します。実行( )を選択しないでください。
- フォームに変数のキーと値のペアを追加します。
- ジョブの実行を選択します。
手動ジョブを実行する権限を持つプロジェクトメンバーは誰でも、ジョブを再試行し、ジョブが最初に実行されたときに指定された変数を表示できます。これには次のユーザーが含まれます:
- 公開プロジェクトの場合: 少なくともデベロッパーロールを持つユーザー。
- 非公開または内部プロジェクトの場合: 少なくともゲストロールを持つユーザー。
手動ジョブの変数として機密情報を入力する場合は、この表示レベルを考慮してください。
CI/CD設定または.gitlab-ci.ymlファイルで定義済みの変数を追加すると、新しい値で変数がオーバーライドされます。このプロセスでオーバーライドされた変数は展開され、マスクされません。
更新した変数で手動ジョブを再試行する
手動で指定した変数を使用して以前に実行した手動ジョブを再試行する際、変数を更新することも、同じ変数を使用することもできます。
以前に指定した変数を使用して手動ジョブを再試行するには、次のようにします:
- 同じ変数を使用する場合:
- ジョブの詳細ページから、再試行( )を選択します。
- 変数を更新する場合:
- ジョブの詳細ページから、CI/CD変数を更新( )を選択します。
- 前回の実行で指定した変数は、フォームに自動入力されます。このフォームから、CI/CD変数を追加、変更、または削除できます。
- ジョブを再実行を選択します。
手動ジョブの確認を必須にする
when: manualとmanual_confirmationを組み合わせて使用すると、手動ジョブの確認を必須にできます。これにより、本番環境へのデプロイなど、機密性の高いジョブにおける誤ったデプロイや削除を防止できます。
ジョブをトリガーするときは、実行前に操作を確認する必要があります。
手動ジョブを保護する
- プラン: Premium、Ultimate
- 提供形態: GitLab.com、GitLab Self-Managed、GitLab Dedicated
保護環境を使用して、手動ジョブの実行が許可されるユーザーのリストを定義します。保護環境に関連付けられたユーザーにのみ、手動ジョブをトリガーする権限を付与できます。これにより、以下が可能になります:
- 環境にデプロイできるユーザーをより厳密に制限する。
- 承認されたユーザーが「承認」するまでパイプラインをブロックする。
手動ジョブを保護するには、次のようにします:
ジョブに
environmentを追加します。例:deploy_prod: stage: deploy script: - echo "Deploy to production server" environment: name: production url: https://example.com when: manual rules: - if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH保護環境設定で、環境(この例では
production)を選択し、手動ジョブをトリガーすることが許可されているユーザー、ロール、またはグループをAllowed to Deploy(デプロイ許可)リストに追加します。このリストに登録されているユーザーのみがこの手動ジョブをトリガーできます。ただし、GitLab管理者は常に保護環境を使用できるため、同様にトリガーできます。
ブロック手動ジョブと保護環境を組み合わせると、後続のパイプラインステージを承認できるユーザーのリストを定義できます。保護された手動ジョブにallow_failure: falseを追加すると、許可されたユーザーがその手動ジョブをトリガーした後にのみ、パイプラインの次のステージが実行されます。
遅延後にジョブを実行する
when: delayedを使用すると、待機期間後にスクリプトを実行したり、ジョブが直ちにpendingステータスになるのを回避したりできます。
期間は、start_inキーワードを使用して設定できます。start_inの値は、単位を指定しない場合、秒単位の経過時間です。最小値は1秒、最大値は1週間です。有効な値の例は以下のとおりです:
'5'(単位のない値は一重引用符で囲む必要があります)5 seconds30 minutes1 day1 week
ステージに遅延ジョブがある場合、パイプラインは遅延ジョブが完了するまで先に進みません。このキーワードを使用すると、異なるステージ間に遅延を挿入できます。
遅延ジョブのタイマーは、直前のステージが完了すると直ちに開始されます。他の種類のジョブと同じように、前のステージが正常に終了しない限り、遅延ジョブのタイマーは開始されません。
次の例では、前のステージが完了してから30分後に実行する、timed rollout 10%という名前のジョブを作成しています:
timed rollout 10%:
stage: deploy
script: echo 'Rolling out 10% ...'
when: delayed
start_in: 30 minutes
environment: production遅延ジョブのアクティブなタイマーを停止するには、スケジュールを解除( )をクリックします。このジョブは、スケジュールによる自動実行ができなくなります。ただし、ジョブを手動で実行することはできます。
遅延ジョブを手動で開始するには、スケジュールを解除( )をクリックして遅延タイマーを停止してから、実行( )をクリックします。GitLab Runnerがすぐにジョブを開始します。
アーカイブされた遅延ジョブは実行されません。
大規模なジョブを並列化する
大規模なジョブを複数の小規模なジョブに分割して並列実行するには、.gitlab-ci.ymlファイルでparallelキーワードを使用します。
言語とテストスイートによって、並列化を有効にする方法が異なります。たとえば、Rubyのテストを並列実行するには、Semaphore Test BoostersとRSpecを使用します:
# Gemfile
source 'https://rubygems.org'
gem 'rspec'
gem 'semaphore_test_boosters'test:
parallel: 3
script:
- bundle
- bundle exec rspec_booster --job $CI_NODE_INDEX/$CI_NODE_TOTALその後、新しいパイプラインビルドのジョブタブに移動すると、RSpecジョブが3つの個別のジョブに分割されていることを確認できます。
Test Boostersは、使用状況の統計情報を作成者に報告します。
並列ジョブの1次元マトリクスを実行する
単一のパイプラインで1つのジョブを複数回並列実行し、ジョブの各インスタンスで異なる変数値を使用する場合は、parallel:matrixキーワードを使用します:
deploystacks:
stage: deploy
script:
- bin/deploy
parallel:
matrix:
- PROVIDER: [aws, ovh, gcp, vultr]
environment: production/$PROVIDERこの例では、4つのdeploystacksジョブが作成され、PROVIDERはそれぞれ異なる値を持つCI/CD変数になります:
deploystacks: [aws]deploystacks: [ovh]deploystacks: [gcp]deploystacks: [vultr]
並列トリガージョブのマトリクスを実行する
単一のパイプラインでトリガージョブを複数回並列実行し、ジョブのインスタンスごとに異なる変数値を使用できます。
例:
deploystacks:
stage: deploy
trigger:
include: path/to/child-pipeline.yml
parallel:
matrix:
- PROVIDER: aws
STACK: [monitoring, app1]
- PROVIDER: ovh
STACK: [monitoring, backup]
- PROVIDER: [gcp, vultr]
STACK: [data]この例では、6つの並列deploystacksトリガージョブを生成します。各ジョブで、PROVIDERとSTACKに異なる値を指定し、これらの変数を使用して6つの異なる子パイプラインを作成します。
deploystacks: [aws, monitoring]
deploystacks: [aws, app1]
deploystacks: [ovh, monitoring]
deploystacks: [ovh, backup]
deploystacks: [gcp, data]
deploystacks: [vultr, data]並列マトリクスジョブごとに異なるRunnerタグを選択する
Runnerを動的に選択するには、parallel: matrixで定義された値をtagsキーワードと組み合わせて使用します:
deploystacks:
stage: deploy
script:
- bin/deploy
parallel:
matrix:
- PROVIDER: aws
STACK: [monitoring, app1]
- PROVIDER: gcp
STACK: [data]
tags:
- ${PROVIDER}-${STACK}
environment: $PROVIDER/$STACKparallel:matrixジョブからアーティファクトをフェッチする
parallel:matrixで作成したジョブからアーティファクトをフェッチするには、dependenciesキーワードを使用します。dependenciesの値には、ジョブ名を以下の形式の文字列で指定します:
<job_name> [<matrix argument 1>, <matrix argument 2>, ... <matrix argument N>]たとえば、RUBY_VERSIONが2.7で、PROVIDERがawsのジョブからアーティファクトをフェッチするには、次のようにします:
ruby:
image: ruby:${RUBY_VERSION}
parallel:
matrix:
- RUBY_VERSION: ["2.5", "2.6", "2.7", "3.0", "3.1"]
PROVIDER: [aws, gcp]
script: bundle install
deploy:
image: ruby:2.7
stage: deploy
dependencies:
- "ruby: [2.7, aws]"
script: echo hello
environment: productiondependenciesエントリを囲む引用符は必須です。
複数の並列ジョブが存在する状況でneedsを使用して特定の並列ジョブを指定する
複数の並列化されたジョブ間に依存関係を作成するには、needs:parallel:matrixを使用できます。設定には、次の2つの手法を使用できます:
matrix.式を使用すると、自動的に設定できます。- 以下に示すように、手動で設定します。
例:
linux:build:
stage: build
script: echo "Building linux..."
parallel:
matrix:
- PROVIDER: aws
STACK:
- monitoring
- app1
- app2
mac:build:
stage: build
script: echo "Building mac..."
parallel:
matrix:
- PROVIDER: [gcp, vultr]
STACK: [data, processing]
linux:rspec:
stage: test
needs:
- job: linux:build
parallel:
matrix:
- PROVIDER: aws
STACK: app1
script: echo "Running rspec on linux..."
mac:rspec:
stage: test
needs:
- job: mac:build
parallel:
matrix:
- PROVIDER: [gcp, vultr]
STACK: [data]
script: echo "Running rspec on mac..."
production:
stage: deploy
script: echo "Running production..."
environment: productionこの例では、いくつかのジョブが生成されます。並列ジョブはそれぞれ異なるPROVIDERとSTACKの値を持ちます。
- 3つの並列
linux:buildジョブ:linux:build: [aws, monitoring]linux:build: [aws, app1]linux:build: [aws, app2]
- 4つの並列
mac:buildジョブ:mac:build: [gcp, data]mac:build: [gcp, processing]mac:build: [vultr, data]mac:build: [vultr, processing]
- 1つの
linux:rspecジョブ。 - 1つの
productionジョブ。
これらのジョブには、次の3つの実行パスがあります:
- Linuxパス:
linux:rspecジョブは、mac:buildの完了を待たずに、linux:build: [aws, app1]ジョブが完了するとすぐに実行されます。 - macOSパス:
mac:rspecジョブは、linux:buildの完了を待たずに、mac:build: [gcp, data]ジョブとmac:build: [vultr, data]ジョブが完了するとすぐに実行されます。 productionジョブは、それ以前のすべてのジョブが完了するとすぐに実行されます。
並列ジョブ間のneedsを指定する
needs:parallel:matrixを使用すると、各並列マトリクスジョブの実行順序をさらに定義できます。
例:
build_job:
stage: build
script:
# ensure that other parallel job other than build_job [1, A] runs longer
- '[[ "$VERSION" == "1" && "$MODE" == "A" ]] || sleep 30'
- echo build $VERSION $MODE
parallel:
matrix:
- VERSION: [1,2]
MODE: [A, B]
deploy_job:
stage: deploy
script: echo deploy $VERSION $MODE
parallel:
matrix:
- VERSION: [3,4]
MODE: [C, D]
'deploy_job: [3, D]':
stage: deploy
script: echo something
needs:
- 'build_job: [1, A]'この例では、いくつかのジョブが生成されます。並列ジョブはそれぞれ異なるVERSIONとMODEの値を持ちます。
- 4つの並列
build_jobジョブ:build_job: [1, A]build_job: [1, B]build_job: [2, A]build_job: [2, B]
- 4つの並列
deploy_jobジョブ:deploy_job: [3, C]deploy_job: [3, D]deploy_job: [4, C]deploy_job: [4, D]
deploy_job: [3, D]ジョブは、他のbuild_jobジョブの完了を待たずに、build_job: [1, A]ジョブが完了するとすぐに実行されます。
トラブルシューティング
手動ジョブ実行時のユーザー割り当ての不整合
まれに、手動ジョブを実行したユーザーが、その手動ジョブに依存する後続ジョブの実行ユーザーとして割り当てられないことがあります。
手動ジョブに依存するジョブに割り当てられるユーザーについて厳格なセキュリティを確保する必要がある場合は、その手動ジョブを保護する必要があります。