本指南介绍如何在 GKE on AWS 上配置工作负载身份以控制工作负载对 GCP 资源的访问权限。其中包含一个有关如何使用身份从集群访问 Google Cloud 资源的示例。
如需了解如何将工作负载身份与 AWS IAM 账号搭配使用以控制对 AWS 资源的访问权限,请参阅将工作负载身份与 AWS 搭配使用。
概览
工作负载身份使用 Google Cloud IAM 权限来控制对 Google Cloud 资源的访问权限。借助 Workload Identity,您可以为每个工作负载分配不同的 IAM 角色。通过这种精细权限控制,您可以遵循最小权限原则。 如果没有工作负载身份,您必须将 Google Cloud IAM 角色分配给 GKE on AWS 节点,从而为这些节点上的所有工作负载提供与节点本身相同的权限。
前提条件
使用 Kubernetes v1.20 或更高版本创建用户集群。
如果您的 AWS VPC 使用代理或防火墙,请将以下网址列入许可名单:
securetoken.googleapis.com
iamcredentials.googleapis.com
sts.googleapis.com
在
anthos-aws
目录中,使用anthos-gke
将上下文切换到用户集群。cd anthos-aws env HTTPS_PROXY=http://localhost:8118 \ anthos-gke aws clusters get-credentials CLUSTER_NAME
将 CLUSTER_NAME 替换为用户集群名称。使用以下命令启用此功能所需的四项新服务:
gcloud services enable securetoken.googleapis.com gcloud services enable iam.googleapis.com gcloud services enable iamcredentials.googleapis.com gcloud services enable sts.googleapis.com
编写 WI 池和提供商名称
每个 Google Cloud 项目都会自动创建一个托管式工作负载身份池,其名称格式为 PROJECT_ID.svc.id.goog
。同样,Google Cloud 会创建一个名称遵循 https://gkehub.googleapis.com/projects/PROJECT_ID/locations/global/memberships/MEMBERSHIP_ID
格式的身份提供商。如需详细了解工作负载身份池,请参阅支持队列的组件。使用您的项目 ID 和成员资格 ID 编写以下名称,如下所示:
export PROJECT_ID=USER_PROJECT_NAME export CLUSTER_MEMBERSHIP_ID=PROJECT_MEMBERSHIP_NAME export IDP="https://gkehub.googleapis.com/projects/${PROJECT_ID}/locations/global/memberships/${CLUSTER_MEMBERSHIP_ID}" export WI_POOL="${PROJECT_ID}.svc.id.goog"
请替换以下内容:
- 将 USER_PROJECT_NAME 替换为用户选择的用户项目名称
- 将 PROJECT_MEMBERSHIP_NAME 替换为集群的成员资格名称
创建 IAM 政策绑定
创建政策绑定,以允许 Kubernetes 服务账号 (KSA) 模拟 Google Cloud 服务账号 (GSA)。
export K8S_NAMESPACE=KUBERNETES_NAMESPACE export KSA_NAME=KUBERNETES_SA_NAME export GCP_SA_EMAIL="WORKLOAD_IDENTITY_TEST@${PROJECT_ID}.iam.gserviceaccount.com" gcloud iam service-accounts add-iam-policy-binding \ --role roles/iam.workloadIdentityUser \ --member "serviceAccount:$WI_POOL[$K8S_NAMESPACE/$KSA_NAME]" $GCP_SA_EMAIL
请替换以下内容:
- 将 KUBERNETES_NAMESPACE 替换为在其中定义了 Kubernetes 服务账号的 Kubernetes 命名空间
- 将 WORKLOAD_IDENTITY_TEST 替换为您选择的工作负载名称
- 将 KUBERNETES_SA_NAME 替换为与应用关联的 Kubernetes 服务账号的名称
创建 SDK ConfigMap
执行以下 shell 脚本,将工作负载身份详细信息存储在 ConfigMap 中。当 Pod 装载 ConfigMap 时,Google Cloud CLI 便可读取工作负载身份详细信息。
cat << EOF > cfmap.yaml kind: ConfigMap apiVersion: v1 metadata: namespace: ${K8S_NAMESPACE} name: my-cloudsdk-config data: config: | { "type": "external_account", "audience": "identitynamespace:${WI_POOL}:${IDP}", "service_account_impersonation_url": "https://iamcredentials.googleapis.com/v1/projects/-/serviceAccounts/${GCP_SA_EMAIL}:generateAccessToken", "subject_token_type": "urn:ietf:params:oauth:token-type:jwt", "token_url": "https://sts.googleapis.com/v1/token", "credential_source": { "file": "/var/run/secrets/tokens/gcp-ksa/token" } } EOF env HTTPS_PROXY=http://localhost:8118 \ kubectl apply -f cfmap.yaml
创建 Kubernetes 服务账号
使用与 IAM 绑定中相同的名称和命名空间在用户集群上创建 KSA。
cat << EOF > k8s-service-account.yaml apiVersion: v1 kind: ServiceAccount metadata: name: ${KSA_NAME} namespace: ${K8S_NAMESPACE} EOF env HTTPS_PROXY=http://localhost:8118 \ kubectl apply -f k8s-service-account.yaml
创建 Pod
接下来,使用上文创建的服务账号令牌投影和 ConfigMap 创建 Pod。
创建示例 Pod yaml 文件。
cat << EOF > sample-pod.yaml apiVersion: v1 kind: Pod metadata: name: sample-pod namespace: ${K8S_NAMESPACE} spec: serviceAccountName: ${KSA_NAME} containers: - command: - /bin/bash - -c - while :; do echo '.'; sleep 500 ; done image: google/cloud-sdk name: cloud-sdk env: - name: GOOGLE_APPLICATION_CREDENTIALS value: /var/run/secrets/tokens/gcp-ksa/google-application-credentials.json volumeMounts: - name: gcp-ksa mountPath: /var/run/secrets/tokens/gcp-ksa readOnly: true volumes: - name: gcp-ksa projected: defaultMode: 420 sources: - serviceAccountToken: path: token audience: ${WI_POOL} expirationSeconds: 172800 - configMap: name: my-cloudsdk-config optional: false items: - key: "config" path: "google-application-credentials.json" EOF
将 Pod 的 YAML 应用到您的集群。
env HTTPS_PROXY=http://localhost:8118 \ kubectl apply -f sample-pod.yaml
使用 Google Cloud 工作负载身份
支持的 SDK 版本
如需使用 Google Cloud 工作负载身份功能,您必须使用支持该功能的 SDK 来构建代码。如需查看支持 Google Cloud 工作负载身份的 SDK 版本列表,请参阅队列工作负载身份。
使用工作负载身份的示例代码
本部分包含使用 Google Cloud 工作负载身份的示例 Python 代码。此示例中的服务账号使用具有“Cloud Storage Admin”权限的身份来列出 Google Cloud 项目的所有 Cloud Storage 存储桶。
在 Pod 中运行 shell 命令。
env HTTPS_PROXY=http://localhost:8118 \ kubectl exec -it sample-pod -- bash
运行脚本以列出项目的存储桶。
# execute these commands inside the Pod pip install --upgrade google-cloud-storage cat << EOF > sample-list-bucket.py from google.cloud import storage storage_client = storage.Client() buckets = storage_client.list_buckets() for bucket in buckets: print(bucket.name) EOF env GOOGLE_CLOUD_PROJECT=USER_PROJECT_NAME \ python3 sample-list-bucket.py
将 USER_PROJECT_NAME 替换为您的 Google Cloud 项目。
详情
- 队列工作负载身份
- 工作负载身份联合
- 从 OIDC 身份提供商访问资源(Kubernetes 集群是 OIDC 身份提供商)
- 将工作负载身份与 AWS 搭配使用