7
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

【Workload Identity】 GKE で Google Service Account を利用する正しいやり方

Posted at

TL;DR

  • GKE から Google Service Account (GSA) を利用するのに GSA のアカウントキーを発行して Secret を作成してはいけない

  • Kubernetes Service Account (KSA) と GSA を紐づける Workload Identity を利用して認証を行うべき

Why?

以下は公式ドキュメントからの抜粋。
アカウントキーを発行してGCPのプロダクトを利用するのには、

  1. キーの漏洩リスク
  2. キーの更新(デフォルトの有効期限は10年)

という Secret を手動で管理、保護する手間がありました。

注: Workload Identity は、GKE 内から Google Cloud サービスにアクセスする場合におすすめの方法です。Workload Identity を使用すると、Kubernetes サービス アカウントを Google サービス アカウントとして機能するよう構成でき、Secret を手動で管理、保護する必要がなくなります。

Workload Identity とは

一言で言うと、「kubernetes の Service Account GCP の Serivce Account を紐づけ(Binding)られるようにする仕組み」です。アカウントキーでの認証方法とWorkload Identity での認証方法を図で比較します。

アカウントキーでの認証方法

Workload Identity.png

Workload Identity での認証方法

Workload Identity (1).png

利用手順

大別すると以下のようになります。
詳細は公式ドキュメントを参照してください。

  1. クラスタで Workload Identity を有効化
  2. GSA を作成し、KSA との IAM policy Binding を作成。
  3. KSA を作成し、GSA へのアノテーションを追加。
  4. Pod で KSA を指定

1. クラスタで Workload Identity を有効化

  • 新しいクラスタで Workload Identity を有効にする
$ gcloud container clusters create cluster-name \
  --release-channel regular \
  --workload-pool=project-id.svc.id.goog
  • 既存のクラスタで Workload Identity を有効にする
$ gcloud container clusters update cluster-name \
  --workload-pool=project-id.svc.id.goog

2. GSA を作成し、KSA との IAM policy Binding を作成

$ gcloud iam service-accounts create gsa-name
$ gcloud iam service-accounts add-iam-policy-binding \
  --role roles/iam.workloadIdentityUser \
  --member "serviceAccount:project-id.svc.id.goog[k8s-namespace/ksa-name]" \
  gsa-name@project-id.iam.gserviceaccount.com
Terraform
main.tf

data "google_project" "project" {
}

locals {
  annotations = formatlist(
    "serviceAccount:${data.google_project.project.project_id}.svc.id.goog[%s]",
    var.k8s_service_accounts,
  )
}

data "google_service_account" "serviceaccount" {
  account_id = var.gcp_service_account_id
}

resource "google_service_account_iam_binding" "wi_iam_binding" {
  service_account_id = data.google_service_account.serviceaccount.name
  role               = "roles/iam.workloadIdentityUser"
  members            = local.annotations
}
variables.tf
variable "gcp_service_account_id" {
  type        = string
  default     = ""
  description = "GCP service account ID (before `@`)"
}

variable "k8s_service_accounts" {
  type        = list(string)
  default     = []
  description = "Kubernetes service accounts in the format of `$ns/$sa_name`"
}

3. KSA を作成し、GSA へのアノテーションを追加

$ kubectl create serviceaccount --namespace k8s-namespace ksa-name
$ kubectl annotate serviceaccount \
  --namespace k8s-namespace \
  ksa-name \
  iam.gke.io/gcp-service-account=gsa-name@project-id.iam.gserviceaccount.com
Manifest
serviceaccount.yaml
apiVersion: v1
kind: ServiceAccount
metadata:
  name: $KSA_NAME
  namespace: $K8S_NAMESPACE
  annotations:
    iam.gke.io/gcp-service-account: "$GSA_NAME@$PROJECT_ID.iam.gserviceaccount.com"

4. Pod で KSA を指定

deployment.yaml
apiVersion: apps/v1
kind: Deployment
# ...
spec:
  template:
    spec:
      serviceAccountName: $KSA_NAME
      # ...
      nodeSelector:
        iam.gke.io/gke-metadata-server-enabled: "true"
7
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
7
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?