Workload Identity 聯盟

本文將概略介紹 Workload Identity Federation。 使用 Workload Identity Federation,您可以使用聯合身分 (而非服務帳戶金鑰),讓地端部署或多雲端工作負載存取 Google Cloud 資源。

您可以使用 Workload Identity Federation,搭配下列工作負載進行驗證:使用 X.509 用戶端憑證;在 Amazon Web Services (AWS) 或 Azure 上執行;在地端部署的 Active Directory 上執行;部署服務,例如 GitHub 和 GitLab;以及支援 OpenID Connect (OIDC) 或安全宣告標記語言 (SAML) V2.0 的任何識別資訊提供者 (IdP)。

為何要使用 Workload Identity Federation?

在外部執行的應用程式 Google Cloud 可以使用服務帳戶金鑰存取 Google Cloud 資源。不過,服務帳戶金鑰是功能強大的憑證,如果管理不當就會帶來安全風險。Workload Identity Federation 可免除服務帳戶金鑰相關的維護和安全負擔。

透過 Workload Identity Federation,您可以使用 Identity and Access Management (IAM),將 IAM 角色授予工作負載身分集區中以聯合身分為基礎的主體。您可以授予主體特定 Google Cloud 資源的存取權。這種方法稱為「直接存取」。或者,您也可以授予服務帳戶存取權,讓服務帳戶存取 Google Cloud 資源。這種做法稱為「服務帳戶模擬」。

Workload Identity 集區

工作負載身分集區是可管理外部身分的實體。

一般來說,建議您為每個需要存取資源的非Google Cloud環境建立新集區,例如開發、預先發布或正式環境。 Google Cloud

Workload Identity Pool 提供者

workload identity pool 提供者是描述 Google Cloud 和 IdP 之間關係的實體,包括:

  • AWS
  • Microsoft Entra ID
  • GitHub
  • GitLab
  • Kubernetes 叢集
  • Okta
  • 地端 Active Directory 同盟服務 (AD FS)
  • Terraform

Workload Identity Federation 遵循 OAuth 2.0 權杖交換規格。您將 IdP 的憑證提供給安全權杖服務,該服務會驗證憑證上的身分,然後傳回聯合權杖做為交換。

使用本機 JWK 的 OIDC 提供者

如要同盟沒有公開 OIDC 端點的工作負載,您可以直接將 OIDC JSON Web Key Sets (JWKS) 上傳至集區。如果您在自己的環境中代管 Terraform 或 GitHub Enterprise,或是受到法規限制而無法公開網址,就可能需要這麼做。詳情請參閱「管理 OIDC JWK (選用)」。

屬性對應

外部 IdP 發行的權杖包含一或多個屬性。部分 IdP 會將這些屬性稱為「權杖附加資訊」。

Google 安全性權杖服務權杖也包含一或多個屬性,如下表所示:

屬性 說明
google.subject 這是必要旗標,使用者的專屬 ID。這項屬性會用於 IAM principal:// 角色繫結,並顯示在 Cloud Logging 記錄中。值不得重複,且長度不得超過 127 個字元。
google.groups 選用。身分所屬的群組集合。這項屬性會用於 IAM principalSet:// 角色繫結,以便授予群組所有成員的存取權。
attribute.NAME 選用。您最多可以定義 50 個自訂屬性,並在 IAM principalSet:// 角色繫結中使用這些屬性,將存取權授予具有特定屬性的所有身分。

屬性對應關係會定義如何從外部權杖取得 Google Security Token Service 權杖屬性的值。您可以為每個 Google Security Token Service 權杖屬性定義屬性對應,格式如下:

TARGET_ATTRIBUTE=SOURCE_EXPRESSION

更改下列內容:

  • TARGET_ATTRIBUTE 是 Google 安全性權杖服務權杖的屬性
  • SOURCE_EXPRESSION 是一般運算語言 (CEL) 運算式,可轉換外部 IdP 發行的權杖中的一或多個屬性

以下列出屬性對應範例:

  • 將判斷結果屬性 sub 指派給 google.subject:

    google.subject=assertion.sub
    
  • 串連多個聲明屬性:

    google.subject='myprovider::' + assertion.aud + '::' + assertion.sub
    
  • 將 GUID 值斷言屬性 workload_id 對應至名稱,然後將結果指派給名為 attribute.my_display_name 的自訂屬性:

    attribute.my_display_name={
      "8bb39bdb-1cc5-4447-b7db-a19e920eb111": "Workload1",
      "55d36609-9bcf-48e0-a366-a3cf19027d2a": "Workload2"
    }[assertion.workload_id]
    
  • 使用 CEL 邏輯運算子和函式,根據身分的 Amazon Resource Name (ARN),將名為 attribute.environment 的自訂屬性設為 prod 或 test:

    attribute.environment=assertion.arn.contains(":instance-profile/Production") ? "prod" : "test"
    
  • 使用 extract 函式,以所擔任的角色名稱或身分 ARN (如果沒有擔任任何角色) 填入自訂屬性 aws_role。

    attribute.aws_role=assertion.arn.contains('assumed-role') ? assertion.arn.extract('{account_arn}assumed-role/') + 'assumed-role/' + assertion.arn.extract('assumed-role/{role_name}/') : assertion.arn
    
  • 使用 split 函式,依據指定分隔符切分字串。舉例來說,如要從電子郵件地址屬性擷取 username 屬性,請在 @ 符號處分割電子郵件地址屬性的值,並使用第一個字串,然後使用下列屬性對應:

    attribute.username=assertion.email.split("@")[0]
    
  • 使用 join 函式,以指定分隔符號串連字串清單。舉例來說,如要透過串連字串清單並以 . 做為分隔符號,填入自訂屬性 department,請使用下列屬性對應:

    attribute.department=assertion.department.join(".")
    

