Quarkus版Keycloakでは、起動前にビルドで焼き込む設定と、起動時に渡す設定が明確に分かれています。この分離を理解しないと、起動が遅い・機密が漏れる・本番でビルドが走るといった落とし穴にはまります。build-time optionとruntime optionの境界、--optimized起動、コンテナでのビルド戦略を実務目線で整理します。

Quarkus版のKeycloak(現行ディストリビューション)を触りはじめて最初に戸惑うのが、「なぜこの設定は起動時に効かないのか」という点です。WildFly版の感覚のまま start に全部のオプションを渡すと、警告が出たり無視されたりします。原因は、Quarkus版が設定をbuild-time option(ビルド時)runtime option(起動時)の2階層に分けているからです。本稿ではこの分離を、現場でハマりやすいポイントとともに整理します。なお具体的なオプションの build/runtime 区分はバージョンで変わり得るため、新しめのバージョンを基準にしつつ最終的には公式ドキュメントでの確認を前提としてください。

01なぜ2階層に分かれるのか

Quarkus版は、起動時のオーバーヘッドを削るために「クローズドワールド仮定」で最適化します。インストールされているプロバイダやフィーチャーが起動のたびに変わらない、という前提を置くことで、プロバイダレジストリの再構築やファクトリ初期化を毎回やらずに済ませ、設定ファイルも事前パースしておく。これが kc.sh build の役割です。公式ドキュメントでも、Keycloakは「build コマンドで使えるbuild option」と「起動時に使えるconfiguration option」を区別すると明記されています(Configuring Keycloak)。

つまり、どのDBベンダーを使うか・どのフィーチャーを有効にするか、といった「サーバの骨格を決める設定」はビルド時に固め、URLやパスワードやホスト名のように「環境ごとに変わる設定」は起動時に渡す、という設計思想です。

02build時に焼き込む代表項目

ビルド時に確定させる代表的なオプションは次のとおりです。いずれも「有効/無効」や「どの実装を使うか」というサーバ構成そのものに関わる項目です。

現場のコツ:「起動時に --metrics-enabled=true を渡したのにメトリクスが出ない」という問い合わせは定番です。metrics-enabledhealth-enabled はbuild-time扱いなので、ビルド時に焼き込んでいなければ起動時指定は効きません。監視要件は設計フェーズで確定させ、イメージに含めておくのが鉄則です。

03runtime時に渡す代表項目

一方、環境依存で毎回変わる値は起動時に渡します。むしろビルド時に入れてはいけないものが含まれる点が重要です。

ここで見落としてはいけないのが機密の扱いです。公式ドキュメントは「すべてのbuild optionはプレーンテキストで永続化される。機密データをbuild optionとして保存してはならない」と明確に警告しています(Configuring Keycloak)。db-password をビルド時に渡すと、最適化されたイメージ内に平文で焼き込まれてしまいます。パスワードやシークレットは必ず起動時に、環境変数やシークレットマウント経由で供給してください。

設定の2階層と流れ build-time(焼き込む) db(ベンダー) / features health-enabled / metrics-enabled cache / transaction → kc.sh build で永続化 runtime(起動時に渡す) db-url / db-username db-password(機密) hostname / TLS / proxy → start --optimized で供給 最適化済みKeycloakプロセス 起動時にbuildを走らせず高速起動
図:build-time optionはイメージに永続化、runtime optionは起動時に供給。機密は必ずruntime側で。

04--optimized起動でビルドをスキップする

Quarkus版の start は、明示的にビルド済みでない場合、起動時に自動でビルド相当の処理を走らせます。これが本番で数十秒の起動遅延やコンテナのスケールアウト遅れの原因になります。事前に kc.sh build を済ませているなら、起動時に --optimized を付けます。

--optimized は「すでに最適化済みのイメージを使う」とKeycloakに伝えるフラグで、起動時のビルドチェック・ビルド実行を回避して起動時間を短縮します(Configuring Keycloak)。

現場のコツ:--optimized を付けたら、起動コマンドからはbuild-timeオプション(--db=--features= など)を外し、runtimeオプションだけを残すのが正しい使い方です。両方を混在させると設定の出どころが二重化し、レビュー時に「どちらが効いているのか」が追いにくくなります。ビルド時と起動時でオプションの棚卸しを分けておくと、変更管理・統制の観点でもクリーンになります。

05コンテナでのビルド戦略(マルチステージ)

本番はほぼコンテナ運用になるため、ビルドをどこで走らせるかが設計上の分かれ目です。推奨は、コンテナのイメージビルド時に kc.sh build を走らせるマルチステージ構成です。公式ドキュメントでも、ビルドステップをコンテナビルド時に実行することで「以降の毎回の起動フェーズで時間を節約できる」としています(Running Keycloak in a container)。

典型的な骨子は次の形です(バージョンで細部は変わるため公式のContainerfile例を基準に)。

ここで重要なのが順序です。カスタムプロバイダ(SPIのJAR)を /opt/keycloak/providers に配置する場合、そのCOPYはbuildコマンドの前に置かなければなりません。公式も「このステップはbuildコマンドをRUNする行より前に置く必要がある」と明記しています(Running Keycloak in a container)。JARを後から入れてもクローズドワールドのレジストリには反映されず、プロバイダが認識されません。

マルチステージbuildの順序 builderステージ 1. providers/ にSPIのJAR配置 2. ENV で db/features/health/metrics 3. RUN kc.sh build JAR配置はbuildより前が必須 最終イメージ COPY --from=builder 成果物 start --optimized で起動 機密はここで環境変数供給 起動は数秒
図:JAR配置→build→最終イメージ。起動時はruntimeオプションと機密だけを渡す。

06設計・統制の観点で効いてくる分離

この分離は単なる起動高速化テクニックではなく、変更管理と監査の観点でも効いてきます。build-time optionはイメージに紐づく=バージョン管理・ビルドパイプラインの対象、runtime optionはデプロイ環境に紐づく=シークレットマネージャや構成管理の対象、と責務がきれいに分かれます。

マルチアカウント・マルチ環境で認証基盤を横断展開する場合、この「イメージは共通・環境設定は外出し」という原則がガバナンスの土台になります。統制の考え方はマルチアカウント統制とも通じます。WildFly版からの移行を検討中なら、この設定モデルの違いは最初に押さえるべきポイントです。

現場のコツ:本番設定の詰めでは、--server-async-bootstrap やヘルスチェックパス(/health/ready)の扱いも合わせて確認しておくと、K8sのreadinessプローブ設計まで一気通貫で決められます(Configuring Keycloak for production)。

07ハマりどころチェックリスト

EMWではKeycloakによるエンタープライズ認証基盤の実構築で、この設定分離を前提にしたコンテナビルドパイプラインとデプロイ設計を組んできました。具体的な構成は導入事例もあわせてご覧ください。

まとめ

Quarkus版Keycloakのbuild/runtime分離は、「サーバの骨格(db・features・health・metrics・cache)はビルドで固め、環境依存値と機密は起動時に渡す」という一本の原則に集約されます。kc.sh build でイメージを最適化し、マルチステージでビルドを前倒しし、--optimized で起動する。この型を守るだけで、起動速度・セキュリティ・統制のすべてが同時に整います。バージョンごとの区分は公式ドキュメントで最終確認する、という運用姿勢だけは崩さないでください。

参考(一次情報)

Keycloakの本番基盤設計やコンテナ最適化でお困りの際は、実構築の経験を踏まえてお問い合わせください。

相談する
← ブログ一覧へ戻る