GitLab CI/CD YAML入門:基本から応用まで徹底解説
GitLab CI/CD は、ソフトウェア開発ライフサイクルを自動化するための強力なツールです。その中心となるのが、.gitlab-ci.yml
ファイルです。この YAML ファイルに記述された設定に基づいて、コードのビルド、テスト、デプロイなどのタスクが自動的に実行されます。本記事では、.gitlab-ci.yml
の基本構造から、高度な機能までを網羅的に解説します。GitLab CI/CD を使いこなし、開発ワークフローを効率化するための知識を身につけましょう。
目次
- GitLab CI/CD とは
.gitlab-ci.yml
の基本構造- stages
- jobs
- variables
- before_script, after_script
- image
- script
- rules
- ジョブの依存関係とパイプライン
- needs
- artifacts
- dependencies (deprecated)
- 環境変数とシークレット
- Predefined variables
- CI/CD 変数の設定 (プロジェクト、グループ、インスタンス)
- マスクされた変数
- GitLab Runner の理解
- Runner の種類 (Shared Runner, Specific Runner)
- タグによるRunnerの選択
- Runner の設定 (Executor タイプ)
- 高度な設定
- include を使った設定ファイルの分割
- cache を使ったビルド時間の短縮
- services を使った依存サービスの実行
- trigger を使ったパイプラインの連鎖
- retry を使ったジョブの再実行
- parallel を使ったテストの並列実行
- パイプラインの可視化とモニタリング
- GitLab UI でのパイプラインの確認
- パイプラインのトリガーとスケジュール
- パイプライン履歴の分析
- ベストプラクティス
.gitlab-ci.yml
のバージョン管理- シークレット情報の管理
- テストの自動化
- デプロイ戦略の自動化
- トラブルシューティング
- パイプラインが失敗した場合の原因特定
- よくあるエラーとその解決策
- まとめと今後の学習
1. GitLab CI/CD とは
GitLab CI/CD (Continuous Integration/Continuous Delivery) は、ソフトウェア開発のワークフローを自動化するための統合されたツールセットです。変更がコードベースにプッシュされるたびに、自動的にビルド、テスト、デプロイを実行することで、開発サイクルを短縮し、バグの早期発見を可能にします。
- 継続的インテグレーション (CI): 開発者が頻繁にコードを共有リポジトリに統合するプラクティスです。変更が統合されるたびに、自動的にビルドとテストを実行し、早期に統合の問題を発見します。
- 継続的デリバリー (CD): ソフトウェアを本番環境に安全かつ迅速にデプロイできるようにするプラクティスです。CI の結果に基づいて、自動的にテスト環境やステージング環境にデプロイし、手動での承認を経て本番環境にデプロイすることができます。
GitLab CI/CD は、.gitlab-ci.yml
ファイルを使用して、パイプラインの定義と実行を管理します。
2. .gitlab-ci.yml
の基本構造
.gitlab-ci.yml
は、GitLab CI/CD の中核となるファイルです。プロジェクトのルートディレクトリに配置され、パイプラインの構造、ジョブの定義、依存関係などを記述します。
2.1. stages
stages
は、パイプライン内のジョブの実行順序を定義します。ステージは順番に実行され、前のステージのすべてのジョブが成功すると、次のステージが開始されます。
yaml
stages:
- build
- test
- deploy
上記の例では、build
、test
、deploy
の3つのステージが定義されています。
2.2. jobs
jobs
は、パイプライン内で実行される個々のタスクを定義します。各ジョブは、特定のステージに割り当てられ、定義されたスクリプトを実行します。
yaml
build_job:
stage: build
script:
- echo "Building the application..."
- ./build.sh
この例では、build_job
という名前のジョブが定義されています。このジョブは build
ステージに割り当てられ、script
に定義されたコマンドを実行します。
2.3. variables
variables
は、ジョブ内で使用できる変数を定義します。変数は、グローバルに定義することも、特定のジョブに対して定義することもできます。
“`yaml
variables:
APP_NAME: “my-application”
build_job:
stage: build
variables:
BUILD_DIR: “build”
script:
– echo “Building $APP_NAME in $BUILD_DIR…”
– ./build.sh -o $BUILD_DIR
“`
上記の例では、APP_NAME
というグローバル変数が定義されています。build_job
では、BUILD_DIR
というジョブ固有の変数が定義されています。スクリプト内で $APP_NAME
や $BUILD_DIR
を使用して、変数の値を参照できます。
2.4. before_script, after_script
before_script
と after_script
は、各ジョブの実行前と実行後に実行されるスクリプトを定義します。before_script
はジョブの script
より前に実行され、after_script
はジョブの script
の後に実行されます。
“`yaml
before_script:
– echo “Setting up the environment…”
– apt-get update -y && apt-get install -y some-dependency
build_job:
stage: build
script:
– echo “Building the application…”
– ./build.sh
after_script:
– echo “Cleaning up the environment…”
– rm -rf build
“`
before_script
は、依存関係のインストールや環境設定など、ジョブの実行に必要な準備を行うために使用されます。after_script
は、一時ファイルの削除やログのアーカイブなど、ジョブの実行後に必要なクリーンアップを行うために使用されます。
2.5. image
image
は、ジョブを実行する Docker イメージを指定します。GitLab Runner は、指定されたイメージをダウンロードし、そのコンテナ内でジョブを実行します。
yaml
build_job:
stage: build
image: node:16
script:
- echo "Building the application..."
- npm install
- npm run build
この例では、build_job
は node:16
イメージを使用して実行されます。ジョブのスクリプトは、Node.js 環境内で実行されます。
2.6. script
script
は、ジョブ内で実行されるコマンドを定義します。複数のコマンドは、改行で区切って記述します。
yaml
test_job:
stage: test
script:
- echo "Running tests..."
- npm test
この例では、test_job
は npm test
コマンドを実行します。
2.7. rules
rules
は、ジョブを実行するかどうかを決定するための条件を定義します。rules
を使用すると、特定のブランチ、タグ、またはファイルが変更された場合にのみジョブを実行するように設定できます。
yaml
deploy_job:
stage: deploy
script:
- echo "Deploying the application..."
- ./deploy.sh
rules:
- if: $CI_COMMIT_BRANCH == "main"
この例では、deploy_job
は CI_COMMIT_BRANCH
環境変数が main
の場合にのみ実行されます。つまり、main
ブランチへのコミット時にのみデプロイジョブが実行されます。rules
には、if
、exists
、changes
などの条件を使用できます。
3. ジョブの依存関係とパイプライン
GitLab CI/CD では、ジョブ間の依存関係を定義し、パイプラインを構築することができます。
3.1. needs
needs
は、現在のジョブが開始される前に完了する必要があるジョブを指定します。needs
を使用すると、ジョブの実行順序を明示的に制御できます。
“`yaml
build_job:
stage: build
script:
– echo “Building the application…”
– ./build.sh
test_job:
stage: test
needs: [build_job]
script:
– echo “Running tests…”
– npm test
“`
この例では、test_job
は build_job
が完了するまで開始されません。needs
を使用することで、ビルドが成功した後にのみテストを実行するように設定できます。
3.2. artifacts
artifacts
は、ジョブの実行結果として生成されたファイルを定義します。artifacts
は、後続のジョブで使用したり、ダウンロードしたりすることができます。
yaml
build_job:
stage: build
script:
- echo "Building the application..."
- ./build.sh
artifacts:
paths:
- build/*
この例では、build_job
は build
ディレクトリ内のすべてのファイルをアーティファクトとして定義します。これらのアーティファクトは、後続のジョブで使用したり、GitLab UI からダウンロードしたりすることができます。
3.3. dependencies (deprecated)
dependencies
は、古いバージョンの GitLab でアーティファクトの依存関係を定義するために使用されていました。現在は needs
と artifacts
を使用することが推奨されています。
4. 環境変数とシークレット
環境変数は、ジョブの実行環境に設定できる変数です。シークレットは、パスワードや API キーなどの機密情報を安全に格納するために使用されます。
4.1. Predefined variables
GitLab CI/CD は、ジョブの実行時に自動的に多くの環境変数を設定します。これらの変数は、パイプラインの実行に関する情報を提供します。
CI_COMMIT_BRANCH
: コミットが作成されたブランチの名前。CI_COMMIT_TAG
: コミットが作成されたタグの名前。CI_PROJECT_ID
: プロジェクトの ID。CI_PIPELINE_ID
: パイプラインの ID。
これらの変数は、ジョブのスクリプト内で使用して、パイプラインの動作をカスタマイズできます。
4.2. CI/CD 変数の設定 (プロジェクト、グループ、インスタンス)
CI/CD 変数は、プロジェクト、グループ、または GitLab インスタンスのレベルで設定できます。プロジェクトレベルの変数は、特定のプロジェクトのパイプラインでのみ使用できます。グループレベルの変数は、グループ内のすべてのプロジェクトで使用できます。インスタンスレベルの変数は、GitLab インスタンス内のすべてのプロジェクトで使用できます。
変数は、GitLab UI の [設定] > [CI/CD] > [変数] で設定できます。
4.3. マスクされた変数
マスクされた変数は、ジョブのログに表示されないように保護された変数です。パスワードや API キーなどの機密情報を格納するために使用されます。マスクされた変数は、GitLab UI で設定するときに [マスク] オプションを有効にすることで設定できます。
5. GitLab Runner の理解
GitLab Runner は、GitLab CI/CD パイプラインのジョブを実行するエージェントです。Runner は、Docker コンテナ、仮想マシン、または物理マシン上で実行できます。
5.1. Runner の種類 (Shared Runner, Specific Runner)
- Shared Runner: GitLab インスタンスで共有されている Runner です。すべてのプロジェクトで使用できます。
- Specific Runner: 特定のプロジェクトまたはグループに割り当てられた Runner です。割り当てられたプロジェクトまたはグループでのみ使用できます。
5.2. タグによるRunnerの選択
Runner にはタグを割り当てることができます。.gitlab-ci.yml
ファイルで tags
キーを使用して、特定のタグを持つ Runner をジョブで使用するように指定できます。
yaml
build_job:
stage: build
tags:
- docker
- linux
script:
- echo "Building the application..."
- ./build.sh
この例では、build_job
は docker
と linux
のタグを持つ Runner を使用します。
5.3. Runner の設定 (Executor タイプ)
Runner の Executor タイプは、ジョブの実行方法を決定します。一般的な Executor タイプには、shell
、docker
、kubernetes
があります。
- shell: ジョブは、Runner が実行されているホストマシン上で直接実行されます。
- docker: ジョブは、指定された Docker イメージを使用してコンテナ内で実行されます。
- kubernetes: ジョブは、Kubernetes クラスタ内で実行されます。
Executor タイプは、Runner の設定ファイルで設定します。
6. 高度な設定
.gitlab-ci.yml
には、パイプラインの動作をカスタマイズするための高度な設定オプションが多数用意されています。
6.1. include を使った設定ファイルの分割
include
キーを使用すると、.gitlab-ci.yml
ファイルを複数のファイルに分割できます。これは、大規模なプロジェクトで設定ファイルを管理しやすくするために便利です。
yaml
include:
- '.gitlab-ci/build.yml'
- '.gitlab-ci/test.yml'
- '.gitlab-ci/deploy.yml'
上記の例では、build.yml
、test.yml
、deploy.yml
ファイルの内容が、.gitlab-ci.yml
ファイルにインクルードされます。
6.2. cache を使ったビルド時間の短縮
cache
キーを使用すると、ジョブの実行結果をキャッシュできます。キャッシュされたファイルは、後続のジョブで再利用され、ビルド時間を短縮できます。
yaml
build_job:
stage: build
script:
- echo "Building the application..."
- ./build.sh
cache:
paths:
- build
この例では、build
ディレクトリの内容がキャッシュされます。後続のジョブは、キャッシュされた build
ディレクトリを使用して、最初からビルドする必要がなくなります。
6.3. services を使った依存サービスの実行
services
キーを使用すると、ジョブの実行に必要な依存サービス (データベースなど) を定義できます。GitLab Runner は、指定されたサービスをコンテナ内で起動し、ジョブからアクセスできるようにします。
yaml
test_job:
stage: test
image: node:16
services:
- postgres:13
variables:
POSTGRES_DB: mydb
POSTGRES_USER: myuser
POSTGRES_PASSWORD: mypassword
script:
- echo "Running tests..."
- npm test
この例では、test_job
は PostgreSQL 13 をサービスとして使用します。ジョブは、POSTGRES_DB
、POSTGRES_USER
、POSTGRES_PASSWORD
環境変数を使用して、PostgreSQL データベースに接続できます。
6.4. trigger を使ったパイプラインの連鎖
trigger
キーを使用すると、現在のパイプラインが完了した後に別のパイプラインをトリガーできます。これは、マイクロサービスアーキテクチャで、サービスのデプロイを連鎖させる場合に便利です。
yaml
deploy_job:
stage: deploy
script:
- echo "Deploying the application..."
- ./deploy.sh
trigger:
project: my-other-project
branch: main
この例では、deploy_job
が完了すると、my-other-project
プロジェクトの main
ブランチのパイプラインがトリガーされます。
6.5. retry を使ったジョブの再実行
retry
キーを使用すると、ジョブが失敗した場合に自動的に再試行するように設定できます。これは、一時的なネットワークの問題などでジョブが失敗する可能性がある場合に便利です。
yaml
test_job:
stage: test
script:
- echo "Running tests..."
- npm test
retry: 2
この例では、test_job
が失敗した場合に最大 2 回まで再試行されます。
6.6. parallel を使ったテストの並列実行
parallel
キーを使用すると、テストを並列実行できます。これは、テストスイートの実行時間を短縮するために便利です。
yaml
test_job:
stage: test
image: node:16
script:
- echo "Running tests..."
- npm test
parallel: 3
この例では、test_job
は 3 つの並列ジョブとして実行されます。各ジョブは、テストスイートの一部を実行します。
7. パイプラインの可視化とモニタリング
GitLab UI では、パイプラインの実行状況を可視化し、モニタリングできます。
7.1. GitLab UI でのパイプラインの確認
GitLab UI の [CI/CD] > [パイプライン] で、パイプラインの実行状況を確認できます。パイプラインの各ジョブの状態 (成功、失敗、実行中など) を確認したり、ジョブのログを表示したりすることができます。
7.2. パイプラインのトリガーとスケジュール
GitLab UI から、手動でパイプラインをトリガーしたり、パイプラインのスケジュールを設定したりできます。スケジュールを設定すると、特定の時間または間隔でパイプラインが自動的にトリガーされます。
7.3. パイプライン履歴の分析
GitLab UI では、パイプラインの履歴を分析できます。過去のパイプラインの実行時間、成功率、失敗率などを確認したり、パフォーマンスの問題を特定したりすることができます。
8. ベストプラクティス
GitLab CI/CD を効果的に使用するためのベストプラクティスをいくつか紹介します。
8.1. .gitlab-ci.yml
のバージョン管理
.gitlab-ci.yml
ファイルは、コードベースの一部としてバージョン管理する必要があります。これにより、過去のビルドを再現したり、パイプラインの変更履歴を追跡したりすることができます。
8.2. シークレット情報の管理
パスワードや API キーなどのシークレット情報は、.gitlab-ci.yml
ファイルに直接記述しないでください。代わりに、GitLab CI/CD の変数機能を使用し、マスクされた変数としてシークレット情報を格納してください。
8.3. テストの自動化
可能な限り、テストを自動化してください。自動化されたテストは、コードの品質を維持し、バグの早期発見を可能にします。
8.4. デプロイ戦略の自動化
デプロイ戦略 (ブルー/グリーンデプロイメント、カナリアデプロイメントなど) を自動化してください。自動化されたデプロイは、デプロイプロセスを迅速かつ安全にします。
9. トラブルシューティング
パイプラインが失敗した場合の原因特定と、よくあるエラーとその解決策について説明します。
9.1. パイプラインが失敗した場合の原因特定
パイプラインが失敗した場合、まずは GitLab UI でジョブのログを確認してください。ログには、エラーメッセージやスタックトレースなど、問題の原因を特定するための情報が含まれている可能性があります。また、CI_DEBUG_TRACE
変数を true
に設定すると、より詳細なデバッグ情報をログに出力できます。
9.2. よくあるエラーとその解決策
- Syntax error in
.gitlab-ci.yml
: YAML ファイルに構文エラーがある場合。YAML リンターを使用して構文を確認してください。 - Runner not found: 指定されたタグを持つ Runner が見つからない場合。Runner が登録されているか、タグが正しく設定されているかを確認してください。
- Dependency installation failed: 依存関係のインストールに失敗した場合。
before_script
で実行されるコマンドが正しいか、必要なリソースが利用可能かを確認してください。 - Test failed: テストが失敗した場合。テストコードにバグがあるか、テスト環境が正しく設定されているかを確認してください。
- Deployment failed: デプロイに失敗した場合。デプロイスクリプトが正しいか、必要な権限があるかを確認してください。
10. まとめと今後の学習
本記事では、GitLab CI/CD の基本から応用までを網羅的に解説しました。.gitlab-ci.yml
ファイルの構造、ジョブの依存関係、環境変数、Runner の設定、高度な設定オプションなどを理解することで、GitLab CI/CD を使いこなし、開発ワークフローを効率化することができます。
今後の学習としては、以下のトピックについて深く掘り下げてみてください。
- GitLab CI/CD の高度な機能: グラフQL API、カスタム executor、Security Scanningなど
- DevOps プラクティス: Infrastructure as Code (IaC)、構成管理、モニタリングなど
- クラウドネイティブな開発: Kubernetes、Docker、マイクロサービスなど
GitLab CI/CD は、継続的に進化しているツールです。GitLab の公式ドキュメントやコミュニティフォーラムなどを活用して、常に最新の情報をキャッチアップし、より効果的な CI/CD パイプラインを構築していきましょう。