このページでは、Google Kubernetes Engine(GKE)クラスタで Kubernetes API サーバーに接続するときに使用できる認証方法について説明します。
Google Cloud APIs に対する Kubernetes ワークロードの認証については、GKE 用 Workload Identity 連携をご覧ください。
概要
Kubernetes API サーバーに対する認証方法は複数あります。GKE では、OAuth 認証がクラスタ認証に推奨されており、自動的に構成されます。
始める前に
作業を始める前に、次のことを確認してください。
- Google Kubernetes Engine API を有効にする。 Google Kubernetes Engine API の有効化
- このタスクに Google Cloud CLI を使用する場合は、gcloud CLI をインストールして初期化する。すでに gcloud CLI をインストールしている場合は、
gcloud components update
を実行して最新のバージョンを取得する。
ユーザーの認証
GKE は、Google Cloud CLI を使用してエンドユーザー認証を管理します。gcloud CLI は、Google Cloud に対するユーザー認証、Kubernetes 構成の設定、クラスタの OAuth アクセス トークンの取得、アクセス トークンの更新を行います。
すべての GKE クラスタは、Google Cloud ユーザー/サービス アカウント ID を受け入れるように設定されています。受け入れる際には、kubectl
から提供された認証情報を検証し、ユーザー/サービス アカウント ID に関連付けられたメールアドレスを取得します。したがって、認証に成功するには、これらのアカウントの認証情報に userinfo.email
OAuth スコープが含まれている必要があります。
gcloud
を使用して新しいまたは既存のクラスタ用の環境の kubeconfig
をセットアップするとき、gcloud
は、gcloud
自体で使用されるものと同じ認証情報を kubectl
に渡します。たとえば gcloud auth login
を使用する場合、userinfo.email
スコープを含め、そのユーザー個人の認証情報が kubectl
に渡されます。これにより、GKE クラスタは kubectl
クライアントを認証できます。
または、Compute Engine インスタンス上で動作しながら、Google Cloud サービス アカウントの認証情報を使用するように kubectl
を設定する方法もあります。ただし、デフォルトでは、Compute Engine インスタンスによって作成される認証情報に userinfo.email
スコープが含まれません。したがって、Compute Engine インスタンスの作成時に --scopes
フラグを使用するなどして、このスコープを明示的に追加する必要があります。
クラスタ内でアクションを承認するには、Identity and Access Management(IAM)または Kubernetes のロールベースのアクセス制御(RBAC)を使用できます。
OAuth を使用した認証
OAuth メソッドを使用してクラスタに対する認証を行うには、次の手順に従います。
認証情報を使用して gcloud CLI にログインします。そうすることでウェブブラウザが開き、Google Cloud への認証プロセスが完了します。
gcloud auth login
特定のクラスタの Kubernetes 認証情報を取得します。
gcloud container clusters get-credentials CLUSTER_NAME \ --zone=COMPUTE_ZONE
認証されていることを確認します。
kubectl cluster-info
ユーザーまたは Google Cloud サービス アカウントが認証された後、GKE クラスタに対するアクションの実行をアカウントに許可する必要があります。認可の構成方法の詳細については、ロールベースのアクセス制御をご覧ください。
アプリケーションの認証
CI/CD パイプラインのスクリプトで認証するなど、ユーザーの操作なしで Pod 内のアプリケーションから API サーバーに対して認証することもできます。これを実現する方法は、アプリケーションが実行されている環境によって異なります。
同じクラスタ内のアプリケーション
アプリケーションが同じ GKE クラスタで実行されている場合は、Kubernetes サービス アカウントを使用して認証します。
Kubernetes サービス アカウントを作成し、Pod に接続します。Pod に Kubernetes サービス アカウントがすでにある場合、または Namespace のデフォルトのサービス アカウントを使用する場合は、このステップをスキップします。
Kubernetes RBAC を使用して、アプリケーションに必要な権限を Kubernetes サービス アカウントに付与します。
次の例では、名前空間が
prod
であるリソースに対して、サービスアカウント名がcicd
で名前空間がcicd-ns
へのview
権限を付与します。kubectl create rolebinding cicd-secret-viewer \ --namespace=prod \ --clusterrole=view \ --serviceaccount=cicd-ns:cicd
実行時に、アプリケーションが Kubernetes API リクエストを送信すると、API サーバーはサービス アカウントの認証情報を認証します。
Google Cloud 内のアプリケーション
アプリケーションが Google Cloud の内部で実行されて、かつ、ターゲット クラスタ(Compute Engine VM や別の GKE クラスタなど)の外部で実行されている場合は、その環境で利用できる IAM サービス アカウントの認証情報を使用して API サーバーに対する認証を行う必要があります。
環境に IAM サービス アカウントを割り当てます。アプリケーションが Compute Engine VM 内で実行されている場合は、インスタンスに IAM サービス アカウントを割り当てます。アプリケーションが別の GKE クラスタで実行されている場合は、GKE 用 Workload Identity 連携を使用して、IAM サービス アカウントとして実行されるように Pod を構成します。
以下の例では、IAM サービス アカウントとして
ci-cd-pipeline@PROJECT_ID.iam.gserviceaccount.com
を使用します。IAM サービス アカウントにクラスタへのアクセス権を付与します。
次の例では、クラスタ内の Kubernetes API オブジェクトへのアクセス権を付与する
roles/container.developer
IAM ロールを付与します。gcloud projects add-iam-policy-binding PROJECT_ID \ --member=serviceAccount:ci-cd-pipeline@PROJECT_ID.iam.gserviceaccount.com \ --role=roles/container.developer
また、RBAC を使用して IAM サービス アカウントにクラスタへのアクセス権を付与することもできます。同じクラスタ内のアプリケーションから
kubectl create rolebinding
コマンドを実行し、--service-account
フラグの代わりに--user=ci-cd-pipeline@PROJECT_ID.iam.gserviceaccount.com
を使用します。クラスタの認証情報を取得します。
gcloud container clusters get-credentials CLUSTER_NAME \ --zone=COMPUTE_ZONE
アプリケーションは、環境に設定された IAM サービス アカウントを使用して自動的に認証されます。
他の環境のアプリケーション
アプリケーションが Google Cloud 外部の環境から認証されている場合、マネージド IAM サービス アカウントの認証情報にはアクセスできません。クラスタの認証情報を取得するには、IAM サービス アカウントの作成、そのキーのダウンロードを行い、実行時にサービスからキーを使用して、gcloud CLI でクラスタの認証情報を取得します。
アプリケーションの IAM サービス アカウントを作成します。IAM サービス アカウントをすでに保有している場合は、このステップをスキップします。
次のコマンドは、
ci-cd-pipeline
という名前の IAM サービス アカウントを作成します。gcloud iam service-accounts create ci-cd-pipeline
IAM サービス アカウントにクラスタへのアクセス権を付与します。
次のコマンドは、
roles/container.developer
IAM ロールをci-cd-pipeline@PROJECT_ID.iam.gserviceaccount.com
IAM サービス アカウントに付与します。gcloud projects add-iam-policy-binding PROJECT_ID \ --member=serviceAccount:ci-cd-pipeline@PROJECT_ID.iam.gserviceaccount.com \ --role=roles/container.developer
RBAC を使用して、IAM サービス アカウントにクラスタへのアクセス権を付与することもできます。同じクラスタ内のアプリケーションから
kubectl create rolebinding
コマンドを実行し、--service-account
フラグの代わりに--user=ci-cd-pipeline@PROJECT_ID.iam.gserviceaccount.com
を使用します。IAM サービス アカウントのキーを作成してダウンロードします。 実行時にアプリケーションで使用できるようにします。
gcloud iam service-accounts keys create gsa-key.json \ --iam-account=ci-cd-pipeline@PROJECT_ID.iam.gserviceaccount.com
アプリケーションを実行している環境で、IAM サービス アカウント キーを使用して gcloud CLI に対する認証を行います。
gcloud auth activate-service-account ci-cd-pipeline@PROJECT_ID.iam.gserviceaccount.com \ --key-file=gsa-key.json
gcloud CLI を使用してクラスタの認証情報を取得します。
gcloud config set project PROJECT_ID gcloud container clusters get-credentials CLUSTER_NAME \ --zone=COMPUTE_ZONE
gcloud を使用しない環境
gcloud CLI を使用してクラスタ認証情報を取得することをおすすめします。この方法は、コントロール プレーンの IP ローテーションや認証情報のローテーションなどのクラスタ イベントの影響を受けにくいためです。ただし、環境に gcloud CLI をインストールできない場合でも、静的な kubeconfig ファイルを作成してクラスタに対する認証を行うことができます。
アプリケーションの IAM サービス アカウントを作成します。IAM サービス アカウントをすでに保有している場合は、このステップをスキップします。
次のコマンドは、
ci-cd-pipeline
という名前の IAM サービス アカウントを作成します。gcloud iam service-accounts create ci-cd-pipeline
IAM サービス アカウントにクラスタへのアクセス権を付与します。
次のコマンドは、
roles/container.developer
IAM ロールをci-cd-pipeline@PROJECT_ID.iam.gserviceaccount.com
IAM サービス アカウントに付与します。gcloud projects add-iam-policy-binding PROJECT_ID \ --member=serviceAccount:ci-cd-pipeline@PROJECT_ID.iam.gserviceaccount.com \ --role=roles/container.developer
カスタム IAM ロールを作成して、付与する権限を詳細に制御することもできます。
IAM サービス アカウントのキーを作成してダウンロードします。
次の例では、鍵ファイルの名前は
gsa-key.json
になります。gcloud iam service-accounts keys create gsa-key.json \ --iam-account=ci-cd-pipeline@PROJECT_ID.iam.gserviceaccount.com
クラスタの
endpoint
とclusterCaCertificate
の値を取得します。gcloud container clusters describe CLUSTER_NAME \ --zone=COMPUTE_ZONE \ --format="value(endpoint)" gcloud container clusters describe CLUSTER_NAME \ --zone=COMPUTE_ZONE \ --format="value(masterAuth.clusterCaCertificate)"
以下を含む
kubeconfig.yaml
ファイルを作成します。apiVersion: v1 kind: Config clusters: - name: CLUSTER_NAME cluster: server: https://endpoint certificate-authority-data: masterAuth.clusterCaCertificate users: - name: ci-cd-pipeline-gsa user: exec: apiVersion: client.authentication.k8s.io/v1beta1 args: - --use_application_default_credentials command: gke-gcloud-auth-plugin installHint: Install gke-gcloud-auth-plugin for kubectl by following https://cloud.google.com/kubernetes-engine/docs/how-to/cluster-access-for-kubectl#install_plugin provideClusterInfo: true contexts: - context: cluster: CLUSTER_NAME user: ci-cd-pipeline-gsa name: CLUSTER_NAME-ci-cd current-context: CLUSTER_NAME-ci-cd
以下を置き換えます。
CLUSTER_NAME
: クラスタの名前。endpoint
: 前のステップで取得したendpoint
の値。masterAuth.clusterCaCertificate
: 前のステップで取得したclusterCaCertificate
の値(base64 でエンコードされた証明書をデコードする必要はありません)。
環境内のアプリケーションと合わせて
kubeconfig.yaml
とgsa-key.json
をデプロイします。アプリケーションを実行する環境で、次の環境変数を設定します。export KUBECONFIG=path/to/kubeconfig.yaml export GOOGLE_APPLICATION_CREDENTIALS=path/to/gsa-key.json
これで、アプリケーションが Kubernetes API にリクエストを送信できるようになりました。アプリケーションは IAM サービス アカウントとして認証されます。
従来の認証方法
GKE と OAuth を統合する前は、事前にプロビジョニングされた X.509 証明書または静的パスワードが唯一の利用可能な認証方法でしたが、現在これらの方法は推奨されておらず、無効にする必要があります。これらの方法は、クラスタの侵害に対する攻撃の範囲が広く、GKE バージョン 1.12 以降で実行しているクラスタでは、デフォルトで無効になっています。以前の認証方法を使用している場合は、無効にすることをおすすめします。
有効にすると、container.clusters.getCredentials
権限を持つユーザーはクライアント証明書と静的パスワードを取得できます。roles/container.admin
、roles/owner
、roles/editor
の各ロールにこの権限があるため、これらのロールは慎重に使用してください。詳細については、GKE での IAM のロールをご覧ください。
静的パスワードによる認証の無効化
静的パスワードとは、API サーバーが検証するユーザー名とパスワードの組み合わせです。GKE では、この認証方法は基本認証と呼ばれます。
既存のクラスタを更新して静的パスワードを削除するには、次のコマンドを実行します。
gcloud container clusters update CLUSTER_NAME --no-enable-basic-auth
クライアント証明書による認証の無効化
証明書認証では、クライアントが提示する証明書を、指定された認証局で API サーバーが検証します。GKE では、クラスタルート認証局(CA)がクライアント証明書に署名します。
クライアント証明書による認証は、Kubernetes API サーバーに対する認可に影響します。従来の属性ベースのアクセス制御(ABAC)による認可がクラスタで有効になっている場合、クライアント証明書はデフォルトで認証され、API サーバーで任意のアクションを実行できます。一方、ロールベースのアクセス制御(RBAC)を有効にしている場合は、クライアント証明書に Kubernetes リソースに対する特定の権限を付与する必要があります。
クライアント証明書を生成せずにクラスタを作成するには、--no-issue-client-certificate
フラグを使用します。
gcloud container clusters create CLUSTER_NAME \
--no-issue-client-certificate
現在、既存のクラスタからクライアント証明書を削除する方法はありません。既存のクラスタでクライアント証明書による認証を停止するには、クラスタで RBAC が有効になっていることと、クライアント証明書がクラスタで認可されていないことを確認してください。
次のステップ
- Google Cloud 認証について学習する。
- GKE でのアクセス制御について学習する。
- Google サービス アカウントについて学習する。
- GKE 用 Workload Identity 連携について学習する。
- クラスタのセキュリティの強化について学習する。