使用 X.509 用戶端憑證時,Workload Identity Federation 會預設將 google.subject 對應至用戶端憑證主體通用名稱 (assertion.subject.dn.cn):

google.subject=assertion.subject.dn.cn

您也可以從葉片和中繼憑證對應其他屬性。

如果是 AWS,如未指定屬性對應,Google 會套用下列預設對應,涵蓋最常見的情況:

google.subject=assertion.arn
attribute.aws_role=assertion.arn.contains('assumed-role') ? assertion.arn.extract('{account_arn}assumed-role/') + 'assumed-role/' + assertion.arn.extract('assumed-role/{role_name}/') : assertion.arn

如果已承擔角色,這項對應會將 google.subject 設為呼叫端的 ARN,並將 attribute.aws_role 設為承擔的角色 ARN (不含工作階段名稱),否則會設為呼叫端的 ARN。您也可以提供自訂對應。

如果是 OIDC 和 SAML 提供者,您必須提供屬性對應。如要建構對應,請參閱供應商的說明文件,瞭解憑證的屬性清單。

詳情請參閱 attributeMapping 欄位的 API 說明文件。

屬性條件

屬性條件是 CEL 運算式,可檢查判斷提示屬性和目標屬性。如果特定憑證的屬性條件評估結果為 true,系統就會接受該憑證。否則系統會拒絕憑證。

您可以使用屬性條件,限制哪些身分可以透過工作負載身分集區進行驗證。

屬性條件適用於下列情境:

  • 如果工作負載使用的 IdP 可供一般大眾存取,您可以限制存取權,只允許您選擇的身分存取工作負載身分集區。

  • 如果您使用 IdP 搭配多個雲端平台,可以防止用於其他平台的憑證與 Google Cloud搭配使用,反之亦然。這有助於避免混淆的代理人問題。

工作負載身分集區提供者的屬性條件可以使用 assertion 關鍵字,這個關鍵字是指代表 IdP 發行驗證憑證的地圖。您可以使用點記號存取地圖的值。舉例來說,AWS 憑證包含 arn 值,您可以將其存取為 assertion.arn。此外,屬性條件可以使用供應商屬性對應中定義的任何屬性。

下列範例只允許來自具有特定 AWS 角色的身分的要求:

attribute.aws_role == "ROLE_MAPPING"

詳情請參閱 attributeCondition 欄位的 API 說明文件。

存取權管理

權杖交換流程會傳回同盟存取權杖。您可以代表主體身分,使用這個同盟存取權杖授予工作負載 Google Cloud 資源的存取權,並取得短期有效的 OAuth 2.0 存取權杖。

您可以使用這個存取權杖提供 IAM 存取權。

建議您使用 Workload Identity Federation,直接提供資源存取權 Google Cloud 。雖然大部分 Google Cloud API 都支援 Workload Identity Federation,但部分 API 有限制。或者,您也可以使用服務帳戶模擬。

您可以使用短期存取權杖,呼叫資源或服務帳戶有權存取的任何 API。 Google Cloud

直接存取資源

您可以透過直接資源存取權,使用資源專屬角色,直接在 Google Cloud 資源上授予外部身分存取權。

替代做法:服務帳戶模擬

除了直接授予資源存取權,您也可以使用服務帳戶模擬。

您必須將 Workload Identity 使用者角色 (roles/iam.workloadIdentityUser) 授予服務帳戶。

主體範圍和安全性

您可以使用主體類型,將存取權授予主體或主體子集。

主體類型

下表說明如何將主體定義為個人和身分群組:

身分 ID 格式
單一識別身分 principal://iam.googleapis.com/projects/PROJECT_NUMBER/locations/global/workloadIdentityPools/POOL_ID/subject/SUBJECT_ATTRIBUTE_VALUE
群組中的所有身分 principalSet://iam.googleapis.com/projects/PROJECT_NUMBER/locations/global/workloadIdentityPools/POOL_ID/group/GROUP_ID
具有特定屬性值的所有身分 principalSet://iam.googleapis.com/projects/PROJECT_NUMBER/locations/global/workloadIdentityPools/POOL_ID/attribute.ATTRIBUTE_NAME/ATTRIBUTE_VALUE

後續步驟