无法将Micrometer指标写入Stackdriver:权限拒绝问题排查
问题描述
在GCP环境中使用io.micrometer.stackdriver.StackdriverMeterRegistry时收到权限报错:
io.grpc.StatusRuntimeException: PERMISSION_DENIED: Permission monitoring.metricDescriptors.list denied (or the resource may not exist). at io.grpc.Status.asRuntimeException(Status.java:539) ... 14 common frames omitted Wrapped by: com.google.api.gax.rpc.PermissionDeniedException: io.grpc.StatusRuntimeException: PERMISSION_DENIED: Permission monitoring.metricDescriptors.list denied (or the resource may not exist).
GKE Autopilot集群的Terraform配置如下:
resource "google_container_cluster" "primary-cluster" { provider = google-beta project = var.project_id name = "${var.project_id}-autopilot-cluster" location = var.region node_locations = toset(var.k8s_node_zones) ip_allocation_policy { } network = google_compute_network.vpc.name subnetwork = google_compute_subnetwork.vpc-subnet.name min_master_version = var.k8s_min_cluster_version release_channel { channel = var.k8s_release_channel } enable_autopilot = true cluster_autoscaling { auto_provisioning_defaults { service_account = google_service_account.gke-service-account.email image_type = "COS_CONTAINERD" disk_size = 10 oauth_scopes = [ "https://www.googleapis.com/auth/cloud-platform", "https://www.googleapis.com/auth/devstorage.full_control", "https://www.googleapis.com/auth/logging.write", "https://www.googleapis.com/auth/monitoring", "https://www.googleapis.com/auth/monitoring.read", "https://www.googleapis.com/auth/monitoring.write" ] } } } resource "google_project_iam_member" "logging_writer" { project = var.project_id role = "roles/logging.logWriter" member = "serviceAccount:${google_service_account.gke-service-account.email}" } resource "google_project_iam_member" "metric_writer" { project = var.project_id role = "roles/monitoring.metricWriter" member = "serviceAccount:${google_service_account.gke-service-account.email}" }
已给gke-service-account配置roles/monitoring.metricWriter角色,GKE默认指标、日志功能正常,Pod也能通过com.google.cloud.storage.Storage访问Cloud Storage。怀疑问题与Autopilot强制启用的Workload Identity特性相关,寻求解决办法。
解决方法
- 补充缺失的权限:
roles/monitoring.metricWriter角色不包含monitoring.metricDescriptors.list权限,需要给关联的服务账号添加roles/monitoring.viewer角色(该角色包含所需的metricDescriptors.list权限),或者直接添加单独的monitoring.metricDescriptors.list权限。对应的Terraform配置示例:resource "google_project_iam_member" "monitoring_viewer" { project = var.project_id role = "roles/monitoring.viewer" member = "serviceAccount:${google_service_account.gke-service-account.email}" } - 确认Workload Identity绑定关系:如果Pod使用了Kubernetes服务账号(KSA),需要确保KSA已与GCP服务账号(GSA)
gke-service-account建立正确的Workload Identity绑定。绑定的Terraform配置示例:
同时,需要在Kubernetes服务账号的注解中指定对应的GCP服务账号:resource "google_service_account_iam_binding" "workload_identity_binding" { service_account_id = google_service_account.gke-service-account.name role = "roles/iam.workloadIdentityUser" members = [ "serviceAccount:${var.project_id}.svc.id.goog[<你的命名空间>/<你的Kubernetes服务账号>]", ] }apiVersion: v1 kind: ServiceAccount metadata: annotations: iam.gke.io/gcp-service-account: <gke-service-account的邮箱> name: <你的Kubernetes服务账号> namespace: <你的命名空间> - 验证权限生效:执行以下命令检查GCP服务账号的权限:
确认输出中包含gcloud projects get-iam-policy ${var.project_id} --filter="bindings.members:serviceAccount:${google_service_account.gke-service-account.email}" --format=jsonroles/monitoring.metricWriter和roles/monitoring.viewer(或单独的monitoring.metricDescriptors.list权限)。
内容的提问来源于stack exchange,提问作者Stefano L
相关产品推荐
相关产品推荐

