はじめに
大規模な CI/CD ワークフローにおいて、共有される GitLab Runner のリソース制約によりビルドキューが滞留し、開発効率の低下を招くケースがあります。この課題に対処するため、Kubernetes 環境上で独自のスケーラブルな Runner インフラストラクチャを構築し、パイプラインの実行スピードを向上させる手法を解説します。
前提条件
- Kubernetes バージョン 1.21 以降
- Cert-Manager v1.7.1 以上のインストール済み
- kubectl CLI および Helm CLI の準備
Operator ライフサイクルマネージャー (OLM) のセットアップ
GitLab Runner の管理を自動化するために、まず Operator をクラスターに導入する際の基盤となる OLM をデプロイします。
OLM インストール
公式リリーススクリプトを利用し、OLM コンポーネントを `olm` ネームスペースに展開します。
curl -sL https://github.com/operator-framework/operator-lifecycle-manager/releases/download/v0.32.0/install.sh | bash -s v0.32.0
正常に展開されたことを確認します。
kubectl get pods -n olm
以下のコンポーネントが Running ステートになっていることを確認してください。
- catalog-operator
- olm-operator
- packageserver
GitLab Runner Operator の導入
OLM 経由で対応するオペレーターをインストールし、カスタムリソース定義 (CRD) が登録されるのを待ちます。
kubectl apply -f https://operatorhub.io/install/gitlab-runner-operator.yaml
インストール状況の確認:
kubectl get csv -n operators
Phase が Succeeded となり、マネージャーポッドが起動しているかを確認します。
ビルドキャッシュ用のストレージ構成 (MinIO)
CI/CD パイプラインの高速化のため、S3 互換ストレージである MinIO を構築し、依存パッケージやビルド結果のキャッシュを格納するように設定します。
ローカルパスプロビジョニングの確立
クラスター内のノード上の物理ディレクトリを動的ボリュームとして使用するための StorageClass を作成します。
---
apiVersion: v1
kind: Namespace
metadata:
name: local-path-storage
# RBAC 関連の Role, ClusterRole, Binding は省略(適切な権限付与を必須)
---
kind: StorageClass
apiVersion: storage.k8s.io/v1
metadata:
name: local-path
provisioner: rancher.io/local-path
volumeBindingMode: WaitForFirstConsumer
reclaimPolicy: Delete
設定適用後、有効なストレージクラスとしてリストされます。
kubectl get sc
MinIO クラスターのデプロイ
PVC でデータを永続化するよう Helm チャートを設定します。
# values.yaml の一部抜粋
auth:
rootUser: admin
rootPassword: "securepass123"
defaultBuckets: "gitlab-cache"
persistence:
enabled: true
existingClaim: "minio-data-pvc"
storageClass: "local-path"
image:
repository: bitnami/minio
tag: 2023.11.1-debian-11-r0
事前に必要な PVC を作成し、その後ヘルムリリースを実行します。
kubectl create namespace cicd-system
helm repo add bitnami https://charts.bitnami.com/bitnami
helm install minio bitnami/minio -f minio-values.yaml -n cicd-system
GitLab Runner のカスタマイズと登録
オペレーターによる Runner 管理のために、認証情報と動作設定を定義します。
設定用 ConfigMap の作成
Git LFS 関連のエラー回避や、SSH キーの設定を行うために、独自の config.toml を注入します。
apiVersion: v1
kind: ConfigMap
metadata:
name: runner-extra-config
namespace: cicd-system
data:
config.toml: |-
[[runners]]
environment = ["GIT_LFS_SKIP_SMUDGE=1"]
pre_clone_script = """
echo "Initializing credentials"
# Git LFS 設定
git config --global lfs.url "https://git-lfs.example.com"
echo "Credential helper store"
git config --global credential.helper store
# SSH ホスト設定
mkdir -p $HOME/.ssh
chmod 700 $HOME/.ssh
echo -e "Host gitlab.example\n\tStrictHostKeyChecking no\n" >> $HOME/.ssh/config
"""
[runners.kubernetes]
privileged = true
pull_policy = "if-not-present"
[runners.kubernetes.node_selector]
"node-type" = "worker"
認証情報の管理
MinIO の認証キーと、私有レジストリの認証情報をシークレットとして管理します。
# MinIO Credential Secret
apiVersion: v1
kind: Secret
metadata:
name: s3-cache-auth
namespace: cicd-system
type: Opaque
stringData:
accesskey: "minioadmin"
secretkey: "miniopassword"
# Docker Registry Secret
apiVersion: v1
kind: Secret
metadata:
name: regcred-inner
namespace: cicd-system
type: kubernetes.io/dockerconfigjson
data:
.dockerconfigjson: {BASE64_ENCODED_JSON}
Runner クラスターの定義
最終的に GitLab に接続する Runner のインスタンスを作成します。注:安定性の観点から、特定のオペレーターバージョンを使用することを推奨します。
---
apiVersion: apps.gitlab.com/v1beta2
kind: Runner
metadata:
name: auto-scaling-runner
namespace: cicd-system
spec:
logLevel: info
runnerImage: "custom-reg/gitlab-runner:v17.4.0"
gitlabUrl: "https://gitlab.example.com/"
buildImage: alpine
concurrent: 10
tags: "k8s,docker"
tokenRef:
secretName: gitlab-reg-token
cacheType: s3
cacheShared: true
s3:
server: "minio.cicd-system.svc.cluster.local:9000"
credentialsSecret: s3-cache-auth
bucket: "build-artifacts"
insecure: true
config: runner-extra-config
適用後、ステータスを確認します。
kubectl get pods -n cicd-system
Runner 操作用のポッドが常時稼働状態であれば、GitLab UI 上で Runner タブから接続状況を確認可能です。