解決代管 Cloud Service Mesh 問題

本文說明 Cloud Service Mesh 的常見問題和解決方法,例如在 Pod 中注入 istio.istio-system 時,安裝工具會產生 HTTP 400 狀態碼和叢集成員資格錯誤等錯誤。

如需 Cloud Service Mesh 疑難排解的額外協助,請參閱「取得支援」。

修訂版本回報為健康狀態不良錯誤

如果受管理 Cloud Service Mesh 的服務代理程式沒有必要的 Identity and Access Management (IAM) 角色,您可能會看到一般 Revision(s) reporting unhealthy 錯誤。一般來說,如果角色遭 Terraform、Puppet 或 CI/CD 重新設定撤銷,就會發生這種情況。

排解這項錯誤所需的步驟,取決於您使用的是 Google Cloud 控制台還是 Google Cloud CLI。

Google Cloud 控制台

  1. 在 Google Cloud 控制台中,依序前往「IAM & Admin」(IAM 與管理) >「IAM」(身分與存取權管理)

  2. 選取「包含 Google 提供的角色授權」

  3. 查看「主體」清單。

    如果清單中顯示服務代理程式和必要 IAM 角色,表示設定正確。

    如果清單未列出服務代理程式和必要角色,請繼續下一個步驟。

  4. 將 Anthos 服務網格服務代理程式角色 (roles/anthosservicemesh.serviceAgent) 授予專案中的 Cloud Service Mesh 服務代理程式。如需相關操作說明,請參閱「管理專案、資料夾和機構的存取權」。

Google Cloud CLI

  1. 在 Google Cloud CLI 中執行下列指令,確認是否已授予必要的 IAM 角色:

    gcloud projects get-iam-policy PROJECT_ID  \
    --flatten="bindings[].members" \
    --filter="bindings.members:serviceAccount:service-PROJECT_NUMBER@gcp-sa-servicemesh.iam.gserviceaccount.com AND bindings.role:roles/anthosservicemesh.serviceAgent" \
    --format='table(bindings.role)'
    
  2. 查看 ROLE 清單。

    如果清單中顯示任何角色,表示設定正確無誤。

    如果清單中沒有任何角色,表示必要角色已遭撤銷。

  3. 如要將必要角色授予服務代理,請執行下列指令:

     gcloud projects add-iam-policy-binding PROJECT_ID \
     --member="serviceAccount:service-PROJECT_NUMBER@gcp-sa-servicemesh.iam.gserviceaccount.com" \
     --role="roles/anthosservicemesh.serviceAgent"
    

安裝工具產生 HTTP 400 錯誤

安裝工具可能會產生類似下列的 HTTP 400 錯誤:

HealthCheckContainerError, message: Cloud Run error: Container failed to start.
Failed to start and then listen on the port defined by the PORT environment
variable. Logs for this revision might contain more information.

如果 Kubernetes 叢集未啟用 Workload Identity,就可能發生這項錯誤。如要啟用,請使用下列指令:

export CLUSTER_NAME=...
export PROJECT_ID=...
export LOCATION=...
gcloud container clusters update $CLUSTER_NAME --zone $LOCATION \
    --workload-pool=$PROJECT_ID.svc.id.goog

代管資料層狀態

下列指令會顯示受管理資料層的狀態:

gcloud container fleet mesh describe --project PROJECT_ID

下表列出所有可能的受管理資料平面狀態:

狀態 程式碼 說明
ACTIVE OK 受管理資料層正常運作。
DISABLED DISABLED 如果沒有命名空間或修訂版本設定為使用受管理資料平面,就會處於這種狀態。按照操作說明透過 Fleet API 啟用代管 Cloud Service Mesh,或在透過 asmcli 佈建代管 Cloud Service Mesh 後,啟用代管資料層。請注意,您必須透過註解命名空間或修訂版本啟用代管資料層,才能取得代管資料層狀態報告。如果沒有註解任何命名空間或修訂版本,註解個別 Pod 會導致系統管理這些 Pod,但功能狀態為 DISABLED
FAILED_PRECONDITION MANAGED_CONTROL_PLANE_REQUIRED 代管資料層需要可用的代管 Cloud Service Mesh 控制層。
PROVISIONING PROVISIONING 正在佈建代管資料層。如果這個狀態持續超過 10 分鐘,可能發生錯誤,請與支援團隊聯絡
STALLED INTERNAL_ERROR 受管理資料層因內部錯誤情況而無法運作。如果問題仍未解決,請聯絡支援團隊
NEEDS_ATTENTION UPGRADE_FAILURES 管理型資料平面需要手動介入,才能讓服務恢復正常狀態。如要進一步瞭解如何解決這個問題,請參閱NEEDS_ATTENTION 狀態

