Status | Authors | Coach | DRIs | Owning Stage | Created |
---|---|---|---|---|---|
proposed | - |
このドキュメントは作業中のものであり、セルズの設計のごく初期の状態を表しています。重要な点は文書化されていませんが、将来的には追加される予定です。これはCellsの可能性のあるアーキテクチャの一つであり、どのアプローチを実装するか決める前に、代替案と比較検討するつもりです。この文書化は、このアプローチを選ばなかった理由を文書化できるよう、これを実装しないと決めた場合でも残しておきます。
セルズCIランナー
GitLabはGitLab Runnerを通してCIジョブを実行します。CIパイプラインの一部として作成された全てのCIジョブはプロジェクトのコンテキストで実行されます。これはGitLab Runnerをどのように管理するかという課題を提起しています。
1.定義
ランナーには3つのタイプがあります:
- インスタンス全体:特定のタグ(選択基準)でグローバルに登録されるランナー
- グループランナー:指定されたトップレベルのグループまたはそのグループ内のプロジェクトのジョブを実行するRunner
- プロジェクトランナー:1つのプロジェクトまたは多数のプロジェクトからジョブを実行するランナー:ランナーによっては、異なるトップレベルグループのプロジェクトからプロジェクトが割り当てられることがあります。
これは、ci_runners
すべてのタイプのRunnerを記述するテーブル ci_runners
である既存のデータ構造と並んで、Cells環境でci_runners
どのように ci_runners
管理されるべきかというci_runners
課題を提起して ci_runners
います。
2.データフロー
GitLab Runnerは、グローバルにスコープされたエンドポイントのセットを使用します:
- 登録トークンによる新しい Runner の登録
https://gitlab.com/api/v4/runners
(削除対象) (registration token
) - ユーザーのコンテキストで新しいランナーを作成
https://gitlab.com/api/v4/user/runners
(runner token
) - 認証された
https://gitlab.com/api/v4/jobs/request
エンドポイントを介してジョブをリクエスト (runner token
) -
https://gitlab.com/api/v4/jobs/:job_id
(build token
) 経由でジョブステータスをアップロードします。 - トレースのアップロード
https://gitlab.com/api/v4/jobs/:job_id/trace
(build token
) 経由 - アーティファクトのダウンロードとアップロードは
https://gitlab.com/api/v4/jobs/:job_id/artifacts
(build token
) から。
現在、3種類の認証トークンが使用されています:
- ランナー登録トークン(削除対象)
- 特定の設定(
tags
,locked
など)でシステムに登録されたランナーを表すランナートークン。 - ビルドトークンは、特定のジョブの更新、アーティファクトのアップロード、依存するアーティファクトのダウンロード、コンテナレジストリイメージのダウンロードとアップロードに限定されたアクセスを与えるエフェメラルトークンを表します。
これらの各エンドポイントは、ヘッダ (/trace
の場合はJOB-TOKEN
) またはボディパラメータ (token
その他のすべてのエンドポイント ) を介して認証トークンを受け取ります。
CIパイプラインは特定のCellのコンテキストで作成されるため、ビルドのピックはその特定のCellで処理される必要があります。このため、ソリューションに依存するビルドピッキングは、以下のいずれかである必要があります:
- 最初に正しいセルにルーティングされます。
- 二段階:グローバル・プールからビルドを要求し、セル固有の URL を使って特定のセルにビルドを要求。
3.提案
3.1.認証トークン
CIランナーのパスがルーティング可能でなくても、これら2つの可能な解決策でルーティング可能にすることができます:
-
https://gitlab.com/api/v4/jobs/request
は、発券メカニズム(X-GitLab-Last-Update
ヘッダーに基づく)と長いポーリングメカニズムを使います。Runnerが最初に起動するとき、RunnerはGitLabにリクエストを送り、GitLabはRunnerが選択するビルドを返します。この値はGitLabによって完全に制御されます。これにより、GitLabはJWTやその他の手段を使い、Routerが簡単に解読できるcell
識別子をエンコードすることができます。 - 通信の大部分(量的な意味で)は
build token
, を使っており、GitLabがRunnerが後で特定のジョブに使うトークンの唯一のオーナーであるため、変更するのが最も簡単なターゲットとなってbuild token
います。トーbuild token
クンを保存するbuild token
のではなく、スコープを定義したJWT
トークンを使うというbuild token
議論が以前build token
ありました。そのようなトークンは、ルータがすべてのリクエストをルーティングするcell
をエンコードすることができます。
3.2.リクエストボディ
- 最もよく使われるエンドポイントは、リクエストボディで認証トークンを渡します。HTTP ヘッダを使うことで、リクエストをプロキシすることなく ルータがこの情報にアクセスできるようになります。
3.3.インスタンスワイドはセルローカル
すべてのランナーが常に登録され、与えられたセルにローカルであるようなデザインを選ぶことができます:
- 各セルはインスタンスワイドランナーのセットを持ち、それぞれのペースで更新されます。
- プロジェクト・ランナーは、同じ組織のプロジェクトにのみリンクすることができ、強力な分離を実現します。
- このモデルでは、
ci_runners
テーブルはセルの内部です。 - このモデルでは、上記のエンドポイントを何らかの方法でセルにスコープするか、 ルーティング可能にする必要があります。プレフィックスをつけたり、Cell のパラメータを追加したり、Runner トークンをデコードして Cell にマッチさせるより強固な方法を提供したり。
- もしルーティング可能なトークンが使われるなら、データベースに保存された暗号化されたランダムなトークンから、むしろ JWT トークンを使う方が好ましいでしょう。
- 登録されたランナーを表示する管理エリアはセルにスコープされなければなりません。
このモデルは強力な分離保証を提供するので望ましいかもしれません。このモデルでは各セルが個別に管理されるため、メンテナンスのオーバーヘッドが大幅に増加します。このモデルでは、プロジェクトがセル間で一貫したランナーエクスペリエンスを持つように、ランナータグ機能を調整する必要があるかもしれません。
3.4.インスタンスワイドクラスターワイド
すべてのRunnerがCell-localであるという提案とは逆に、Runnerはグローバルである、あるいはインスタンスワイドのRunnerだけがグローバルであると考えることができます。
しかし、これにはシステムの大幅な見直しが必要で、以下の点を変更しなければなりません:
-
ci_runners
テーブルをci_instance_runners
,… に分解しなければならないでしょう。 - すべてのインターフェイスは、正しいテーブルを使用するために採用されなければならないでしょう。
- ビルドのキューイングは、各セルがすべての保留中のビルドと実行中のビルドを知ることができるように、2段階に作り直さなければなりません。
- おそらく、
ci_pending_builds
とci_running_builds
をcluster-wide
テーブルにする必要があり、CI キューイングに関連するシステムでホットスポットが発生する可能性が高まります。
このモデルはエンジニアリングの観点からは実装が複雑です。セル間で共有されるデータもあります。システム内にホットスポットやスケーラビリティのイシューが発生し、例えば不正使用時に他の Cell の Organizations の経験に影響を与える可能性があります。
3.5.GitLab CIデーモン
もう一つの潜在的な解決策は、ビルドのキューイングを担当する専用のサービスを持ち、そのデータベースを所有し、シャード化またはセル化されたサービスのモデルで動作させることです。CI/CD Daemonについては以前にも議論がありました。
サービスがシャーデッド化されている場合:
- モデルによりますが、Runnerがクラスター全体かCell-localの場合、このサービスはすべてのCellからデータをフェッチする必要があります。
- もしシャードサービスが使われるなら、
ci_pending_builds/ci_running_builds
を含むデータベースをサービスと共有するモデルを適応させることができます。 - もしシャード化されたサービスを使うなら、各CellがRunnerが選ぶべきCI/CD Daemonのビルドにプッシュするモデルを考えることができます。
- シャード化されたサービスは、どのCellが指定されたビルドの処理を担当しているかを認識し、処理要求を指定されたCellにルーティングすることができます。
サービスがCell化されている場合:
- ルーティング可能なエンドポイントへの期待はすべて有効です。
一般的に、CI Daemonの使用は前述の問題に対して大きな助けにはなりません。しかし、これはより効率的な処理とデカップリングモデルに関連するいくつかのプラス面を提供します:プッシュモデル、そしてGitLabランナー(gRPCやWebsocketなど)とのステートフルな通信を提供する方法を開きます。
4.評価
すべての選択肢を考慮すると、最も有望な解決策は次のように思われます:
- インスタンス・ワイドとセル・ローカルの使い分け
- ルーティング可能なアイデンティティを持つようにエンドポイントを絞り込む(特定のパス経由か、より良いトークン経由のいずれか)
もう1つの潜在的な利点は、ci_builds.token
を廃止し、むしろ CI Runner によって許可されるより広範なスコープをより良く簡単にエンコードできるJWT token
を使用することです。