本文档介绍了如何为 Google Distributed Cloud connected 设置和使用 Workload Identity 集群身份验证。Workload Identity 集群身份验证使用 短期令牌和工作负载身份联合来允许工作负载 安全地访问 Google Cloud 资源,而不是使用服务帐号密钥。短期凭据是 OAuth 2.0 访问令牌。默认情况下,访问令牌会在 1 小时后过期。
借助 Workload Identity 集群身份验证,工作负载可以使用自己的 Kubernetes 身份来 访问 Google Cloud 资源,或模拟 Google 服务帐号。
与使用服务帐号密钥相比,Workload Identity 集群身份验证有以下两个主要优势:
提高安全性:如果服务账号密钥管理不当,则会带来安全风险。OAuth 2.0 令牌和工作负载身份联合被视为服务帐号密钥的最佳实践替代方案。如需详细了解服务帐号令牌,请参阅短期有效的服务帐号。如需详细了解工作负载身份联合,请参阅 工作负载身份联合。
减少维护工作:服务账号密钥需要更多维护工作。 定期轮替和保护这些密钥可能会带来管理负担。
本页面适用于负责设置、监控和管理底层技术基础架构生命周期的管理员、架构师和运维人员。如需详细了解我们在 Google Cloud 内容中提及的常见角色和示例任务,请参阅常见的 GKE 用户角色和 任务。
集群管理
本指南介绍了如何为应用使用工作负载身份联合。 对于 Distributed Cloud connected 集群,系统会自动管理集群级工作负载身份联合。
Distributed Cloud connected 集群由 Google 通过
Distributed Cloud Edge Container API创建和管理,方法是使用
gcloud edge-cloud container clusters create
命令或在 Google Cloud 控制台中进行操作。
Distributed Cloud connected 集群会自动注册到其创建所在的项目中的舰队。您无需执行任何手动舰队注册。工作负载身份联合池会自动提供,并
遵循格式 PROJECT_ID.svc.id.goog。
准备工作
如需设置工作负载身份联合,请先验证您的 Google Cloud 项目是否已启用以下 API。如需了解如何 启用 API,请参阅 启用服务:
iam.googleapis.comsts.googleapis.comiamcredentials.googleapis.comgkehub.googleapis.com
确保您已安装以下命令行工具:
- 最新版本的 Google Cloud CLI,其中
包含
gcloud,用于与交互的命令行工具 Google Cloud。 kubectl
如果您使用 Cloud Shell 作为与 Google Cloud交互的 Shell 环境,则系统会为您安装这些工具。
- 最新版本的 Google Cloud CLI,其中
包含
确保您已初始化用于您项目的 gcloud CLI。
确保您拥有项目的以下 IAM 角色。 执行设置需要这些角色:
- 所有者 (
roles/owner) 或 - IAM Security Admin (
roles/iam.securityAdmin) 和 Service Account Admin (roles/iam.serviceAccountAdmin)
- 所有者 (
在以下部分中,您将创建服务账号并授予 Workload Identity 集群身份验证所需的角色。
推荐:工作负载身份联合直接资源访问权限
借助工作负载身份联合直接资源访问权限,您可以使用工作负载身份联合向 Kubernetes ServiceAccount 授予 IAM 角色,以便它可以直接访问 Google Cloud资源。
| 身份 | 用途 | 角色 |
|---|---|---|
| Kubernetes ServiceAccount |
工作负载使用的 Kubernetes 身份。向此身份授予访问所需 Google Cloud 资源所需的
角色。此示例授予了 roles/storage.objectViewer 角色和 roles/logging.admin 角色。 |
roles/storage.objectViewerroles/logging.admin |
替代方法:IAM 服务帐号模拟
或者,您可以配置 Kubernetes ServiceAccount 以使用 IAM 服务帐号模拟。
| 服务账号 | 用途 | 角色 |
|---|---|---|
| Google 服务帐号 | 集群内工作负载模拟的 Google 服务帐号。向此服务帐号授予访问所需 Google Cloud 资源所需的角色。 | 取决于要访问的资源。 |
| Kubernetes ServiceAccount |
向此身份授予模拟 Google 服务帐号的权限。此授予使用 roles/iam.workloadIdentityUser 角色。 |
roles/iam.workloadIdentityUser
|
设置服务账号
以下部分包含有关如何创建所需的 Kubernetes ServiceAccount 以及如何使用工作负载身份联合直接资源访问权限或 Google 服务帐号模拟向其授予 Workload Identity 集群身份验证所需角色的说明。
创建 Kubernetes ServiceAccount
在集群中,使用
kubectl create
命令为 Pod 创建 Kubernetes ServiceAccount。您还可以使用任何现有的
ServiceAccount,包括命名空间中的默认 ServiceAccount。
kubectl create serviceaccount KSA_NAME --namespace NAMESPACE
替换以下值:
KSA_NAME:Kubernetes ServiceAccount 的名称NAMESPACE:集群的命名空间
使用工作负载身份联合授予直接资源访问权限
如需直接向 Kubernetes ServiceAccount 身份授予 Identity and Access Management 角色,请按以下步骤操作。
使用 gcloud projects describe 命令查找您的项目数字编号:
gcloud projects describe PROJECT_ID --format="value(projectNumber)"将
PROJECT_ID替换为您的项目 ID。使用 gcloud projects add-iam-policy-binding 命令向 Kubernetes 身份正文授予所需的角色:
gcloud projects add-iam-policy-binding PROJECT_ID \ --member="principal://iam.gserviceaccount.com/projects/PROJECT_NUMBER/locations/global/workloadIdentityPools/PROJECT_ID.svc.id.goog/subject/ns/NAMESPACE/sa/KSA_NAME" \ --role=roles/storage.objectViewer gcloud projects add-iam-policy-binding PROJECT_ID \ --member="principal://iam.gserviceaccount.com/projects/PROJECT_NUMBER/locations/global/workloadIdentityPools/PROJECT_ID.svc.id.goog/subject/ns/NAMESPACE/sa/KSA_NAME" \ --role=roles/logging.admin替换以下值:
PROJECT_NUMBER:您的项目数字编号NAMESPACE:集群的命名空间KSA_NAME:Kubernetes ServiceAccount 的名称
替代方法:使用 IAM 服务帐号模拟来授予访问权限
如果您希望工作负载模拟 Google 服务帐号,请按以下步骤操作。
使用 gcloud iam service-accounts create 命令创建 Google 服务帐号:
gcloud iam service-accounts create my-app-sa \ --project=PROJECT_ID将
PROJECT_ID替换为您的项目 ID。使用 gcloud projects add-iam-policy-binding 命令向 Google 服务帐号授予所需的角色:
gcloud projects add-iam-policy-binding PROJECT_ID \ --member=serviceAccount:my-app-sa@PROJECT_ID.iam.gserviceaccount.com \ --role=roles/storage.objectViewer gcloud projects add-iam-policy-binding PROJECT_ID \ --member=serviceAccount:my-app-sa@PROJECT_ID.iam.gserviceaccount.com \ --role=roles/logging.admin使用 gcloud iam service-accounts add-iam-policy-binding 命令向 Kubernetes ServiceAccount 授予模拟 Google 服务帐号的权限:
gcloud iam service-accounts add-iam-policy-binding my-app-sa@PROJECT_ID.iam.gserviceaccount.com \ --role=roles/iam.workloadIdentityUser \ --member="serviceAccount:PROJECT_ID.svc.id.goog[NAMESPACE/KSA_NAME]"替换以下值:
NAMESPACE:集群的命名空间KSA_NAME:Kubernetes ServiceAccount 的名称
使用 kubectl annotate 命令为 Kubernetes ServiceAccount 添加注解,以将其与 Google 服务帐号相关联:
kubectl annotate serviceaccount \ --namespace NAMESPACE KSA_NAME \ iam.gke.io/gcp-service-account=my-app-sa@PROJECT_ID.iam.gserviceaccount.com
配置工作负载
更新 Pod 规范以使用 Kubernetes ServiceAccount 并挂载投影的令牌卷。由于 Distributed Cloud connected 集群位于
Google Cloud之外,因此您还必须提供凭据配置文件,并将
GOOGLE_APPLICATION_CREDENTIALS 环境变量设置为指向该文件。
Google Cloud Pod 中的客户端库使用这些凭据通过 Security Token Service API 将
Kubernetes 令牌交换为 Google Cloud 访问令牌。
生成
credential-configuration.json文件。根据您使用的是工作负载身份联合直接资源访问权限还是 IAM 服务帐号模拟,选择相应的命令。工作负载身份联合直接资源访问权限
使用 gcloud iam workload-identity-pools create-cred-config 命令:
gcloud iam workload-identity-pools create-cred-config \ projects/PROJECT_NUMBER/locations/global/workloadIdentityPools/PROJECT_ID.svc.id.goog/providers/attestor \ --credential-source-file=/var/run/secrets/tokens/gcp-ksa/token \ --credential-source-type=text \ --output-file=credential-configuration.json使用 IAM 服务帐号模拟来授予访问权限
使用 gcloud iam workload-identity-pools create-cred-config 命令:
gcloud iam workload-identity-pools create-cred-config \ projects/PROJECT_NUMBER/locations/global/workloadIdentityPools/PROJECT_ID.svc.id.goog/providers/attestor \ --service-account=my-app-sa@PROJECT_ID.iam.gserviceaccount.com \ --credential-source-file=/var/run/secrets/tokens/gcp-ksa/token \ --credential-source-type=text \ --output-file=credential-configuration.json将
PROJECT_NUMBER替换为您的 Google Cloud 项目 编号。您可以通过运行gcloud projects describe PROJECT_ID --format="value(projectNumber)"找到项目编号。使用
kubectl create configmap命令创建 KubernetesConfigMap以存储配置文件:kubectl create configmap CREDENTIAL_CONFIG_MAP \ --namespace NAMESPACE \ --from-file=credential-configuration.json替换以下值:
CREDENTIAL_CONFIG_MAP:ConfigMap的名称,其中包含凭据配置文件NAMESPACE:集群的命名空间
使用以下 YAML 内容更新 Pod 规范:
spec: serviceAccountName: KSA_NAME containers: - name: MY_CONTAINER image: MY_IMAGE env: - name: GOOGLE_APPLICATION_CREDENTIALS value: /var/run/secrets/tokens/gcp-creds/credential-configuration.json volumeMounts: - mountPath: /var/run/secrets/tokens/gcp-ksa name: gcp-ksa - mountPath: /var/run/secrets/tokens/gcp-creds name: gcp-creds readOnly: true volumes: - name: gcp-ksa projected: defaultMode: 0420 sources: - serviceAccountToken: path: token audience: PROJECT_ID.svc.id.goog expirationSeconds: 3600 - name: gcp-creds configMap: name: CREDENTIAL_CONFIG_MAP替换以下值:
KSA_NAME:Kubernetes ServiceAccount 的名称MY_CONTAINER:容器的名称MY_IMAGE:映像的名称
限制
当您为 Distributed Cloud connected 使用工作负载身份联合时,不支持以下功能:
- 在令牌交换过程中使用代理服务器
如需了解如何将工作负载身份联合与 VPC Service Controls 结合使用, 请参阅 配置 VPC Service Controls 集成。