NEEDS_ATTENTION 個州/省

如果 gcloud container fleet mesh describe 指令顯示受管理資料層狀態為 NEEDS_ATTENTION 狀態,且代碼為 UPGRADE_FAILURES,則表示受管理資料層無法升級特定工作負載。這些工作負載會標示 dataplane-upgrade: failed,以供受管理資料平面服務進一步分析。您必須手動重新啟動 Proxy,才能升級。如要取得需要注意的 Pod 清單,請執行下列指令:

kubectl get pods --all-namespaces -l dataplane-upgrade=failed

叢集成員錯誤 (未指定識別資訊提供者)

安裝工具可能會因叢集成員資格錯誤而失敗,例如:

asmcli: [ERROR]: Cluster has memberships.hub.gke.io CRD but no identity
provider specified. Please ensure that an identity provider is available for the
registered cluster.

如果註冊叢集前未啟用 GKE Workload Identity,就可能發生這項錯誤。您可以使用 gcloud container fleet memberships register --enable-workload-identity 指令,透過指令列重新註冊叢集。

檢查代管控制層狀態

如要檢查代管控制平面的狀態,請執行 gcloud container fleet mesh describe --project FLEET_PROJECT_ID

在回應中,membershipStates[].servicemesh.controlPlaneManagement.details 欄位可能會說明具體錯誤。

如需更多詳細資料,請檢查叢集中的ControlPlaneRevision自訂資源,該資源會在佈建受管理控制層時更新,或佈建失敗時更新。

如要檢查資源狀態,請將 NAME 替換為各管道對應的值:asm-managedasm-managed-stableasm-managed-rapid

kubectl describe controlplanerevision NAME -n istio-system

輸出內容類似如下:

    Name:         asm-managed

    …

    Status:
      Conditions:
        Last Transition Time:  2021-08-05T18:56:32Z
        Message:               The provisioning process has completed successfully
        Reason:                Provisioned
        Status:                True
        Type:                  Reconciled
        Last Transition Time:  2021-08-05T18:56:32Z
        Message:               Provisioning has finished
        Reason:                ProvisioningFinished
        Status:                True
        Type:                  ProvisioningFinished
        Last Transition Time:  2021-08-05T18:56:32Z
        Message:               Provisioning has not stalled
        Reason:                NotStalled
        Status:                False
        Type:                  Stalled

Reconciled 條件會判斷代管控制層是否正常運作。如果是 true,代表控制層已順利運作。 Stalled 會判斷代管控制層佈建程序是否發生錯誤。如果 StalledMessage 欄位會包含特定錯誤的詳細資訊。如要進一步瞭解可能發生的錯誤,請參閱「停滯代碼」一節。

ControlPlaneRevision 停滯代碼

Stalled 條件在 ControlPlaneRevisions 狀態中可能成立的原因有很多。

原因 訊息 說明
PreconditionFailed 系統僅支援 GKE 成員資格,但「${CLUSTER_NAME}」不是 GKE 叢集。 目前的叢集似乎不是 GKE 叢集。受管理控制層僅適用於 GKE 叢集。
不支援 ControlPlaneRevision 名稱:${NAME} ControlPlaneRevision 的名稱必須是下列其中一個:
  • asm-managed
  • asm-managed-rapid
  • asm-managed-stable
不支援的 ControlPlaneRevision 命名空間:${NAMESPACE} ControlPlaneRevision 的命名空間必須為 istio-system
ControlPlaneRevision (名稱為 ${NAME}) 不支援管道${CHANNEL}。預期 ${OTHER_CHANNEL} ControlPlaneRevision 的名稱必須與 ControlPlaneRevision 的管道相符,如下所示:
  • asm-managed -> regular
  • asm-managed-rapid -> rapid
  • asm-managed-stable -> stable
頻道不得省略或空白 Channel 是 ControlPlaneRevision 的必填欄位。自訂資源缺少或空白。
不支援的控制平面修訂版本類型:${TYPE} managed_service 是 ControlPlaneRevisionType 欄位的唯一允許欄位。
不支援的 Kubernetes 版本:${VERSION} 支援 Kubernetes 1.15 以上版本。
Workload Identity 未啟用 請在叢集上啟用 Workload Identity。
不支援的工作負載集區:${POOL} 工作負載集區的格式必須為 ${PROJECT_ID}.svc.id.goog
ProvisioningFailed 更新叢集資源時發生錯誤 Google 無法更新叢集內資源,例如 CRD 和 Webhook。
MutatingWebhookConfiguration「istiod-asm-managed」包含網址為 ${EXISTING_URL} 的 Webhook,但預期為 ${EXPECTED_URL} 為避免中斷安裝程序,Google 不會覆寫現有 Webhook。如要採用這項行為,請手動更新。
ValidatingWebhookConfiguration ${NAME} 包含網址為 ${EXISTING_URL} 的 Webhook,但預期為 ${EXPECTED_URL} 為避免中斷安裝程序,Google 不會覆寫現有 Webhook。如要採用這項行為,請手動更新。

代管 Cloud Service Mesh 無法連線至 GKE 叢集

2022 年 6 月至 2022 年 9 月期間,Google 完成了與授權網路、Cloud Run 和 Cloud Run functions 相關的安全工作,這些服務位於 Google Kubernetes Engine (GKE)。先前使用受管理 Cloud Service Mesh,但在遷移前停止使用的專案,沒有 Cloud Run 和 GKE 之間通訊所需的 API。

在這種情況下,受管理 Cloud Service Mesh 佈建作業會失敗,且 Cloud Logging 會顯示下列錯誤訊息:

Connect Gateway API has not been used in project [*PROJECT_NUMBER*] before or it is disabled.
Enable it by visiting https://console.developers.google.com/apis/api/connectgateway.googleapis.com/overview?project=[*PROJECT_NUMBER*] then retry.
If you enabled this API recently, wait a few minutes for the action to propagate to our systems and retry.

使用下列查詢篩選這則訊息:

resource.type="istio_control_plane"
resource.labels.project_id=[*PROJECT_ID*]
resource.labels.location=[*REGION*]
severity=ERROR
jsonPayload.message=~"Connect Gateway API has not been used in project"

在此期間,側車注入和部署任何 Cloud Service Mesh 相關的 Kubernetes 自訂資源也會失敗,且 Cloud Logging 會顯示下列警告訊息:

Error creating: Internal error occurred: failed calling webhook
"rev.namespace.sidecar-injector.istio.io": failed to call webhook: an error on
the server ("unknown") has prevented the request from succeeding.

使用下列查詢篩選這則訊息:

resource.type="k8s_cluster"
resource.labels.project_id=[*PROJECT_ID*]
resource.labels.location=[*REGION*]
resource.labels.cluster_name=[*CLUSTER_NAME*]
severity=WARNING
jsonPayload.message=~"Internal error occurred: failed calling webhook"

如何解決這個問題:

  1. 啟用必要的 connectgateway API:

     gcloud services enable connectgateway.googleapis.com --project=[*PROJECT_ID*]
    
  2. 重新安裝代管 Cloud Service Mesh

  3. 對工作負載執行滾動式重新啟動。

Google Cloud 未啟用 API

如果代管 Cloud Service Mesh 叢集使用TRAFFIC_DIRECTOR 控制層實作,則必須啟用特定 API。

  1. 啟用所有必要 API,包括未使用代管 Cloud Service Mesh 時列為「可停用」的 API。

    gcloud services enable --project=[*PROJECT_ID*] \
        trafficdirector.googleapis.com \
        networkservices.googleapis.com \
        networksecurity.googleapis.com
    
  2. 請確認您沒有任何自動工具會還原這項變更。如果錯誤再次發生,請更新任何相關設定或允許清單。